• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright 2014-2022 The GmSSL Project. All Rights Reserved.
3  *
4  *  Licensed under the Apache License, Version 2.0 (the License); you may
5  *  not use this file except in compliance with the License.
6  *
7  *  http://www.apache.org/licenses/LICENSE-2.0
8  */
9 
10 #include <stdio.h>
11 #include <errno.h>
12 #include <string.h>
13 #include <stdlib.h>
14 #include <unistd.h>
15 #include <netdb.h>
16 #include <sys/types.h>
17 #include <arpa/inet.h>
18 #include <sys/socket.h>
19 #include <netinet/in.h>
20 #include <gmssl/tls.h>
21 #include <gmssl/error.h>
22 #include "url_parser.h"
23 
24 
main(int argc,char * argv[])25 int main(int argc, char *argv[])
26 {
27 	int ret = -1;
28 	char *prog = argv[0];
29 	const int cipher = TLS_cipher_ecc_sm4_cbc_sm3;
30 	URL_COMPONENTS *url;
31 	struct hostent *hp;
32 	int port = 443;
33 	struct sockaddr_in server;
34 	int sock;
35 	TLS_CTX ctx;
36 	TLS_CONNECT conn;
37 	char request[1024];
38 	uint8_t buf[16800];
39 	char *p;
40 	size_t len;
41 
42 	if (argc != 2) {
43 		fprintf(stderr, "example: echo \"key=word\" | tlcp_post https://sm2only.ovssl.cn\n");
44 		return 1;
45 	}
46 
47 	if (!(url = parse_url(argv[1]))) {
48 		fprintf(stderr, "parse url '%s' failure\n", argv[1]);
49 		return 1;
50 	}
51 	if (!(hp = gethostbyname(url->host))) {
52 		herror("tlcp_client: '-host' invalid");
53 		goto end;
54 	}
55 	if (url->port != -1) {
56 		port = url->port;
57 	}
58 
59 	server.sin_addr = *((struct in_addr *)hp->h_addr_list[0]);
60 	server.sin_family = AF_INET;
61 	server.sin_port = htons(port);
62 
63 	if ((sock = socket(AF_INET, SOCK_STREAM, 0)) < 0) {
64 		perror("socket");
65 		goto end;
66 	}
67 	if (connect(sock, (struct sockaddr *)&server , sizeof(server)) < 0) {
68 		perror("connect");
69 		goto end;
70 	}
71 
72 	memset(&ctx, 0, sizeof(ctx));
73 	memset(&conn, 0, sizeof(conn));
74 
75 	tls_ctx_init(&ctx, TLS_protocol_tlcp, TLS_client_mode);
76 	tls_ctx_set_cipher_suites(&ctx, &cipher, 1);
77 	tls_init(&conn, &ctx);
78 	tls_set_socket(&conn, sock);
79 
80 	if (tls_do_handshake(&conn) != 1) {
81 		fprintf(stderr, "%s: error\n", prog);
82 		goto end;
83 	}
84 
85 	snprintf(request, sizeof(request)-1, "POST %s HTTP/1.1\r\nHost: %s\r\n\r\n",
86 		url->path ? url->path : "/",
87 		url->host);
88 
89 	tls_send(&conn, (uint8_t *)request, strlen(request), &len);
90 
91 	len = fread(buf, 1, sizeof(buf), stdin);
92 	if (len) {
93 		tls_send(&conn, buf, len, &len);
94 	}
95 
96 	if (tls_recv(&conn, buf, sizeof(buf), &len) != 1) {
97 		fprintf(stderr, "recv failure\n");
98 		goto end;
99 	}
100 	buf[len] = 0;
101 
102 	p = strstr((char *)buf, "\r\n\r\n");
103 	if (p) {
104 		printf("%s", p + 4);
105 		fflush(stdout);
106 	}
107 
108 end:
109 	free_url_components(url);
110 	close(sock);
111 	tls_ctx_cleanup(&ctx);
112 	tls_cleanup(&conn);
113 	return 0;
114 }
115