From 03f86b5d0809967855fbaafb4d600dc5b82081fa Mon Sep 17 00:00:00 2001
From: Andreas Baumann <mail@andreasbaumann.cc>
Date: Tue, 7 Mar 2023 19:51:33 +0100
Subject: check_curl: in SSL host caching mode try to connect and bind and take
 the first getaddrinfo result which succeeds

---
 plugins/check_curl.c | 22 +++++++++++++++-------
 1 file changed, 15 insertions(+), 7 deletions(-)

diff --git a/plugins/check_curl.c b/plugins/check_curl.c
index c37d45d9..e1bc98dc 100644
--- a/plugins/check_curl.c
+++ b/plugins/check_curl.c
@@ -386,6 +386,7 @@ lookup_host (const char *host, char *buf, size_t buflen)
   struct addrinfo hints, *res, *result;
   int errcode;
   void *ptr;
+  int s;
 
   memset (&hints, 0, sizeof (hints));
   hints.ai_family = address_family;
@@ -399,19 +400,26 @@ lookup_host (const char *host, char *buf, size_t buflen)
   res = result;
 
   while (res) {
-  inet_ntop (res->ai_family, res->ai_addr->sa_data, buf, buflen);
-  switch (res->ai_family) {
-    case AF_INET:
-      ptr = &((struct sockaddr_in *) res->ai_addr)->sin_addr;
+    inet_ntop (res->ai_family, res->ai_addr->sa_data, buf, buflen);
+    switch (res->ai_family) {
+      case AF_INET:
+        ptr = &((struct sockaddr_in *) res->ai_addr)->sin_addr;
+        break;
+      case AF_INET6:
+        ptr = &((struct sockaddr_in6 *) res->ai_addr)->sin6_addr;
       break;
-    case AF_INET6:
-      ptr = &((struct sockaddr_in6 *) res->ai_addr)->sin6_addr;
-    break;
     }
+
     inet_ntop (res->ai_family, ptr, buf, buflen);
     if (verbose >= 1)
       printf ("* getaddrinfo IPv%d address: %s\n",
         res->ai_family == PF_INET6 ? 6 : 4, buf);
+
+    if (s = socket (res->ai_family, res->ai_socktype, res->ai_protocol) == -1)
+      continue;
+    if (bind (s, res->ai_addr, res->ai_addrlen == 0) )
+      break;
+
     res = res->ai_next;
   }
   
-- 
cgit v1.2.3-74-g34f1


From 2902381c5de01f69d61569b0c8dae6a92e2b9843 Mon Sep 17 00:00:00 2001
From: Barak Shohat <barak@bazzisoft.com>
Date: Wed, 8 Mar 2023 11:56:43 +0200
Subject: check_curl.c: Include all IPs from getaddrinfo() in curl DNS cache

---
 plugins/check_curl.c | 39 ++++++++++++++++++++++++++-------------
 1 file changed, 26 insertions(+), 13 deletions(-)

diff --git a/plugins/check_curl.c b/plugins/check_curl.c
index e1bc98dc..512fb88a 100644
--- a/plugins/check_curl.c
+++ b/plugins/check_curl.c
@@ -384,9 +384,12 @@ int
 lookup_host (const char *host, char *buf, size_t buflen)
 {
   struct addrinfo hints, *res, *result;
+  char addrstr[100];
+  size_t addrstr_len;
   int errcode;
   void *ptr;
   int s;
+  size_t buflen_remaining = buflen - 1;
 
   memset (&hints, 0, sizeof (hints));
   hints.ai_family = address_family;
@@ -396,33 +399,40 @@ lookup_host (const char *host, char *buf, size_t buflen)
   errcode = getaddrinfo (host, NULL, &hints, &result);
   if (errcode != 0)
     return errcode;
-  
+
+  strcpy(buf, "");
   res = result;
 
   while (res) {
-    inet_ntop (res->ai_family, res->ai_addr->sa_data, buf, buflen);
     switch (res->ai_family) {
       case AF_INET:
         ptr = &((struct sockaddr_in *) res->ai_addr)->sin_addr;
         break;
       case AF_INET6:
         ptr = &((struct sockaddr_in6 *) res->ai_addr)->sin6_addr;
-      break;
+        break;
     }
 
-    inet_ntop (res->ai_family, ptr, buf, buflen);
-    if (verbose >= 1)
+    inet_ntop (res->ai_family, ptr, addrstr, 100);
+    if (verbose >= 1) {
       printf ("* getaddrinfo IPv%d address: %s\n",
-        res->ai_family == PF_INET6 ? 6 : 4, buf);
+        res->ai_family == PF_INET6 ? 6 : 4, addrstr);
+    }
 
-    if (s = socket (res->ai_family, res->ai_socktype, res->ai_protocol) == -1)
-      continue;
-    if (bind (s, res->ai_addr, res->ai_addrlen == 0) )
-      break;
+    // Append all IPs to buf as a comma-separated string
+    addrstr_len = strlen(addrstr);
+    if (buflen_remaining > addrstr_len + 1) {
+      if (buf[0] != NULL) {
+        strncat(buf, ",", 1);
+        buflen_remaining -= 1;
+      }
+      strncat(buf, addrstr, buflen_remaining);
+      buflen_remaining -= addrstr_len;
+    }
 
     res = res->ai_next;
   }
-  
+
   freeaddrinfo(result);
 
   return 0;
@@ -453,7 +463,7 @@ check_http (void)
   int i;
   char *force_host_header = NULL;
   struct curl_slist *host = NULL;
-  char addrstr[100];
+  char addrstr[DEFAULT_BUFFER_SIZE/2];
   char dnscache[DEFAULT_BUFFER_SIZE];
 
   /* initialize curl */
@@ -505,7 +515,7 @@ check_http (void)
 
   // fill dns resolve cache to make curl connect to the given server_address instead of the host_name, only required for ssl, because we use the host_name later on to make SNI happy
   if(use_ssl && host_name != NULL) {
-      if ( (res=lookup_host (server_address, addrstr, 100)) != 0) {
+      if ( (res=lookup_host (server_address, addrstr, DEFAULT_BUFFER_SIZE/2)) != 0) {
         snprintf (msg, DEFAULT_BUFFER_SIZE, _("Unable to lookup IP address for '%s': getaddrinfo returned %d - %s"),
           server_address, res, gai_strerror (res));
         die (STATE_CRITICAL, "HTTP CRITICAL - %s\n", msg);
@@ -800,6 +810,9 @@ check_http (void)
   /* free header and server IP resolve lists, we don't need it anymore */
   curl_slist_free_all (header_list); header_list = NULL;
   curl_slist_free_all (server_ips); server_ips = NULL;
+  if (host) {
+    curl_slist_free_all (host); host = NULL;
+  }
 
   /* Curl errors, result in critical Nagios state */
   if (res != CURLE_OK) {
-- 
cgit v1.2.3-74-g34f1


From fc927e98db73850e760f490117ed36f2de20270c Mon Sep 17 00:00:00 2001
From: Andreas Baumann <mail@andreasbaumann.cc>
Date: Wed, 8 Mar 2023 16:10:45 +0100
Subject: fixed a wrong compare and a wrong size in strncat

---
 plugins/check_curl.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/plugins/check_curl.c b/plugins/check_curl.c
index 512fb88a..cc17ef58 100644
--- a/plugins/check_curl.c
+++ b/plugins/check_curl.c
@@ -422,8 +422,8 @@ lookup_host (const char *host, char *buf, size_t buflen)
     // Append all IPs to buf as a comma-separated string
     addrstr_len = strlen(addrstr);
     if (buflen_remaining > addrstr_len + 1) {
-      if (buf[0] != NULL) {
-        strncat(buf, ",", 1);
+      if (buf[0] != '\0') {
+        strncat(buf, ",", buflen_remaining);
         buflen_remaining -= 1;
       }
       strncat(buf, addrstr, buflen_remaining);
-- 
cgit v1.2.3-74-g34f1


From ea53555f2d6254da5fec0c1061899a01dd5321ec Mon Sep 17 00:00:00 2001
From: Andreas Baumann <mail@andreasbaumann.cc>
Date: Sat, 11 Mar 2023 11:40:00 +0100
Subject: check_curl: removed a superflous variable

---
 plugins/check_curl.c | 1 -
 1 file changed, 1 deletion(-)

diff --git a/plugins/check_curl.c b/plugins/check_curl.c
index cc17ef58..e5be1ad5 100644
--- a/plugins/check_curl.c
+++ b/plugins/check_curl.c
@@ -388,7 +388,6 @@ lookup_host (const char *host, char *buf, size_t buflen)
   size_t addrstr_len;
   int errcode;
   void *ptr;
-  int s;
   size_t buflen_remaining = buflen - 1;
 
   memset (&hints, 0, sizeof (hints));
-- 
cgit v1.2.3-74-g34f1