summary | shortlog | log | commit | commitdiff | tree
raw | patch | inline | side by side (parent: a7dd605)
raw | patch | inline | side by side (parent: a7dd605)
author | Florian Forster <octo@verplant.org> | |
Mon, 12 Jun 2006 20:30:13 +0000 (22:30 +0200) | ||
committer | Florian Forster <octo@verplant.org> | |
Mon, 12 Jun 2006 20:30:13 +0000 (22:30 +0200) |
Use `ping_setopt' and `PING_OPT_SOURCE' to set it. This _might_ fail under *BSD
and/or Mac OS X, I have to test that..
and/or Mac OS X, I have to test that..
src/liboping.c | patch | blob | history | |
src/oping.h | patch | blob | history |
diff --git a/src/liboping.c b/src/liboping.c
index 6131107a03509c320168e0c36d9cffd0edcc2fff..d74659fd24df0a9a7d48dd3763d2cdb2878a303c 100644 (file)
--- a/src/liboping.c
+++ b/src/liboping.c
struct pingobj
{
- double timeout;
- int ttl;
- int addrfamily;
- char *data;
+ double timeout;
+ int ttl;
+ int addrfamily;
+ char *data;
+
+ struct sockaddr_storage *srcaddr;
+ socklen_t srcaddrlen;
- char errmsg[PING_ERRMSG_LEN];
+ char errmsg[PING_ERRMSG_LEN];
- pinghost_t *head;
+ pinghost_t *head;
};
/*
if (obj->data != NULL)
free (obj->data);
+ if (obj->srcaddr != NULL)
+ free (obj->srcaddr);
+
free (obj);
return;
obj->addrfamily = PING_DEF_AF;
ret = -1;
}
+ if (obj->srcaddr != NULL)
+ {
+ free (obj->srcaddr);
+ obj->srcaddr = NULL;
+ }
break;
case PING_OPT_DATA:
obj->data = strdup ((const char *) value);
break;
+ case PING_OPT_SOURCE:
+ {
+ char *hostname = (char *) value;
+ struct addrinfo ai_hints;
+ struct addrinfo *ai_list;
+ int status;
+
+ memset ((void *) &ai_hints, '\0', sizeof (ai_hints));
+ ai_hints.ai_family = obj->addrfamily;
+#if defined(AI_ADDRCONFIG)
+ ai_hints.ai_flags = AI_ADDRCONFIG;
+#endif
+ status = getaddrinfo (hostname, NULL, &ai_hints, &ai_list);
+ if (status != 0)
+ {
+ ping_set_error (obj, "getaddrinfo",
+ status == EAI_SYSTEM
+ ? strerror (errno)
+ : gai_strerror (status));
+ ret = -1;
+ break;
+ }
+#if WITH_DEBUG
+ if (ai_list->ai_next != NULL)
+ {
+ dprintf ("hostname = `%s' is ambiguous.\n", hostname);
+ }
+#endif
+ if (obj->srcaddr == NULL)
+ {
+ obj->srcaddrlen = 0;
+ obj->srcaddr = (struct sockaddr_storage *) malloc (sizeof (struct sockaddr_storage));
+ if (obj->srcaddr == NULL)
+ {
+ ping_set_error (obj, "malloc",
+ strerror (errno));
+ ret = -1;
+ freeaddrinfo (ai_list);
+ break;
+ }
+ }
+ memset ((void *) obj->srcaddr, '\0', sizeof (struct sockaddr_storage));
+ assert (ai_list->ai_addrlen <= sizeof (struct sockaddr_storage));
+ memcpy ((void *) obj->srcaddr, (const void *) ai_list->ai_addr,
+ ai_list->ai_addrlen);
+ obj->srcaddrlen = ai_list->ai_addrlen;
+
+ freeaddrinfo (ai_list);
+ } /* case PING_OPT_SOURCE */
+ break;
+
default:
ret = -2;
} /* switch (option) */
diff --git a/src/oping.h b/src/oping.h
index 54d031017166495d0378ab7f6942902e123b4bf4..4cdb3cf3608cefe2cf7a91d75a73e0b69d102b4f 100644 (file)
--- a/src/oping.h
+++ b/src/oping.h
#define PING_OPT_TTL 0x02
#define PING_OPT_AF 0x04
#define PING_OPT_DATA 0x08
+#define PING_OPT_SOURCE 0x10
#define PING_DEF_TIMEOUT 1.0
#define PING_DEF_TTL 255