[core] cleanup: consolidate FAM code in stat_cache
[lighttpd.git] / src / inet_ntop_cache.c
blob868b8df2f254520ec43b929fa4b024b55ad44ab9
1 #include "first.h"
3 #include "inet_ntop_cache.h"
5 #include "sys-socket.h"
6 #include <sys/types.h>
7 #include <string.h>
8 #ifndef _WIN32
9 #include <arpa/inet.h>
10 #endif
12 #include "sock_addr.h"
15 const char * inet_ntop_cache_get_ip(server *srv, sock_addr *addr) {
16 #ifdef HAVE_IPV6
17 typedef struct {
18 int family;
19 union {
20 struct in6_addr ipv6;
21 struct in_addr ipv4;
22 } addr;
23 char b2[INET6_ADDRSTRLEN + 1];
24 } inet_ntop_cache_type;
25 #define INET_NTOP_CACHE_MAX 4
26 static inet_ntop_cache_type inet_ntop_cache[INET_NTOP_CACHE_MAX];
27 static int ndx;
29 int i;
30 UNUSED(srv);
31 #ifdef HAVE_SYS_UN_H
32 if (addr->plain.sa_family == AF_UNIX) return addr->un.sun_path;
33 #endif
34 for (i = 0; i < INET_NTOP_CACHE_MAX; i++) {
35 if (inet_ntop_cache[i].family == addr->plain.sa_family) {
36 if (inet_ntop_cache[i].family == AF_INET6 &&
37 0 == memcmp(inet_ntop_cache[i].addr.ipv6.s6_addr, addr->ipv6.sin6_addr.s6_addr, 16)) {
38 /* IPv6 found in cache */
39 break;
40 } else if (inet_ntop_cache[i].family == AF_INET &&
41 inet_ntop_cache[i].addr.ipv4.s_addr == addr->ipv4.sin_addr.s_addr) {
42 /* IPv4 found in cache */
43 break;
49 if (i == INET_NTOP_CACHE_MAX) {
50 /* not found in cache */
51 const char *s;
53 i = ndx;
54 if (++ndx >= INET_NTOP_CACHE_MAX) ndx = 0;
55 s = sock_addr_inet_ntop(addr, inet_ntop_cache[i].b2, INET6_ADDRSTRLEN);
56 if (NULL == s) return "";
58 inet_ntop_cache[i].family = addr->plain.sa_family;
60 if (inet_ntop_cache[i].family == AF_INET) {
61 inet_ntop_cache[i].addr.ipv4.s_addr = addr->ipv4.sin_addr.s_addr;
62 } else if (inet_ntop_cache[i].family == AF_INET6) {
63 memcpy(inet_ntop_cache[i].addr.ipv6.s6_addr, addr->ipv6.sin6_addr.s6_addr, 16);
67 return inet_ntop_cache[i].b2;
68 #else
69 UNUSED(srv);
70 if (addr->plain.sa_family == AF_INET) return inet_ntoa(addr->ipv4.sin_addr);
71 #ifdef HAVE_SYS_UN_H
72 if (addr->plain.sa_family == AF_UNIX) return addr->un.sun_path;
73 #endif
74 return "";
75 #endif