DANE support structures, constructructors and accessors
[openssl.git] / demos / bio / sconnect.c
1 /* NOCW */
2 /* demos/bio/sconnect.c */
3
4 /*-
5  * A minimal program to do SSL to a passed host and port.
6  * It is actually using non-blocking IO but in a very simple manner
7  * sconnect host:port - it does a 'GET / HTTP/1.0'
8  *
9  * cc -I../../include sconnect.c -L../.. -lssl -lcrypto
10  */
11 #include <stdio.h>
12 #include <stdlib.h>
13 #include <unistd.h>
14 #include <string.h>
15 #include <openssl/err.h>
16 #include <openssl/ssl.h>
17
18 #define HOSTPORT "localhost:4433"
19 #define CAFILE "root.pem"
20
21 extern int errno;
22
23 int main(argc, argv)
24 int argc;
25 char *argv[];
26 {
27     const char *hostport = HOSTPORT;
28     const char *CAfile = CAFILE;
29     char *hostname;
30     char *cp;
31     BIO *out = NULL;
32     char buf[1024 * 10], *p;
33     SSL_CTX *ssl_ctx = NULL;
34     SSL *ssl;
35     BIO *ssl_bio;
36     int i, len, off, ret = 1;
37
38     if (argc > 1)
39         hostport = argv[1];
40     if (argc > 2)
41         CAfile = argv[2];
42
43     hostname = OPENSSL_strdup(hostport);
44     if ((cp = strchr(hostname, ':')) != NULL)
45         *cp = 0;
46
47 #ifdef WATT32
48     dbug_init();
49     sock_init();
50 #endif
51
52     /* Lets get nice error messages */
53     SSL_load_error_strings();
54
55     /* Setup all the global SSL stuff */
56     OpenSSL_add_ssl_algorithms();
57     ssl_ctx = SSL_CTX_new(TLS_client_method());
58
59     /* Enable trust chain verification */
60     SSL_CTX_set_verify(ssl_ctx, SSL_VERIFY_PEER, NULL);
61     SSL_CTX_load_verify_locations(ssl_ctx, CAfile, NULL);
62
63     /* Lets make a SSL structure */
64     ssl = SSL_new(ssl_ctx);
65     SSL_set_connect_state(ssl);
66
67     /* Enable peername verification */
68     if (SSL_set1_host(ssl, hostname) <= 0)
69         goto err;
70
71     /* Use it inside an SSL BIO */
72     ssl_bio = BIO_new(BIO_f_ssl());
73     BIO_set_ssl(ssl_bio, ssl, BIO_CLOSE);
74
75     /* Lets use a connect BIO under the SSL BIO */
76     out = BIO_new(BIO_s_connect());
77     BIO_set_conn_hostname(out, hostport);
78     BIO_set_nbio(out, 1);
79     out = BIO_push(ssl_bio, out);
80
81     p = "GET / HTTP/1.0\r\n\r\n";
82     len = strlen(p);
83
84     off = 0;
85     for (;;) {
86         i = BIO_write(out, &(p[off]), len);
87         if (i <= 0) {
88             if (BIO_should_retry(out)) {
89                 fprintf(stderr, "write DELAY\n");
90                 sleep(1);
91                 continue;
92             } else {
93                 goto err;
94             }
95         }
96         off += i;
97         len -= i;
98         if (len <= 0)
99             break;
100     }
101
102     for (;;) {
103         i = BIO_read(out, buf, sizeof(buf));
104         if (i == 0)
105             break;
106         if (i < 0) {
107             if (BIO_should_retry(out)) {
108                 fprintf(stderr, "read DELAY\n");
109                 sleep(1);
110                 continue;
111             }
112             goto err;
113         }
114         fwrite(buf, 1, i, stdout);
115     }
116
117     ret = 1;
118     goto done;
119
120  err:
121     if (ERR_peek_error() == 0) { /* system call error */
122         fprintf(stderr, "errno=%d ", errno);
123         perror("error");
124     } else
125         ERR_print_errors_fp(stderr);
126  done:
127     BIO_free_all(out);
128     SSL_CTX_free(ssl_ctx);
129     return (ret == 1);
130 }