Пример #1
0
static void do_handle_error(liGnuTLSFilter *f, const char *gnutlsfunc, int r, gboolean writing) {
	switch (r) {
	case GNUTLS_E_AGAIN:
		if (writing) f->write_wants_read = TRUE;
		break;
	case GNUTLS_E_REHANDSHAKE:
#ifdef HAVE_SAVE_RENEGOTIATION
		if (f->initial_handshaked_finished && !gnutls_safe_renegotiation_status(f->session)) {
			_ERROR(f->srv, f->wrk, f->log_context, "%s: client initiated unsafe renegotitation, closing connection", gnutlsfunc);
			f_close_with_alert(f, r);
		} else {
			_DEBUG(f->srv, f->wrk, f->log_context, "%s: client initiated renegotitation", gnutlsfunc);
		}
#else
		if (f->initial_handshaked_finished) {
			_ERROR(f->srv, f->wrk, f->log_context, "%s: client initiated renegotitation, closing connection", gnutlsfunc);
			f_close_with_alert(f, r);
		}
#endif
		break;
	case GNUTLS_E_UNEXPECTED_PACKET_LENGTH:
		f_close_with_alert(f, r);
		break;
	case GNUTLS_E_UNKNOWN_CIPHER_SUITE:
	case GNUTLS_E_UNSUPPORTED_VERSION_PACKET:
		_DEBUG(f->srv, f->wrk, f->log_context, "%s (%s): %s", gnutlsfunc,
			gnutls_strerror_name(r), gnutls_strerror(r));
		f_close_with_alert(f, r);
		break;
	default:
		if (gnutls_error_is_fatal(r)) {
			_ERROR(f->srv, f->wrk, f->log_context, "%s (%s): %s", gnutlsfunc,
				gnutls_strerror_name(r), gnutls_strerror(r));
			if (f->initial_handshaked_finished) {
				f_close_with_alert(f, r);
			} else {
				f_abort_gnutls(f);
			}
		} else {
			_ERROR(f->srv, f->wrk, f->log_context, "%s non fatal (%s): %s", gnutlsfunc,
				gnutls_strerror_name(r), gnutls_strerror(r));
		}
	}
}
Пример #2
0
void doit(void)
{
  /* Server stuff. */
  gnutls_certificate_credentials_t serverx509cred;
  gnutls_session_t server;
  int sret = GNUTLS_E_AGAIN;
  /* Client stuff. */
  gnutls_certificate_credentials_t clientx509cred;
  gnutls_session_t client;
  int cret = GNUTLS_E_AGAIN;

  /* General init. */
  gnutls_global_init ();
  gnutls_global_set_log_function (tls_log_func);
  if (debug) gnutls_global_set_log_level (2);

  /* Init server */
  gnutls_certificate_allocate_credentials (&serverx509cred);
  gnutls_certificate_set_x509_key_mem (serverx509cred,
                                       &server_cert, &server_key,
                                       GNUTLS_X509_FMT_PEM);
  gnutls_init (&server, GNUTLS_SERVER);
  gnutls_credentials_set (server, GNUTLS_CRD_CERTIFICATE, serverx509cred);
  gnutls_priority_set_direct (server, "NORMAL", NULL);
  gnutls_transport_set_push_function (server, server_push);
  gnutls_transport_set_pull_function (server, server_pull);
  gnutls_transport_set_ptr (server, (gnutls_transport_ptr_t)server);

  /* Init client */
  gnutls_certificate_allocate_credentials (&clientx509cred);
  gnutls_init (&client, GNUTLS_CLIENT);
  gnutls_credentials_set (client, GNUTLS_CRD_CERTIFICATE, clientx509cred);
  gnutls_priority_set_direct (client, "NORMAL", NULL);
  gnutls_transport_set_push_function (client, client_push);
  gnutls_transport_set_pull_function (client, client_pull);
  gnutls_transport_set_ptr (client, (gnutls_transport_ptr_t)client);

  /* Check that initially no session use the extension. */
  if (gnutls_safe_renegotiation_status (server)
      || gnutls_safe_renegotiation_status (client))
    {
      puts ("Client or server using extension before handshake?");
      abort ();
    }

  HANDSHAKE(client, server);

  /* Check that both sessions use the extension. */
  if (!gnutls_safe_renegotiation_status (server)
      || !gnutls_safe_renegotiation_status (client))
    {
      puts ("Client or server not using safe renegotiation extension?");
      abort ();
    }

  sret = gnutls_rehandshake (server);
  if (debug)
    {
      tls_log_func (0, "gnutls_rehandshake (server)...\n");
      tls_log_func (0, gnutls_strerror (sret));
      tls_log_func (0, "\n");
    }

  {
    ssize_t n;
    char b[1];
    n = gnutls_record_recv (client, b, 1);
    if (n != GNUTLS_E_REHANDSHAKE)
      abort ();
  }

  HANDSHAKE(client, server);

  /* Check that session still use the extension. */
  if (!gnutls_safe_renegotiation_status (server)
      || !gnutls_safe_renegotiation_status (client))
    {
      puts ("Client or server not using safe renegotiation extension?");
      abort ();
    }

  /* Check that this API does not affect anything after first
     handshake.
     gnutls_safe_negotiation_set_initial (server, 0); */

  sret = gnutls_rehandshake (server);
  if (debug)
    {
      tls_log_func (0, "gnutls_rehandshake (server)...\n");
      tls_log_func (0, gnutls_strerror (sret));
      tls_log_func (0, "\n");
    }

  {
    ssize_t n;
    char b[1];
    n = gnutls_record_recv (client, b, 1);
    if (n != GNUTLS_E_REHANDSHAKE)
      abort ();
  }

  HANDSHAKE(client, server);

  /* Check that disabling the extension will break rehandshakes.
     gnutls_safe_renegotiation_set (client, 0); */

  sret = gnutls_rehandshake (server);
  if (debug)
    {
      tls_log_func (0, "gnutls_rehandshake (server)...\n");
      tls_log_func (0, gnutls_strerror (sret));
      tls_log_func (0, "\n");
    }

  {
    ssize_t n;
    char b[1];
    n = gnutls_record_recv (client, b, 1);
    if (n != GNUTLS_E_REHANDSHAKE)
      abort ();
  }

  HANDSHAKE(client, server);

  gnutls_bye (client, GNUTLS_SHUT_RDWR);
  gnutls_bye (server, GNUTLS_SHUT_RDWR);

  gnutls_deinit (client);
  gnutls_deinit (server);

  gnutls_certificate_free_credentials (serverx509cred);
  gnutls_certificate_free_credentials (clientx509cred);

  gnutls_global_deinit ();

  if (debug)
    {
      puts ("Self-test successful");
    }

  return;
}
Пример #3
0
static void do_handle_error(liGnuTLSFilter *f, const char *gnutlsfunc, int r, gboolean writing) {
	switch (r) {
	case GNUTLS_E_AGAIN:
		if (writing) f->write_wants_read = TRUE;
		return;
	case GNUTLS_E_REHANDSHAKE:
#ifdef HAVE_SAVE_RENEGOTIATION
		if (f->initial_handshaked_finished && !gnutls_safe_renegotiation_status(f->session)) {
			_ERROR(f->srv, f->wrk, f->log_context, "%s: client initiated unsafe renegotitation, closing connection", gnutlsfunc);
			f_close_with_alert(f, r);
		} else {
			_DEBUG(f->srv, f->wrk, f->log_context, "%s: client initiated renegotitation", gnutlsfunc);
		}
#else
		if (f->initial_handshaked_finished) {
			_ERROR(f->srv, f->wrk, f->log_context, "%s: client initiated renegotitation, closing connection", gnutlsfunc);
			f_close_with_alert(f, r);
		}
#endif
		return;
	case GNUTLS_E_UNEXPECTED_PACKET_LENGTH:
		f_close_with_alert(f, r);
		return;
	case GNUTLS_E_UNKNOWN_CIPHER_SUITE:
	case GNUTLS_E_UNSUPPORTED_VERSION_PACKET:
		_DEBUG(f->srv, f->wrk, f->log_context, "%s (%s): %s", gnutlsfunc,
			gnutls_strerror_name(r), gnutls_strerror(r));
		f_close_with_alert(f, r);
		return;
	case GNUTLS_E_FATAL_ALERT_RECEIVED:
	case GNUTLS_E_WARNING_ALERT_RECEIVED:
		{
			gnutls_alert_description_t alert_desc = gnutls_alert_get(f->session);
			const char* alert_desc_name = gnutls_alert_get_name(alert_desc);
			_INFO(f->srv, f->wrk, f->log_context, "%s (%s): %s %s (%u)", gnutlsfunc,
				gnutls_strerror_name(r), gnutls_strerror(r),
				(NULL != alert_desc_name) ? alert_desc_name : "unknown alert",
				(unsigned int) alert_desc);
		}
		/* error not handled yet: break instead of return */
		break;
	default:
		if (gnutls_error_is_fatal(r)) {
			_ERROR(f->srv, f->wrk, f->log_context, "%s (%s): %s", gnutlsfunc,
				gnutls_strerror_name(r), gnutls_strerror(r));
		} else {
			_WARNING(f->srv, f->wrk, f->log_context, "%s non fatal (%s): %s", gnutlsfunc,
				gnutls_strerror_name(r), gnutls_strerror(r));
		}
		/* error not handled yet: break instead of return */
		break;
	}

	/* generic error handling */
	if (gnutls_error_is_fatal(r)) {
		if (f->initial_handshaked_finished) {
			f_close_with_alert(f, r);
		} else {
			f_abort_gnutls(f);
		}
	}
}
Пример #4
0
void doit(void)
{
	/* Server stuff. */
	gnutls_certificate_credentials_t serverx509cred;
	gnutls_session_t server;
	int sret = GNUTLS_E_AGAIN;
	/* Client stuff. */
	gnutls_certificate_credentials_t clientx509cred;
	gnutls_session_t client;
	int cret = GNUTLS_E_AGAIN;

	/* General init. */
	global_init();
	gnutls_global_set_log_function(tls_log_func);
	if (debug)
		gnutls_global_set_log_level(2);

	/* Init server */
	gnutls_certificate_allocate_credentials(&serverx509cred);
	gnutls_certificate_set_x509_key_mem(serverx509cred,
					    &server_cert, &server_key,
					    GNUTLS_X509_FMT_PEM);
	gnutls_init(&server, GNUTLS_SERVER);
	gnutls_credentials_set(server, GNUTLS_CRD_CERTIFICATE,
			       serverx509cred);
	gnutls_priority_set_direct(server, "NORMAL", NULL);
	gnutls_transport_set_push_function(server, server_push);
	gnutls_transport_set_pull_function(server, server_pull);
	gnutls_transport_set_ptr(server, server);

	/* Init client */
	gnutls_certificate_allocate_credentials(&clientx509cred);
	gnutls_init(&client, GNUTLS_CLIENT);
	gnutls_credentials_set(client, GNUTLS_CRD_CERTIFICATE,
			       clientx509cred);
	gnutls_priority_set_direct(client, "NORMAL", NULL);
	gnutls_transport_set_push_function(client, client_push);
	gnutls_transport_set_pull_function(client, client_pull);
	gnutls_transport_set_ptr(client, client);

	HANDSHAKE(client, server);

	if (!gnutls_safe_renegotiation_status(client) ||
	    !gnutls_safe_renegotiation_status(server)) {
		tls_log_func(0, "Session not using safe renegotiation!\n");
		exit(1);
	}

	if (!(gnutls_session_get_flags(client) & GNUTLS_SFLAGS_SAFE_RENEGOTIATION) ||
	    !(gnutls_session_get_flags(server) & GNUTLS_SFLAGS_SAFE_RENEGOTIATION)) {
		tls_log_func(0, "Session not using safe renegotiation!\n");
		exit(1);
	}

	sret = gnutls_rehandshake(server);
	if (debug) {
		tls_log_func(0, "gnutls_rehandshake (server)...\n");
		tls_log_func(0, gnutls_strerror(sret));
		tls_log_func(0, "\n");
	}

	{
		ssize_t n;
		char b[1];
		n = gnutls_record_recv(client, b, 1);
		if (n != GNUTLS_E_REHANDSHAKE)
			abort();
	}

	HANDSHAKE(client, server);

	if (!gnutls_safe_renegotiation_status(client) ||
	    !gnutls_safe_renegotiation_status(server)) {
		tls_log_func(0,
			     "Rehandshaked session not using safe renegotiation!\n");
		exit(1);
	}

	if (!(gnutls_session_get_flags(client) & GNUTLS_SFLAGS_SAFE_RENEGOTIATION) ||
	    !(gnutls_session_get_flags(server) & GNUTLS_SFLAGS_SAFE_RENEGOTIATION)) {
		tls_log_func(0,
			     "Rehandshaked session not using safe renegotiation!\n");
		exit(1);
	}

	gnutls_bye(client, GNUTLS_SHUT_RDWR);
	gnutls_bye(server, GNUTLS_SHUT_RDWR);

	gnutls_deinit(client);
	gnutls_deinit(server);

	gnutls_certificate_free_credentials(serverx509cred);
	gnutls_certificate_free_credentials(clientx509cred);

	gnutls_global_deinit();

	if (debug) {
		puts("Self-test successful");
	}

	return;
}
Пример #5
0
int
main (int argc, char *argv[])
{
    int debug_level = argc - 1;
    int exit_code = EXIT_SUCCESS;
    /* Server stuff. */
    gnutls_certificate_credentials_t serverx509cred;
    gnutls_session_t server;
    int sret = GNUTLS_E_AGAIN;
    /* Client stuff. */
    gnutls_certificate_credentials_t clientx509cred;
    gnutls_session_t client;
    int cret = GNUTLS_E_AGAIN;

    /* General init. */
    gnutls_global_init ();
    gnutls_global_set_log_function (tls_log_func);
    gnutls_global_set_log_level (debug_level);

    /* Init server */
    gnutls_certificate_allocate_credentials (&serverx509cred);
    gnutls_certificate_set_x509_key_mem (serverx509cred,
                                         &server_cert, &server_key,
                                         GNUTLS_X509_FMT_PEM);
    gnutls_init (&server, GNUTLS_SERVER);
    gnutls_credentials_set (server, GNUTLS_CRD_CERTIFICATE, serverx509cred);
    gnutls_priority_set_direct (server, "NORMAL:%DISABLE_SAFE_RENEGOTIATION",
                                NULL);
    gnutls_transport_set_push_function (server, server_push);
    gnutls_transport_set_pull_function (server, server_pull);

    /* Init client */
    gnutls_certificate_allocate_credentials (&clientx509cred);
    gnutls_init (&client, GNUTLS_CLIENT);
    gnutls_credentials_set (client, GNUTLS_CRD_CERTIFICATE, clientx509cred);
    gnutls_priority_set_direct (client, "NORMAL", NULL);
    gnutls_transport_set_push_function (client, client_push);
    gnutls_transport_set_pull_function (client, client_pull);

    /* Check that initially no session use the extension. */
    if (gnutls_safe_renegotiation_status (server)
            || gnutls_safe_renegotiation_status (client))
    {
        puts ("Client or server using extension before handshake?");
        abort ();
    }

    do
    {
        static int max_iter = 0;
        if (max_iter++ > 10)
            abort ();

        if (cret == GNUTLS_E_AGAIN)
        {
            cret = gnutls_handshake (client);
            if (debug_level > 0)
            {
                tls_log_func (0, "gnutls_handshake (client)...\n");
                tls_log_func (0, gnutls_strerror (cret));
                tls_log_func (0, "\n");
            }
        }

        if (sret == GNUTLS_E_AGAIN)
        {
            sret = gnutls_handshake (server);
            if (debug_level > 0)
            {
                tls_log_func (0, "gnutls_handshake (server)...\n");
                tls_log_func (0, gnutls_strerror (sret));
                tls_log_func (0, "\n");
            }
        }
    }
    while (
        /* Not done: */
        !(cret == GNUTLS_E_SUCCESS && sret == GNUTLS_E_SUCCESS)
        /* No error: */
        && (cret == GNUTLS_E_AGAIN || sret == GNUTLS_E_AGAIN));

    if (cret != GNUTLS_E_SUCCESS && sret != GNUTLS_E_SUCCESS)
        exit_code = EXIT_FAILURE;

    if (gnutls_safe_renegotiation_status (client) ||
            gnutls_safe_renegotiation_status (server))
    {
        tls_log_func (0, "Session using safe renegotiation but shouldn't?!\n");
        exit_code = EXIT_FAILURE;
    }

    sret = gnutls_rehandshake (server);
    if (debug_level > 0)
    {
        tls_log_func (0, "gnutls_rehandshake (server)...\n");
        tls_log_func (0, gnutls_strerror (sret));
        tls_log_func (0, "\n");
    }

    {
        ssize_t n;
        char b[1];
        n = gnutls_record_recv (client, b, 1);
        if (n != GNUTLS_E_REHANDSHAKE)
            abort ();
    }

    cret = GNUTLS_E_AGAIN;
    sret = GNUTLS_E_AGAIN;

    do
    {
        static int max_iter = 0;
        if (max_iter++ > 10)
            abort ();

        if (cret == GNUTLS_E_AGAIN)
        {
            cret = gnutls_handshake (client);
            if (debug_level > 0)
            {
                tls_log_func (0, "second gnutls_handshake (client)...\n");
                tls_log_func (0, gnutls_strerror (cret));
                tls_log_func (0, "\n");
            }
        }

        if (sret == GNUTLS_E_AGAIN)
        {
            sret = gnutls_handshake (server);
            if (debug_level > 0)
            {
                tls_log_func (0, "second gnutls_handshake (server)...\n");
                tls_log_func (0, gnutls_strerror (sret));
                tls_log_func (0, "\n");
            }
        }

        if (cret == GNUTLS_E_UNSAFE_RENEGOTIATION_DENIED)
            break;
    }
    while (
        /* Not done: */
        !(cret == GNUTLS_E_SUCCESS && sret == GNUTLS_E_SUCCESS)
        /* No error: */
        && (cret == GNUTLS_E_AGAIN || sret == GNUTLS_E_AGAIN));

    if (cret != GNUTLS_E_UNSAFE_RENEGOTIATION_DENIED
            && sret != GNUTLS_E_SUCCESS)
        exit_code = 1;

    if (gnutls_safe_renegotiation_status (client) ||
            gnutls_safe_renegotiation_status (server))
    {
        tls_log_func (0, "Rehandshaked worked and uses safe reneg?!\n");
        exit_code = EXIT_FAILURE;
    }

    gnutls_bye (client, GNUTLS_SHUT_RDWR);
    gnutls_bye (server, GNUTLS_SHUT_RDWR);

    gnutls_deinit (client);
    gnutls_deinit (server);

    free (to_server);
    free (to_client);

    gnutls_certificate_free_credentials (serverx509cred);

    gnutls_global_deinit ();

    if (debug_level > 0)
    {
        if (exit_code == 0)
            puts ("Self-test successful");
        else
            puts ("Self-test failed");
    }

    return exit_code;
}