+ * duplicate server
+ * @param s the old server we want to duplicate
+ * @return new duplicated server
+ **/
+SERVER* dup_serve(SERVER *s) {
+ SERVER *serve = NULL;
+
+ serve=g_new0(SERVER, 1);
+ if (serve == NULL)
+ return NULL;
+
+ if (s->exportname)
+ serve->exportname = g_strdup(s->exportname);
+
+ serve->expected_size = s->expected_size;
+
+ if (s->listenaddr)
+ serve->listenaddr = g_strdup(s->listenaddr);
+
+ serve->port = s->port;
+
+ if (s->authname)
+ serve->authname = strdup(s->authname);
+
+ serve->flags = s->flags;
+ serve->socket = serve->socket;
+ serve->socket_family = serve->socket_family;
+ serve->cidrlen = s->cidrlen;
+
+ if (s->prerun)
+ serve->prerun = g_strdup(s->prerun);
+
+ if (s->postrun)
+ serve->postrun = g_strdup(s->postrun);
+
+ return serve;
+}
+
+/**
+ * append new server to array
+ * @param s server
+ * @param a server array
+ * @return 0 success, -1 error
+ */
+int append_serve(SERVER *s, GArray *a) {
+ SERVER *ns = NULL;
+ struct addrinfo hints;
+ struct addrinfo *ai = NULL;
+ struct addrinfo *rp = NULL;
+ char host[NI_MAXHOST];
+ gchar *port = NULL;
+ int e;
+ int ret;
+
+ if(!s) {
+ err("Invalid parsing server");
+ return -1;
+ }
+
+ port = g_strdup_printf("%d", s->port);
+
+ memset(&hints,'\0',sizeof(hints));
+ hints.ai_family = AF_UNSPEC;
+ hints.ai_socktype = SOCK_STREAM;
+ hints.ai_flags = AI_ADDRCONFIG | AI_PASSIVE;
+ hints.ai_protocol = IPPROTO_TCP;
+
+ e = getaddrinfo(s->listenaddr, port, &hints, &ai);
+
+ if (port)
+ g_free(port);
+
+ if(e == 0) {
+ for (rp = ai; rp != NULL; rp = rp->ai_next) {
+ e = getnameinfo(rp->ai_addr, rp->ai_addrlen, host, sizeof(host), NULL, 0, NI_NUMERICHOST);
+
+ if (e != 0) { // error
+ fprintf(stderr, "getnameinfo: %s\n", gai_strerror(e));
+ continue;
+ }
+
+ // duplicate server and set listenaddr to resolved IP address
+ ns = dup_serve (s);
+ if (ns) {
+ ns->listenaddr = g_strdup(host);
+ ns->socket_family = rp->ai_family;
+ g_array_append_val(a, *ns);
+ free(ns);
+ ns = NULL;
+ }
+ }
+
+ ret = 0;
+ } else {
+ fprintf(stderr, "getaddrinfo failed on listen host/address: %s (%s)\n", s->listenaddr ? s->listenaddr : "any", gai_strerror(e));
+ ret = -1;
+ }
+
+ if (ai)
+ freeaddrinfo(ai);
+
+ return ret;
+}
+
+/**