Skip webcheck idle period check if we just went online. Improve webcheck logging
[bpdyndnsd] / src / ip_addr_helper.cpp
CommitLineData
0665b239
BS
1/** @file
2 * @brief IPHelper class implementation. This class represents a Helper to get the actual IP.
3 *
4 *
5 *
6 * @copyright Intra2net AG
7 * @license GPLv2
8*/
9
4de6a9b8 10#include "ip_addr_helper.hpp"
0665b239 11#include <boost/asio.hpp>
1c0908b5 12#include <boost/regex.hpp>
1d2e2f56
BS
13#include <arpa/inet.h>
14#include <sys/socket.h>
15#include <netdb.h>
16#include <ifaddrs.h>
17
0665b239
BS
18
19using namespace std;
20
21namespace net = boost::asio;
22
23/**
24 * Default constructor.
25 */
ad0e5016 26IPAddrHelper::IPAddrHelper()
b30f392d 27 : Log(new Logger)
2b0f7c11 28 , WebcheckInterval(0)
20399847 29 , LastWebcheck(0)
b30f392d 30 , ProxyPort(0)
0665b239
BS
31 , UseIPv6(false)
32{
33}
34
35
36/**
37 * Constructor.
38 */
08a5a621 39IPAddrHelper::IPAddrHelper(const Logger::Ptr _log, const string& _webcheck_url, const string& _webcheck_url_alt, const int _webcheck_interval, const time_t _last_webcheck ,const bool _use_ipv6, const string& _proxy, const int _proxy_port)
9a0aff44
BS
40 : Log(_log)
41 , WebcheckIpUrl(_webcheck_url)
b30f392d 42 , WebcheckIpUrlAlt(_webcheck_url_alt)
2b0f7c11 43 , WebcheckInterval(_webcheck_interval)
20399847 44 , LastWebcheck(_last_webcheck)
9a0aff44
BS
45 , Proxy(_proxy)
46 , ProxyPort(_proxy_port)
47 , UseIPv6(_use_ipv6)
0665b239 48{
019dc0d9 49 Hostname = net::ip::host_name();
019dc0d9 50 Log->print_hostname(Hostname);
0665b239
BS
51}
52
53
54/**
55 * Default destructor
56 */
ad0e5016 57IPAddrHelper::~IPAddrHelper()
0665b239
BS
58{
59}
60
61
62/**
1d2e2f56 63 * Tests if a given IP is a local IPv6 address
4ef36a12
BS
64 * @param ip The IP to test
65 * @return true if given IP is local, false if not.
66 */
1d2e2f56
BS
67bool IPAddrHelper::is_local_ipv6(const string ip) const
68{
69 // IPv6 any
70 boost::regex expr_any_ipv6("^::$");
71
72 // IPV6 loopback
73 boost::regex expr_loopback_ipv6("^::1$");
74
75 // IPV6 local unicast address
76 boost::regex expr_local_unicast_ipv6("^fc00:");
77
78 // IPV6 link local
79 boost::regex expr_link_local_ipv6("^fe[8,9,a,b]{1}");
80
81 // IPV6 site local
82 boost::regex expr_site_local_ipv6("^fe[c,d,e,f]{1}");
83
84 // It's time to test against the regex patterns
85 if ( boost::regex_search(ip,expr_any_ipv6) )
86 {
87 Log->print_regex_match(expr_any_ipv6.str(),ip);
88 return true;
89 }
90 else if ( boost::regex_search(ip,expr_loopback_ipv6) )
91 {
92 Log->print_regex_match(expr_loopback_ipv6.str(),ip);
93 return true;
94 }
95 else if ( boost::regex_search(ip,expr_local_unicast_ipv6) )
96 {
97 Log->print_regex_match(expr_local_unicast_ipv6.str(),ip);
98 return true;
99 }
100 else if ( boost::regex_search(ip,expr_link_local_ipv6) )
101 {
102 Log->print_regex_match(expr_link_local_ipv6.str(),ip);
103 return true;
104 }
105 else if ( boost::regex_search(ip,expr_site_local_ipv6) )
106 {
107 Log->print_regex_match(expr_site_local_ipv6.str(),ip);
108 return true;
109 }
110
111 return false;
112}
113
114
115/**
116 * Tests if a given IP is a local IPv4 address
117 * @param ip The IP to test
118 * @return true if given IP is local, false if not.
119 */
120bool IPAddrHelper::is_local_ipv4(const string ip) const
4ef36a12
BS
121{
122 // 127.0.0.1
123 boost::regex expr_loopback("127\\.[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}");
124
125 // 192.168.x.x
126 boost::regex expr_192("192\\.168\\.[0-9]{1,3}\\.[0-9]{1,3}");
127
128 // 10.x.x.x
129 boost::regex expr_10("10\\.[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}");
130
131 // 169.254.x.x
132 boost::regex expr_169_254("169\\.254\\.[0-9]{1,3}\\.[0-9]{1,3}");
133
134 // 172.16.x.x -> 172.31.x.x
135 boost::regex expr_172_1("172\\.1[6-9]{1}\\.[0-9]{1,3}\\.[0-9]{1,3}");
136 boost::regex expr_172_2("172\\.2[0-9]{1}\\.[0-9]{1,3}\\.[0-9]{1,3}");
137 boost::regex expr_172_3("172\\.3[0-1]{1}\\.[0-9]{1,3}\\.[0-9]{1,3}");
138
139 // It's time to test against the regex patterns
140 if ( boost::regex_search(ip,expr_loopback) )
141 {
142 Log->print_regex_match(expr_loopback.str(),ip);
143 return true;
144 }
145 else if ( boost::regex_search(ip,expr_192) )
146 {
147 Log->print_regex_match(expr_192.str(),ip);
148 return true;
149 }
150 else if ( boost::regex_search(ip,expr_10) )
151 {
152 Log->print_regex_match(expr_10.str(),ip);
153 return true;
154 }
155 else if ( boost::regex_search(ip,expr_169_254) )
156 {
157 Log->print_regex_match(expr_169_254.str(),ip);
158 return true;
159 }
160 else if ( boost::regex_search(ip,expr_172_1) )
161 {
162 Log->print_regex_match(expr_172_1.str(),ip);
163 return true;
164 }
165 else if ( boost::regex_search(ip,expr_172_2) )
166 {
167 Log->print_regex_match(expr_172_2.str(),ip);
168 return true;
169 }
170 else if ( boost::regex_search(ip,expr_172_3) )
171 {
172 Log->print_regex_match(expr_172_3.str(),ip);
173 return true;
174 }
175
176 return false;
177}
178
179
180/**
0665b239 181 * Get the actual IP of this host through a conventional DNS query or through a IP webcheck URL if configured so.
3c4705d9 182 * @param changed_to_online Indicates if we just went online
0665b239
BS
183 * @return A string representation of the actual IP in dotted format or an empty string if something went wrong.
184 */
3c4705d9 185string IPAddrHelper::get_actual_ip( bool use_webcheck, bool changed_to_online )
0665b239 186{
3c0cd271 187 string ip;
1d2e2f56 188
46fffdd6 189 if ( !WebcheckIpUrl.empty() && use_webcheck )
3c4705d9 190 ip = webcheck_ip(changed_to_online);
46fffdd6
BS
191 else
192 ip = get_local_wan_nic_ip();
3c0cd271 193
1d2e2f56
BS
194 return ip;
195}
196
197
198/**
199 * Get the IP address of the local wan interface if there is one.
200 * @return The IP address of the wan interface or an empty string if something went wrong.
201 */
ce70569b 202string IPAddrHelper::get_local_wan_nic_ip() const
1d2e2f56
BS
203{
204 struct ifaddrs *if_addr_struct, *ifa;
ce70569b
BS
205 unsigned short address_family;
206 int ret_val;
1d2e2f56
BS
207 char ip_addr_buff[NI_MAXHOST];
208 list<string> external_ipv4_addresses;
209 list<string> external_ipv6_addresses;
210
211 // Get linked list of all interface addresses.
212 if ( getifaddrs(&if_addr_struct) == -1 )
4ef36a12 213 {
1d2e2f56
BS
214 Log->print_error_getting_local_wan_ip("getifaddrs", strerror(errno));
215 freeifaddrs(if_addr_struct);
4ef36a12
BS
216 return "";
217 }
3c0cd271 218
1d2e2f56
BS
219 // Iterate through the linked list.
220 for ( ifa = if_addr_struct; ifa != NULL; ifa = ifa->ifa_next)
221 {
3e0bfbf5
TJ
222 // Skip interfaces without IP addresses
223 if (!ifa->ifa_addr)
224 continue;
225
1d2e2f56
BS
226 // Get the address family of the actual address.
227 address_family = ifa->ifa_addr->sa_family;
228
229 // If it is an IPv4 then process further.
230 if ( address_family == AF_INET )
231 {
232 // Translate the address to a protocol independent representation (dottet format). Copy address into ip_addr_buff.
08a5a621 233 ret_val = getnameinfo(ifa->ifa_addr, (socklen_t)sizeof(struct sockaddr_in), ip_addr_buff, NI_MAXHOST, NULL, 0, NI_NUMERICHOST);
1d2e2f56
BS
234 if ( ret_val != 0 )
235 {
236 Log->print_error_getting_local_wan_ip("getnameinfo", gai_strerror(ret_val));
237 freeifaddrs(if_addr_struct);
238 return "";
239 }
240
241 // Generate IPv4 string out of char array.
242 string ipv4_addr(ip_addr_buff);
243
244 Log->print_own_ipv4(ipv4_addr, Hostname);
245
246 // Test if it is a local address.
247 if ( !is_local_ipv4(ipv4_addr) )
248 external_ipv4_addresses.push_back(ipv4_addr);
249 else
250 Log->print_ip_is_local(ipv4_addr);
251 }
252 // If it is an IPv6 address and IPv6 is enabled then process further.
ce70569b 253 else if ( (address_family == AF_INET6) && (UseIPv6) )
1d2e2f56
BS
254 {
255 // Translate the address to a protocol independent representation (dottet format). Copy address into ip_addr_buff.
08a5a621 256 ret_val = getnameinfo(ifa->ifa_addr, (socklen_t)sizeof(struct sockaddr_in6), ip_addr_buff, NI_MAXHOST, NULL, 0, NI_NUMERICHOST);
1d2e2f56
BS
257 if ( ret_val != 0 )
258 {
259 Log->print_error_getting_local_wan_ip("getnameinfo", gai_strerror(ret_val));
260 freeifaddrs(if_addr_struct);
261 return "";
262 }
263
264 // Generate IPv6 string out of char array.
265 string ipv6_addr(ip_addr_buff);
266
267 Log->print_own_ipv6(ipv6_addr, Hostname);
268
269 // Test if it is a local address.
270 if ( !is_local_ipv6(ipv6_addr) )
271 external_ipv6_addresses.push_back(ipv6_addr);
272 else
273 Log->print_ip_is_local(ipv6_addr);
274 }
275 }
276 freeifaddrs(if_addr_struct);
277
278 // Return the first element in IPv6 list if IPv6 is enabled, otherwise return first element in IPv4 list.
ce70569b 279 if ( (UseIPv6) && (!external_ipv6_addresses.empty()) )
1d2e2f56
BS
280 return external_ipv6_addresses.front();
281 else if ( !external_ipv4_addresses.empty() )
282 return external_ipv4_addresses.front();
283
284 return "";
0665b239
BS
285}
286
0665b239
BS
287
288/**
687d99fb 289 * Get the actual IP of the given host through a DNS query.
c3dea5dc 290 * @param _hostname The hostname for the dns lookup, if empty string, then perform a dns lookup to the local hostname.
0665b239
BS
291 * @return A string representation of the actual IP in dotted format or an empty string if something went wrong.
292 */
ad0e5016 293string IPAddrHelper::dns_query(const string& _hostname) const
0665b239 294{
1d2e2f56
BS
295 list<string> external_ipv4_addresses;
296 list<string> external_ipv6_addresses;
0665b239 297
1d2e2f56 298 // Init the hostname with the given _hostname or with local Hostname if empty.
c3dea5dc
BS
299 string hostname = Hostname;
300 if ( !_hostname.empty() )
301 hostname = _hostname;
302
0665b239
BS
303 try
304 {
305 // BOOST asio isn't the simplest way to perform a DNS lookup, but it works just fine.
306 net::io_service io_service;
307 net::ip::tcp::resolver resolver(io_service);
1d2e2f56
BS
308
309 // Define the DNS query.
310 net::ip::tcp::resolver::query query(hostname, "0", net::ip::resolver_query_base::address_configured | net::ip::resolver_query_base::all_matching);
311
312 // Perform the DNS query.
0665b239
BS
313 net::ip::tcp::resolver::iterator endpoint_iterator = resolver.resolve(query);
314 net::ip::tcp::resolver::iterator end;
1d2e2f56
BS
315
316 // Iterate through the returned IP addresses.
0665b239
BS
317 while(endpoint_iterator != end)
318 {
1d2e2f56 319 // Get the IP address out of the endpoint iterator.
687d99fb
BS
320 net::ip::address ip;
321 ip = endpoint_iterator->endpoint().address();
1d2e2f56
BS
322
323 // Test if it is a IPv4 address.
0665b239 324 if ( ip.is_v4() )
1d2e2f56
BS
325 {
326 // Get the string representation.
327 string ipv4_addr = ip.to_string();
328
329 Log->print_own_ipv4(ipv4_addr, hostname);
330
331 // If it is not a local address then push it in the external ipv4 address list.
2f83caa3 332 //if ( !is_local_ipv4(ipv4_addr) )
1d2e2f56 333 external_ipv4_addresses.push_back(ipv4_addr);
2f83caa3
BS
334 //else
335 // Log->print_ip_is_local(ipv4_addr);
1d2e2f56
BS
336 }
337 // Test if it is a IPv6 address and if IPv6 is enabled.
ce70569b 338 else if ( (ip.is_v6()) && (UseIPv6) )
1d2e2f56
BS
339 {
340 // Get the string representation.
341 string ipv6_addr = ip.to_string();
342
343 Log->print_own_ipv6(ipv6_addr, hostname);
344
345 // If it is not a local address then push it in the external ipv6 address list.
2f83caa3 346 //if ( !is_local_ipv6(ipv6_addr) )
1d2e2f56 347 external_ipv6_addresses.push_back(ipv6_addr);
2f83caa3
BS
348 //else
349 // Log->print_ip_is_local(ipv6_addr);
1d2e2f56 350 }
0665b239
BS
351 endpoint_iterator++;
352 }
353 io_service.reset();
354 }
ce70569b 355 catch(const exception& e)
0665b239 356 {
c3dea5dc 357 Log->print_error_hostname_to_ip(e.what(),hostname);
0665b239
BS
358 return "";
359 }
360
1d2e2f56 361 // Return the first element in IPv6 list if IPv6 is enabled, otherwise return first element in IPv4 list.
ce70569b 362 if ( (UseIPv6) && (!external_ipv6_addresses.empty()) )
1d2e2f56
BS
363 return external_ipv6_addresses.front();
364 else if ( !external_ipv4_addresses.empty() )
365 return external_ipv4_addresses.front();
0665b239 366
1d2e2f56
BS
367 // Could not get a external IP address, so return empty string.
368 return "";
0665b239
BS
369}
370
371
372/**
373 * Get the actual IP of this host through a IP webcheck URL.
3c4705d9 374 * @param changed_to_online Indicates if we just went online
0665b239
BS
375 * @return A string representation of the actual IP in dotted format or an empty string if something went wrong.
376 */
3c4705d9 377string IPAddrHelper::webcheck_ip(bool changed_to_online)
0665b239 378{
2b0f7c11 379 // Init IPAddress with a empty string.
1c0908b5
BS
380 string ip_addr = "";
381
2b0f7c11 382 // Get the current time.
ce70569b 383 time_t current_time = time(NULL);
2b0f7c11
BS
384
385 // Test if webcheck is allowed due to webcheck_interval.
3c4705d9
TJ
386 // Ignored if we just went online.
387 if ( !changed_to_online && (LastWebcheck + ((time_t)WebcheckInterval*60)) >= current_time )
2b0f7c11
BS
388 {
389 // Webcheck not allowed, log it and return empty string.
390 Log->print_webcheck_exceed_interval( LastWebcheck, (WebcheckInterval*60), current_time );
1d2e2f56 391 return "";
2b0f7c11
BS
392 }
393
1c0908b5
BS
394 // Init CURL buffers
395 string curl_writedata_buff;
396 char curl_err_buff[CURL_ERROR_SIZE];
397 int curl_err_code=1;
398
399 // Init URL List
400 list<string> url_list;
401 url_list.push_back(WebcheckIpUrl);
402 url_list.push_back(WebcheckIpUrlAlt);
403 string actual_url;
404
405 // Init CURL
406 CURL * curl_easy_handle = init_curl(curl_writedata_buff,curl_err_buff);
ce70569b
BS
407 if ( curl_easy_handle == NULL )
408 {
409 return "";
410 }
1c0908b5
BS
411
412 // If perform_curl_operation returns a connection problem indicating return code, try the next ip webcheck url if there is one.
413 while ( (curl_err_code == 1) && (url_list.size() != 0) && (url_list.front() != "") )
414 {
415 // Set URL
416 actual_url = url_list.front();
417 url_list.pop_front();
c730deea
BS
418 if (set_curl_url(curl_easy_handle,actual_url) == CURLE_OK )
419 {
420 // Perform curl operation, err_code of 1 indicated connection problem, so try next url.
421 curl_err_code = perform_curl_operation(curl_easy_handle, curl_err_buff, actual_url);
422 }
1c0908b5
BS
423 }
424
425 // Cleanup CURL handle
426 curl_easy_cleanup(curl_easy_handle);
427
428 // If curl_err_code is not 0, the ip couldn't be determined through any configured webcheck url.
429 if ( curl_err_code != 0 )
430 {
2b0f7c11 431 // Log it and return the empty string.
1c0908b5 432 Log->print_webcheck_no_ip();
1d2e2f56 433 return "";
1c0908b5
BS
434 }
435
2b0f7c11 436 // Log the received curl data.
1c0908b5
BS
437 Log->print_received_curl_data(curl_writedata_buff);
438
1d2e2f56
BS
439 // Try to parse a IPv4 address out of the received data.
440 ip_addr = parse_ipv4(curl_writedata_buff);
441
5ad93dad
BS
442 // TODO: Parsing of IPv6 address out of received curl data via webcheck IP.
443
1d2e2f56
BS
444 if ( !ip_addr.empty() )
445 {
446 // Got a IPv4 address out of the received data.
447 Log->print_own_ipv4(ip_addr, Hostname);
448 }
449 else
450 {
451 return "";
452 }
0665b239 453
2b0f7c11
BS
454 // Set the LastWebcheck time to current time.
455 LastWebcheck = current_time;
456
1d2e2f56
BS
457 // If IP is within a private range then return ""
458 if ( is_local_ipv4(ip_addr) )
459 {
460 Log->print_ip_is_local(ip_addr);
461 return "";
462 }
463
2b0f7c11 464 // Return the parsed IPAddress.
0665b239
BS
465 return ip_addr;
466}
1c0908b5
BS
467
468
469/**
1d2e2f56 470 * Tries to find a IPv4 Address in dottet format in a given string and returns the IP-Address found.
1c0908b5
BS
471 * @param data The string data to search in for a valid IPv4-Address.
472 * @return The IP Address found or an empty string.
473 */
1d2e2f56 474string IPAddrHelper::parse_ipv4(const string& data) const
1c0908b5
BS
475{
476 string ip = "";
477
1d2e2f56 478 // Regex for ipv4 address in dottet format
1c0908b5
BS
479 boost::regex expr("([0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3})");
480
481 boost::smatch matches;
482
483 if ( boost::regex_search(data,matches,expr) )
484 {
485 ip = matches[1];
1d2e2f56 486 Log->print_regex_match(expr.str(),ip);
1c0908b5
BS
487 }
488 else
489 {
490 Log->print_regex_ip_not_found(data);
491 }
492
493 return ip;
494}
495
496
497/**
498 * Performs the curl operation.
499 * @param curl_easy_handle The initialized and configured curl handle.
500 * @param curl_err_buff The pointer to the curl error buffer to get error messages from.
501 * @param actual_url The actual configured URL.
502 * @return 0 if all is fine, 1 if an connection problem to the configured url occurs, -1 on other errors.
503 */
ce70569b 504int IPAddrHelper::perform_curl_operation(CURL * curl_easy_handle, const char* curl_err_buff, const string& actual_url) const
1c0908b5 505{
ce70569b
BS
506 CURLcode curl_err_code;
507 if ( (curl_err_code = curl_easy_perform(curl_easy_handle) ) != CURLE_OK )
1c0908b5
BS
508 {
509 // CURL error occured
510 if ( (curl_err_code == CURLE_COULDNT_CONNECT) || (curl_err_code == CURLE_OPERATION_TIMEOUTED) || (curl_err_code == CURLE_COULDNT_RESOLVE_HOST) )
511 {
512 // In case of connection problems we should return 1, that the fallback url will be used.
513 Log->print_webcheck_url_connection_problem(curl_err_buff, actual_url);
514 return 1;
515 }
516 else
517 {
518 // other error
519 Log->print_webcheck_error(curl_err_buff, actual_url);
520 return -1;
521 }
522 }
523 // Operation performed without any problems
524 return 0;
525}
526
527
528/**
529 * Sets a url to the easy curl handle
530 * @param curl_easy_handle The easy curl handle to set the url for.
531 * @param url The url to set.
c730deea 532 * @return CURLcode Curl Error code, CURLE_OK if everything is right.
1c0908b5 533 */
c730deea 534CURLcode IPAddrHelper::set_curl_url(CURL * curl_easy_handle, const string& url) const
1c0908b5 535{
c730deea
BS
536 CURLcode curl_error = CURLE_OK;
537
538 if ( curl_easy_handle != NULL )
539 {
540 curl_error = curl_easy_setopt(curl_easy_handle,CURLOPT_URL,url.c_str());
541 if ( curl_error != CURLE_OK )
542 {
543 // Some options could not be set, so destroy the CURL handle.
544 Log->print_curl_error_init("Could not set CURL URL properly.",curl_error);
545 }
546 }
547 return curl_error;
1c0908b5
BS
548}
549
550
551/**
552 * Initialized curl easy handle with a few options.
553 * @param curl_writedata_buff Reference to a string wich will be filled with the curl result
554 * @param curl_err_buff A pointer to an char array which will be filled with error message.
555 * @return A pointer to the easy curl handle.
556 */
ad0e5016 557CURL * IPAddrHelper::init_curl(string& curl_writedata_buff,char* curl_err_buff) const
1c0908b5 558{
f1dda324 559 string user_agent = "Intra2net AG - Bullet Proof DYNDNS Daemon - 0.1.1";
ce70569b 560
1c0908b5 561 CURL *curl_easy_handle = curl_easy_init();
ce70569b
BS
562 if ( curl_easy_handle == NULL )
563 {
564 // something went wrong.
565 Log->print_curl_error_init("Could not initialize CURL object.",CURLE_FAILED_INIT);
566 return NULL;
567 }
1c0908b5 568
08a5a621 569 CURLcode curlError = curl_easy_setopt(curl_easy_handle,CURLOPT_NOPROGRESS,1);
ce70569b
BS
570 if ( curlError == CURLE_OK)
571 curlError = curl_easy_setopt(curl_easy_handle,CURLOPT_CONNECTTIMEOUT,5);
572 if ( curlError == CURLE_OK)
573 curlError = curl_easy_setopt(curl_easy_handle,CURLOPT_TIMEOUT,10);
574 if ( curlError == CURLE_OK)
575 curlError = curl_easy_setopt(curl_easy_handle,CURLOPT_BUFFERSIZE,1024);
576 if ( curlError == CURLE_OK)
577 curlError = curl_easy_setopt(curl_easy_handle,CURLOPT_ERRORBUFFER,curl_err_buff);
578 if ( curlError == CURLE_OK)
579 curlError = curl_easy_setopt(curl_easy_handle,CURLOPT_WRITEFUNCTION,http_receive);
580 if ( curlError == CURLE_OK)
581 curlError = curl_easy_setopt(curl_easy_handle,CURLOPT_WRITEDATA,&curl_writedata_buff);
582 if ( curlError == CURLE_OK)
583 curlError = curl_easy_setopt(curl_easy_handle,CURLOPT_USERAGENT,&user_agent);
1c0908b5 584
4eb87664
BS
585 if ( !Proxy.empty() )
586 {
ce70569b
BS
587 if ( curlError == CURLE_OK)
588 curlError = curl_easy_setopt(curl_easy_handle,CURLOPT_PROXY,Proxy.c_str());
589 if ( curlError == CURLE_OK)
590 curlError = curl_easy_setopt(curl_easy_handle,CURLOPT_PROXYPORT,ProxyPort);
591 }
592
593 if ( curlError != CURLE_OK )
594 {
595 // Some options could not be set, so destroy the CURL handle.
596 Log->print_curl_error_init("Could not set CURL options properly.",curlError);
597 curl_easy_cleanup(curl_easy_handle);
598 curl_easy_handle = NULL;
4eb87664
BS
599 }
600
1c0908b5
BS
601 return curl_easy_handle;
602}
603
604
605/**
606 * Callback Function is called every time CURL is receiving data from HTTPS-Server and will copy all received Data to the given stream pointer
607 * @param inBuffer Pointer to input.
608 * @param size How many mem blocks are received
609 * @param nmemb size of each memblock
610 * @param outBuffer Pointer to output stream.
611 * @return The size received.
612 */
ce70569b 613size_t IPAddrHelper::http_receive( const char *inBuffer, size_t size, size_t nmemb, string *outBuffer )
1c0908b5
BS
614{
615 outBuffer->append(inBuffer);
616 return (size*nmemb);
617}
20399847
BS
618
619
620/**
621 * Get member LastWebcheck
622 * @return LastWebcheck
623 */
08a5a621 624time_t IPAddrHelper::get_last_webcheck() const
20399847
BS
625{
626 return LastWebcheck;
627}