saccept.c 2.1 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14
/* NOCW */
/* demos/bio/saccept.c */

/* A minimal program to server an SSL connection.
 * It uses blocking.
 * saccept host:port
 * host is the interface IP to use.  If any interface, use *:port
 * The default it *:4433
 *
 * cc -I../../include saccept.c -L../.. -lssl -lcrypto
 */

#include <stdio.h>
#include <signal.h>
15 16
#include <openssl/err.h>
#include <openssl/ssl.h>
17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48

#define CERT_FILE	"server.pem"

BIO *in=NULL;

void close_up()
	{
	if (in != NULL)
		BIO_free(in);
	}

int main(argc,argv)
int argc;
char *argv[];
	{
	char *port=NULL;
	BIO *ssl_bio,*tmp;
	SSL_CTX *ctx;
	SSL *ssl;
	char buf[512];
	int ret=1,i;

        if (argc <= 1)
		port="*:4433";
	else
		port=argv[1];

	signal(SIGINT,close_up);

	SSL_load_error_strings();

	/* Add ciphers and message digests */
49
	OpenSSL_add_ssl_algorithms();
50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72

	ctx=SSL_CTX_new(SSLv23_server_method());
	if (!SSL_CTX_use_certificate_file(ctx,CERT_FILE,SSL_FILETYPE_PEM))
		goto err;
	if (!SSL_CTX_use_PrivateKey_file(ctx,CERT_FILE,SSL_FILETYPE_PEM))
		goto err;
	if (!SSL_CTX_check_private_key(ctx))
		goto err;

	/* Setup server side SSL bio */
	ssl=SSL_new(ctx);
	ssl_bio=BIO_new_ssl(ctx,0);

	if ((in=BIO_new_accept(port)) == NULL) goto err;

	/* This means that when a new connection is acceptede on 'in',
	 * The ssl_bio will be 'dupilcated' and have the new socket
	 * BIO push into it.  Basically it means the SSL BIO will be
	 * automatically setup */
	BIO_set_accept_bios(in,ssl_bio);

again:
	/* The first call will setup the accept socket, and the second
73
	 * will get a socket.  In this loop, the first actual accept
74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107
	 * will occur in the BIO_read() function. */

	if (BIO_do_accept(in) <= 0) goto err;

	for (;;)
		{
		i=BIO_read(in,buf,512);
		if (i == 0)
			{
			/* If we have finished, remove the underlying
			 * BIO stack so the next time we call any function
			 * for this BIO, it will attempt to do an
			 * accept */
			printf("Done\n");
			tmp=BIO_pop(in);
			BIO_free_all(tmp);
			goto again;
			}
		if (i < 0) goto err;
		fwrite(buf,1,i,stdout);
		fflush(stdout);
		}

	ret=0;
err:
	if (ret)
		{
		ERR_print_errors_fp(stderr);
		}
	if (in != NULL) BIO_free(in);
	exit(ret);
	return(!ret);
	}