summaryrefslogtreecommitdiff
path: root/usr/src/lib/print/libpapi-common/common/misc.c
diff options
context:
space:
mode:
authorps29005 <none@none>2008-07-18 16:08:33 -0700
committerps29005 <none@none>2008-07-18 16:08:33 -0700
commita18dc42fc967d11feba9b8be61c6727dc6c56b48 (patch)
tree336dd000adc2ff7a4938db982383c2b78764752e /usr/src/lib/print/libpapi-common/common/misc.c
parentcbded9ae11944b2d8ab0ae13e5dbd0881ddba98c (diff)
downloadillumos-gate-a18dc42fc967d11feba9b8be61c6727dc6c56b48.tar.gz
6599099 fix for 4383387 should reuse existing memory
6599100 libpapi should be more picky about the uri schemes it allows. 6599950 print localhost checking should be shared
Diffstat (limited to 'usr/src/lib/print/libpapi-common/common/misc.c')
-rw-r--r--usr/src/lib/print/libpapi-common/common/misc.c141
1 files changed, 139 insertions, 2 deletions
diff --git a/usr/src/lib/print/libpapi-common/common/misc.c b/usr/src/lib/print/libpapi-common/common/misc.c
index 646a26e18a..2688fd0ec0 100644
--- a/usr/src/lib/print/libpapi-common/common/misc.c
+++ b/usr/src/lib/print/libpapi-common/common/misc.c
@@ -20,7 +20,7 @@
*/
/*
- * Copyright 2006 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*
*/
@@ -31,9 +31,14 @@
/*LINTLIBRARY*/
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
#include <string.h>
+#include <ctype.h>
+#include <sys/types.h>
#include <papi.h>
-
+#include <uri.h>
#include <config-site.h>
/*
@@ -85,3 +90,135 @@ strlcat(char *dst, const char *src, size_t dstsize)
return (l1 + l2);
}
#endif
+
+#if defined(__sun) && defined(__SVR4)
+#include <sys/systeminfo.h>
+#include <sys/socket.h>
+#include <sys/ioctl.h>
+#include <sys/sockio.h>
+#include <net/if.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+#include <netdb.h>
+
+static struct in6_addr **
+local_interfaces()
+{
+ struct in6_addr **result = NULL;
+ int s;
+ struct lifnum n;
+ struct lifconf c;
+ struct lifreq *r;
+ int count;
+
+ /* we need a socket to get the interfaces */
+ if ((s = socket(AF_INET, SOCK_DGRAM, 0)) < 0)
+ return (0);
+
+ /* get the number of interfaces */
+ memset(&n, 0, sizeof (n));
+ n.lifn_family = AF_UNSPEC;
+ if (ioctl(s, SIOCGLIFNUM, (char *)&n) < 0) {
+ close(s);
+ return (0); /* no interfaces */
+ }
+
+ /* get the interface(s) configuration */
+ memset(&c, 0, sizeof (c));
+ c.lifc_family = AF_UNSPEC;
+ c.lifc_buf = calloc(n.lifn_count, sizeof (struct lifreq));
+ c.lifc_len = (n.lifn_count * sizeof (struct lifreq));
+ if (ioctl(s, SIOCGLIFCONF, (char *)&c) < 0) {
+ free(c.lifc_buf);
+ close(s);
+ return (0); /* can't get interface(s) configuration */
+ }
+ close(s);
+
+ r = c.lifc_req;
+ for (count = c.lifc_len / sizeof (struct lifreq);
+ count > 0; count--, r++) {
+ struct in6_addr v6[1], *addr = NULL;
+
+ switch (r->lifr_addr.ss_family) {
+ case AF_INET: {
+ struct sockaddr_in *s =
+ (struct sockaddr_in *)&r->lifr_addr;
+ IN6_INADDR_TO_V4MAPPED(&s->sin_addr, v6);
+ addr = v6;
+ }
+ break;
+ case AF_INET6: {
+ struct sockaddr_in6 *s =
+ (struct sockaddr_in6 *)&r->lifr_addr;
+ addr = &s->sin6_addr;
+ }
+ break;
+ }
+
+ if (addr != NULL) {
+ struct in6_addr *a = malloc(sizeof (*a));
+
+ memcpy(a, addr, sizeof (*a));
+ list_append(&result, a);
+ }
+ }
+ free(c.lifc_buf);
+
+ return (result);
+}
+
+static int
+match_interfaces(char *host)
+{
+ struct in6_addr **lif = local_interfaces();
+ struct hostent *hp;
+ int rc = 0;
+ int errnum;
+
+ /* are there any local interfaces */
+ if (lif == NULL)
+ return (0);
+
+ /* cycle through the host db addresses */
+ hp = getipnodebyname(host, AF_INET6, AI_ALL|AI_V4MAPPED, &errnum);
+ if (hp != NULL) {
+ struct in6_addr **tmp = (struct in6_addr **)hp->h_addr_list;
+ int i;
+
+ for (i = 0; ((rc == 0) && (tmp[i] != NULL)); i++) {
+ int j;
+
+ for (j = 0; ((rc == 0) && (lif[j] != NULL)); j++)
+ if (memcmp(tmp[i], lif[j],
+ sizeof (struct in6_addr)) == 0)
+ rc = 1;
+ }
+ }
+ free(lif);
+
+ return (rc);
+}
+#endif
+
+int
+is_localhost(char *host)
+{
+ char hostname[BUFSIZ];
+
+ /* is it "localhost" */
+ if (strncasecmp(host, "localhost", 10) == 0)
+ return (1);
+
+ /* is it the {nodename} */
+ sysinfo(SI_HOSTNAME, hostname, sizeof (hostname));
+ if (strncasecmp(host, hostname, strlen(hostname)) == 0)
+ return (1);
+
+#if defined(__sun) && defined(__SVR4)
+ /* does it match one of the host's configured interfaces */
+ if (match_interfaces(host) != 0)
+ return (1);
+#endif
+ return (0);
+}