1 // ----------------------------------------------------------------------------
2 // Copyright (C) 2014...2019
3 //              David Freese, W1HKJ
4 //
5 // This file is part of fldigi
6 //
7 // fldigi is free software; you can redistribute it and/or modify
8 // it under the terms of the GNU General Public License as published by
9 // the Free Software Foundation; either version 3 of the License, or
10 // (at your option) any later version.
11 //
12 // fldigi is distributed in the hope that it will be useful,
13 // but WITHOUT ANY WARRANTY; without even the implied warranty of
14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 // GNU General Public License for more details.
16 //
17 // You should have received a copy of the GNU General Public License
18 // along with this program.  If not, see <http://www.gnu.org/licenses/>.
19 // ----------------------------------------------------------------------------
20 
21 #ifndef NETWORK_H_
22 #define NETWORK_H_
23 
24 #include <stdio.h>
25 #include <stdlib.h>
26 #include <string.h>
27 
28 #include <iostream>
29 #include <sstream>
30 #include <fstream>
31 #include <string>
32 #include <cmath>
33 
34 #include "mbedtls/config.h"
35 #include "mbedtls/net.h"
36 #include "mbedtls/net_sockets.h"
37 #include "mbedtls/debug.h"
38 #include "mbedtls/ssl.h"
39 #include "mbedtls/entropy.h"
40 #include "mbedtls/ctr_drbg.h"
41 #include "mbedtls/error.h"
42 #include "mbedtls/certs.h"
43 
44 extern bool get_http(const std::string& url, std::string& reply, double timeout = 0.0);
45 
46 extern char ca_crt_rsa[];
47 extern size_t ca_crt_rsa_size;
48 
49 //----------------------------------------------------------------------
50 //#define DEBUG_LEVEL 1
51 
52 #define MBEDTLS_EXIT_SUCCESS    0
53 #define MBEDTLS_EXIT_FAILURE    1
54 #define MBEDTLS_DEBUG_C
55 #define MBEDTLS_CHECK_PARAMS
56 
57 #define H_FIELD_SIZE     512
58 #define H_READ_SIZE     2048
59 
60 typedef struct
61 {
62     char method[8];
63     int  status;
64     char content_type[H_FIELD_SIZE];
65     long content_length;
66     bool chunked;
67     bool close;
68     char location[H_FIELD_SIZE];
69     char referrer[H_FIELD_SIZE];
70     char cookie[H_FIELD_SIZE];
71     char boundary[H_FIELD_SIZE];
72 
73 } HTTP_HEADER;
74 
75 typedef struct
76 {
77     bool    verify;
78 
79     mbedtls_net_context         ssl_fd;
80     mbedtls_entropy_context     entropy;
81     mbedtls_ctr_drbg_context    ctr_drbg;
82     mbedtls_ssl_context         ssl;
83     mbedtls_ssl_config          conf;
84     mbedtls_x509_crt            cacert;
85 
86 } HTTP_SSL;
87 
88 typedef struct {
89 
90     bool    https;
91     char    host[256];
92     char    port[8];
93     char    path[H_FIELD_SIZE];
94 
95 } HTTP_URL;
96 
97 typedef struct
98 {
99     HTTP_URL    url;
100 
101     HTTP_HEADER request;
102     HTTP_HEADER response;
103     HTTP_SSL    tls;
104 
105     long        length;
106     char        r_buf[H_READ_SIZE];
107     long        r_len;
108     bool        header_end;
109     char        *body;
110     long        body_size;
111     long        body_len;
112 
113 
114 } HTTP_INFO;
115 
116 //----------------------------------------------------------------------
117 
118 class Url {
119 	std::string _url;
120 	std::string _host;
121 	std::string _port;
122 	std::string _request;
123 	std::string _data;
124 	std::string _pers;
125 
126 	std::string server_port;
127 
128 	bool _https;
129 
130 	int  _err;
131 	char err_string[1024];
132 	char buf[4096];
133 
134 	mbedtls_net_context server_fd;
135 	uint32_t flags;
136 
137 	mbedtls_entropy_context entropy;
138 	mbedtls_ctr_drbg_context ctr_drbg;
139 	mbedtls_ssl_context ssl;
140 	mbedtls_ssl_config conf;
141 	mbedtls_x509_crt cacert;
142 
143 	bool _debug;
144 	static int _rotate_log;
145 
146 	double _timeout;
147 
148 	std::ofstream debug_file;
149 
150 	int http_get(std::string &response);
151 	int https_get(std::string &response);
152 
153 public:
Url()154 	Url() {
155 		init();
156 	};
Url(std::string url)157 	Url(std::string url) {
158 		init();
159 		_url = url;
160 		parse(url);
161 	}
~Url()162 	~Url() {
163 		if (debug_file) {
164 			debug_file.close();
165 		}
166 	};
167 
init()168 	void init() {
169 		_https = false;
170 		server_port.clear();
171 		_url.clear();
172 		_host.clear();
173 		_port.clear();
174 		_request.clear();
175 		_data.clear();
176 		_pers = "fldigi";
177 		_timeout = 5.0;
178 		debug();
179 	}
180 
181 	void parse(std::string url);
182 
host()183 	std::string host() { return _host; }
port()184 	std::string port() { return _port; }
request()185 	std::string request() { return _request; }
data()186 	std::string data() { return _data; }
url()187 	std::string url() { return _url; }
strerr()188 	std::string strerr() { return err_string; };
error()189 	int error() { return _err; }
190 
https()191 	bool https() { return _https; }
str_https()192 	std::string str_https() {
193 		if (_https) return "true";
194 		return "false";
195 	}
196 
197 	int get(std::string response);
198 	int get(std::string url, std::string &response);
199 
timeout(double t)200 	void timeout(double t) { _timeout = t; }
timeout()201 	double timeout() { return _timeout; }
202 
203 	void debug();
204 };
205 
206 
207 #endif // NETWORK_H_
208