/** * Display what session id we have. */ private void display_session_id(SSL ssl) { byte[] session_id = ssl.GetSessionId(); if (session_id.Length > 0) { Console.WriteLine("-----BEGIN SSL SESSION PARAMETERS-----"); foreach (byte b in session_id) { Console.Write("{0:x02}", b); } Console.WriteLine("\n-----END SSL SESSION PARAMETERS-----"); } }
/* * do_client() */ private void do_client(int build_mode, string[] args) { if (build_mode < axtls.SSL_BUILD_ENABLE_CLIENT) { print_client_options(build_mode, args[1]); } int i = 1, res; int port = 4433; bool quiet = false; string password = null; int reconnect = 0; string private_key_file = null; string hostname = "127.0.0.1"; /* organise the cert/ca_cert lists */ int cert_index = 0; int ca_cert_index = 0; int cert_size = SSLUtil.MaxCerts(); int ca_cert_size = SSLUtil.MaxCACerts(); string[] cert = new string[cert_size]; string[] ca_cert = new string[ca_cert_size]; uint options = axtls.SSL_SERVER_VERIFY_LATER|axtls.SSL_DISPLAY_CERTS; byte[] session_id = null; while (i < args.Length) { if (args[i] == "-connect") { string host_port; if (i >= args.Length-1) { print_client_options(build_mode, args[i]); } host_port = args[++i]; int index_colon; if ((index_colon = host_port.IndexOf(':')) < 0) print_client_options(build_mode, args[i]); hostname = new string(host_port.ToCharArray(), 0, index_colon); port = Int32.Parse(new String(host_port.ToCharArray(), index_colon+1, host_port.Length-index_colon-1)); } else if (args[i] == "-cert") { if (i >= args.Length-1 || cert_index >= cert_size) { print_client_options(build_mode, args[i]); } cert[cert_index++] = args[++i]; } else if (args[i] == "-key") { if (i >= args.Length-1) { print_client_options(build_mode, args[i]); } private_key_file = args[++i]; options |= axtls.SSL_NO_DEFAULT_KEY; } else if (args[i] == "-CAfile") { if (i >= args.Length-1 || ca_cert_index >= ca_cert_size) { print_client_options(build_mode, args[i]); } ca_cert[ca_cert_index++] = args[++i]; } else if (args[i] == "-verify") { options &= ~(uint)axtls.SSL_SERVER_VERIFY_LATER; } else if (args[i] == "-reconnect") { reconnect = 4; } else if (args[i] == "-quiet") { quiet = true; options &= ~(uint)axtls.SSL_DISPLAY_CERTS; } else if (args[i] == "-pass") { if (i >= args.Length-1) { print_client_options(build_mode, args[i]); } password = args[++i]; } else if (build_mode == axtls.SSL_BUILD_FULL_MODE) { if (args[i] == "-debug") { options |= axtls.SSL_DISPLAY_BYTES; } else if (args[i] == "-state") { options |= axtls.SSL_DISPLAY_STATES; } else if (args[i] == "-show-rsa") { options |= axtls.SSL_DISPLAY_RSA; } else print_client_options(build_mode, args[i]); } else /* don't know what this is */ print_client_options(build_mode, args[i]); i++; } // IPHostEntry hostInfo = Dns.Resolve(hostname); IPHostEntry hostInfo = Dns.GetHostEntry(hostname); IPAddress[] addresses = hostInfo.AddressList; IPEndPoint ep = new IPEndPoint(addresses[0], port); Socket client_sock = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); client_sock.Connect(ep); if (!client_sock.Connected) { Console.WriteLine("could not connect"); Environment.Exit(1); } if (!quiet) { Console.WriteLine("CONNECTED"); } /********************************************************************** * This is where the interesting stuff happens. Up until now we've * just been setting up sockets etc. Now we do the SSL handshake. **********************************************************************/ SSLClient ssl_ctx = new SSLClient(options, axtls.SSL_DEFAULT_CLNT_SESS); if (ssl_ctx == null) { Console.Error.WriteLine("Error: Client context is invalid"); Environment.Exit(1); } if (private_key_file != null) { int obj_type = axtls.SSL_OBJ_RSA_KEY; if (private_key_file.EndsWith(".p8")) obj_type = axtls.SSL_OBJ_PKCS8; else if (private_key_file.EndsWith(".p12")) obj_type = axtls.SSL_OBJ_PKCS12; if (ssl_ctx.ObjLoad(obj_type, private_key_file, password) != axtls.SSL_OK) { Console.Error.WriteLine("Private key '" + private_key_file + "' is undefined."); Environment.Exit(1); } } for (i = 0; i < cert_index; i++) { if (ssl_ctx.ObjLoad(axtls.SSL_OBJ_X509_CERT, cert[i], null) != axtls.SSL_OK) { Console.WriteLine("Certificate '" + cert[i] + "' is undefined."); Environment.Exit(1); } } for (i = 0; i < ca_cert_index; i++) { if (ssl_ctx.ObjLoad(axtls.SSL_OBJ_X509_CACERT, ca_cert[i], null) != axtls.SSL_OK) { Console.WriteLine("Certificate '" + cert[i] + "' is undefined."); Environment.Exit(1); } } SSL ssl = new SSL(new IntPtr(0)); /* keep compiler happy */ /* Try session resumption? */ if (reconnect > 0) { while (reconnect-- > 0) { ssl = ssl_ctx.Connect(client_sock, session_id); if ((res = ssl.HandshakeStatus()) != axtls.SSL_OK) { if (!quiet) { SSLUtil.DisplayError(res); } ssl.Dispose(); Environment.Exit(1); } display_session_id(ssl); session_id = ssl.GetSessionId(); if (reconnect > 0) { ssl.Dispose(); client_sock.Close(); /* and reconnect */ client_sock = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); client_sock.Connect(ep); } } } else { ssl = ssl_ctx.Connect(client_sock, null); } /* check the return status */ if ((res = ssl.HandshakeStatus()) != axtls.SSL_OK) { if (!quiet) { SSLUtil.DisplayError(res); } Environment.Exit(1); } if (!quiet) { string common_name = ssl.GetCertificateDN(axtls.SSL_X509_CERT_COMMON_NAME); if (common_name != null) { Console.WriteLine("Common Name:\t\t\t" + common_name); } display_session_id(ssl); display_cipher(ssl); } for (;;) { string user_input = Console.ReadLine(); if (user_input == null) break; byte[] buf = new byte[user_input.Length+2]; buf[buf.Length-2] = (byte)'\n'; /* add the carriage return */ buf[buf.Length-1] = 0; /* null terminate */ for (i = 0; i < buf.Length-2; i++) { buf[i] = (byte)user_input[i]; } if ((res = ssl_ctx.Write(ssl, buf, buf.Length)) < axtls.SSL_OK) { if (!quiet) { SSLUtil.DisplayError(res); } break; } } ssl_ctx.Dispose(); }