3939#define MAXLINE 4096
4040#define SERV_PORT 11111
4141
42- int main (int argc , char * * argv )
42+ static int new_udp_client_socket (WOLFSSL * ssl , const char * host );
43+ static int talk_to_server (WOLFSSL * ssl , const char * msg );
44+
45+ int
46+ main (int argc ,
47+ char * argv [])
4348{
4449 /* standard variables used in a dtls client*/
45- int sockfd = 0 ;
46- int err1 ;
47- int readErr ;
48- struct sockaddr_in servAddr ;
49- const char * host = argv [1 ];
50- WOLFSSL * ssl = 0 ;
51- WOLFSSL_CTX * ctx = 0 ;
52- WOLFSSL * sslResume = 0 ;
53- WOLFSSL_SESSION * session = 0 ;
54- char * srTest = "testing session resume" ;
55- char cert_array [] = "../certs/ca-cert.pem" ;
56- char buffer [80 ];
57- char * certs = cert_array ;
58- /* variables used in a dtls client for session reuse*/
59- int recvlen ;
60- char sendLine [MAXLINE ];
61- char recvLine [MAXLINE - 1 ];
50+ int sockfd = 0 ;
51+ int err1 ;
52+ const char * host = argv [1 ];
53+ WOLFSSL * ssl = NULL ; /* The ssl for original connection. */
54+ WOLFSSL * ssl_res = NULL ; /* The ssl for resuming connection. */
55+ WOLFSSL_CTX * ctx = NULL ;
56+ WOLFSSL_SESSION * session = NULL ;
57+ char cert_array [] = "../certs/ca-cert.pem" ;
58+ char buffer [80 ];
59+ char * certs = cert_array ;
60+ int ret = 0 ;
6261
62+ /* variables used in a dtls client for session reuse*/
6363 if (argc != 2 ) {
6464 printf ("usage: udpcli <IP address>\n" );
65- return 1 ;
65+ return EXIT_FAILURE ;
6666 }
6767
6868 wolfSSL_Init ();
@@ -72,163 +72,194 @@ int main (int argc, char** argv)
7272
7373 if ( (ctx = wolfSSL_CTX_new (wolfDTLSv1_2_client_method ())) == NULL ) {
7474 fprintf (stderr , "wolfSSL_CTX_new error.\n" );
75- return 1 ;
75+ return EXIT_FAILURE ;
7676 }
7777
7878 if (wolfSSL_CTX_load_verify_locations (ctx , certs , 0 ) != SSL_SUCCESS ) {
7979 fprintf (stderr , "Error loading %s, please check the file.\n" , certs );
80- return 1 ;
80+ return EXIT_FAILURE ;
8181 }
8282
8383 ssl = wolfSSL_new (ctx );
8484 if (ssl == NULL ) {
85- printf ("unable to get ssl object" );
86- return 1 ;
87- }
88-
89- memset (& servAddr , 0 , sizeof (servAddr ));
90- servAddr .sin_family = AF_INET ;
91- servAddr .sin_port = htons (SERV_PORT );
92- if ( (inet_pton (AF_INET , host , & servAddr .sin_addr )) < 1 ) {
93- printf ("Error and/or invalid IP address" );
94- return 1 ;
85+ printf ("error: wolfSSL_new failed\n" );
86+ return EXIT_FAILURE ;
9587 }
9688
97- wolfSSL_dtls_set_peer (ssl , & servAddr , sizeof ( servAddr ) );
89+ sockfd = new_udp_client_socket (ssl , host );
9890
99- if ( ( sockfd = socket ( AF_INET , SOCK_DGRAM , 0 )) < 0 ) {
100- printf ("cannot create a socket. " );
101- return 1 ;
91+ if (sockfd <= 0 ) {
92+ printf ("error: new_udp_client_socket failed\n " );
93+ return EXIT_FAILURE ;
10294 }
10395
104- wolfSSL_set_fd (ssl , sockfd );
10596 if (wolfSSL_connect (ssl ) != SSL_SUCCESS ) {
10697 err1 = wolfSSL_get_error (ssl , 0 );
10798 memset (buffer , 0 , 80 );
10899 printf ("err = %d, %s\n" , err1 , wolfSSL_ERR_error_string (err1 , buffer ));
109100 printf ("SSL_connect failed" );
110- return 1 ;
101+ return EXIT_FAILURE ;
111102 }
112103
113- /*****************************************************************************/
114- /* Code for sending datagram to server */
115-
116- /* Loop while the user gives input or until an EOF is read */
117- while ( fgets (sendLine , MAXLINE , stdin ) != NULL ) {
104+ /* Save the session */
105+ session = wolfSSL_get1_session (ssl );
118106
119- /* Attempt to send sendLine to the server */
120- if ( ( wolfSSL_write (ssl , sendLine , strlen (sendLine ))) !=
121- strlen (sendLine ) ) {
122- printf ("Error: wolfSSL_write failed.\n" );
123- }
107+ if (session == NULL ) {
108+ printf ("error: get session failed\n" );
109+ return EXIT_FAILURE ;
110+ }
124111
125- /* Attempt to read a message from server and store it in recvLine */
126- recvlen = wolfSSL_read (ssl , recvLine , sizeof (recvLine ) - 1 );
112+ printf ("info: saved session: %p\n" , session );
127113
128- /* Error checking wolfSSL_read */
129- if (recvlen < 0 ) {
130- readErr = wolfSSL_get_error (ssl , 0 );
131- if (readErr != SSL_ERROR_WANT_READ ) {
132- printf ("Error: wolfSSL_read failed.\n" );
133- }
134- }
114+ ret = talk_to_server (ssl , "first client message" );
135115
136- recvLine [ recvlen ] = '\0' ;
137- fputs ( recvLine , stdout ) ;
116+ if ( ret ) {
117+ return EXIT_FAILURE ;
138118 }
139- /* */
140- /*****************************************************************************/
141-
142- /* Keep track of the old session information */
143- wolfSSL_write (ssl , srTest , sizeof (srTest ));
144- session = wolfSSL_get_session (ssl );
145- sslResume = wolfSSL_new (ctx );
146119
147- /* Cleanup the memory used by the old session & ssl object */
120+ /* Close the socket */
148121 wolfSSL_shutdown (ssl );
149122 wolfSSL_free (ssl );
150123 close (sockfd );
151124
152- /* Perform setup with new variables/old session information */
153- memset (& servAddr , 0 , sizeof (servAddr ));
154- servAddr .sin_family = AF_INET ;
155- servAddr .sin_port = htons (SERV_PORT );
156- if ( (inet_pton (AF_INET , host , & servAddr .sin_addr )) < 1 ) {
157- printf ("Error and/or invalid IP address" );
158- return 1 ;
125+ ssl = NULL ;
126+ sockfd = 0 ;
127+
128+ /* Make a new WOLFSSL. */
129+ ssl_res = wolfSSL_new (ctx );
130+ if (ssl_res == NULL ) {
131+ printf ("error: wolfSSL_new failed\n" );
132+ return EXIT_FAILURE ;
159133 }
160134
161- wolfSSL_dtls_set_peer (sslResume , & servAddr , sizeof (servAddr ));
135+ /* Set up to resume the session */
136+ ret = wolfSSL_set_session (ssl_res , session );
162137
163- if ( ( sockfd = socket ( AF_INET , SOCK_DGRAM , 0 )) < 0 ) {
164- printf ( "cannot create a socket." );
165- return 1 ;
138+ if (ret != WOLFSSL_SUCCESS ) {
139+ fprintf ( stderr , "error: wolfSSL_set_session returned: %d\n" , ret );
140+ return EXIT_FAILURE ;
166141 }
167142
168- wolfSSL_set_fd (sslResume , sockfd );
143+ /* Open a new udp socket. */
144+ sockfd = new_udp_client_socket (ssl_res , host );
169145
170- /* New method call - specifies to the WOLFSSL object to use the *
171- * given WOLFSSL_SESSION object */
172- wolfSSL_set_session (sslResume , session );
173-
174- wolfSSL_set_fd (sslResume , sockfd );
175- if (wolfSSL_connect (sslResume ) != SSL_SUCCESS ) {
176- err1 = wolfSSL_get_error (sslResume , 0 );
177- memset (buffer , 0 , 80 );
178- printf ("err = %d, %s\n" , err1 , wolfSSL_ERR_error_string (err1 , buffer ));
179- printf ("SSL_connect failed on session reuse\n" );
180- return 1 ;
146+ if (sockfd <= 0 ) {
147+ printf ("error: new_udp_client_socket failed\n" );
148+ return EXIT_FAILURE ;
181149 }
182150
183- if (wolfSSL_session_reused (sslResume )) {
184- printf ("reused session id\n" );
151+ /* Test if the resume was successful */
152+ if (wolfSSL_session_reused (ssl_res )) {
153+ printf ("info: session ID reused; Successful resume\n" );
185154 }
186155 else {
187- printf ("didn't reuse session id!!! \n" );
156+ printf ("info: session ID not reused \n" );
188157 }
189158
190- /*****************************************************************************/
191- /* Code for sending datagram to server */
192- /* Clear out variables for reuse */
193- recvlen = 0 ;
194- memset (sendLine , 0 , MAXLINE );
195- memset (recvLine , 0 , MAXLINE - 1 );
159+ ret = talk_to_server (ssl_res , "client message after resume" );
160+
161+ if (ret ) {
162+ return EXIT_FAILURE ;
163+ }
196164
197- /* Loop while the user gives input or until an EOF is read */
198- while ( fgets (sendLine , MAXLINE , stdin ) != NULL ) {
165+ /* Cleanup memory used for storing the session information */
166+ wolfSSL_shutdown (ssl_res );
167+ wolfSSL_free (ssl_res );
168+ wolfSSL_SESSION_free (session );
199169
200- /* Attempt to send sendLine to the server */
201- if ( ( wolfSSL_write (ssl , sendLine , strlen (sendLine ))) !=
202- strlen (sendLine ) ) {
203- printf ("Error: wolfSSL_write failed.\n" );
204- }
170+ close (sockfd );
171+ wolfSSL_CTX_free (ctx );
172+ wolfSSL_Cleanup ();
205173
206- /* Attempt to read a message from server and store it in recvLine */
207- recvlen = wolfSSL_read (ssl , recvLine , sizeof (recvLine ) - 1 );
174+ ssl_res = NULL ;
175+ session = NULL ;
176+ sockfd = 0 ;
208177
209- /* Error checking wolfSSL_read */
210- if (recvlen < 0 ) {
211- readErr = wolfSSL_get_error (ssl , 0 );
212- if (readErr != SSL_ERROR_WANT_READ ) {
213- printf ("Error: wolfSSL_read failed.\n" );
214- }
215- }
178+ return 0 ;
179+ }
180+
181+ /* Given an ssl structure and host, open a new udp
182+ * client socket and set it and the server address
183+ * to the ssl.
184+ **/
185+ static int
186+ new_udp_client_socket (WOLFSSL * ssl ,
187+ const char * host )
188+ {
189+ struct sockaddr_in servAddr ;
190+ int sockfd = 0 ;
191+ int ret = 0 ;
192+
193+ sockfd = socket (AF_INET , SOCK_DGRAM , 0 );
216194
217- recvLine [recvlen ] = '\0' ;
218- fputs (recvLine , stdout );
195+ if (sockfd <= 0 ) {
196+ int errsave = errno ;
197+ printf ("error: socket returned %d\n" , errsave );
198+ return -1 ;
219199 }
220- /* */
221- /*****************************************************************************/
222200
223- wolfSSL_write (sslResume , srTest , sizeof (srTest ));
201+ /* servAddr setup */
202+ memset (& servAddr , 0 , sizeof (servAddr ));
203+ servAddr .sin_family = AF_INET ;
204+ servAddr .sin_port = htons (SERV_PORT );
205+
206+ ret = inet_pton (AF_INET , host , & servAddr .sin_addr );
224207
225- /* Cleanup memory used for storing the session information */
226- wolfSSL_shutdown (sslResume );
227- wolfSSL_free (sslResume );
208+ if (ret != 1 ) {
209+ printf ("error: inet_pton %s returned %d\n" , host , ret );
210+ close (sockfd );
211+ sockfd = 0 ;
212+ return -1 ;
213+ }
228214
229- close (sockfd );
230- wolfSSL_CTX_free (ctx );
231- wolfSSL_Cleanup ();
215+ ret = wolfSSL_dtls_set_peer (ssl , & servAddr , sizeof (servAddr ));
216+
217+ if (ret != SSL_SUCCESS ) {
218+ printf ("error: wolfSSL_dtls_set_peer returned %d\n" , ret );
219+ close (sockfd );
220+ sockfd = 0 ;
221+ return -1 ;
222+ }
223+
224+ wolfSSL_set_fd (ssl , sockfd );
225+
226+ printf ("info: opened socket: %d\n" , sockfd );
227+
228+ return sockfd ;
229+ }
230+
231+ /* Send a message to the server.
232+ **/
233+ static int
234+ talk_to_server (WOLFSSL * ssl ,
235+ const char * send_msg )
236+ {
237+ char recv_msg [MAXLINE ];
238+ int recv_len ;
239+
240+ memset (recv_msg , 0 , sizeof (recv_msg ));
241+
242+ /* Attempt to send send_msg to the server */
243+ if ( ( wolfSSL_write (ssl , send_msg , strlen (send_msg ))) !=
244+ strlen (send_msg ) ) {
245+ printf ("Error: wolfSSL_write failed.\n" );
246+ return -1 ;
247+ }
248+
249+ /* Attempt to read a message from server and store it in recv_msg */
250+ recv_len = wolfSSL_read (ssl , recv_msg , sizeof (recv_msg ) - 1 );
251+
252+ /* Error checking wolfSSL_read */
253+ if (recv_len < 0 ) {
254+ int readErr = wolfSSL_get_error (ssl , 0 );
255+ if (readErr != SSL_ERROR_WANT_READ ) {
256+ printf ("Error: wolfSSL_read failed.\n" );
257+ }
258+ return -1 ;
259+ }
260+
261+ recv_msg [recv_len ] = '\0' ;
262+ printf ("info: server response: %s" , recv_msg );
232263
233264 return 0 ;
234265}
0 commit comments