summaryrefslogtreecommitdiffstats
path: root/lib/libatm
diff options
context:
space:
mode:
Diffstat (limited to 'lib/libatm')
-rw-r--r--lib/libatm/Makefile41
-rw-r--r--lib/libatm/atm_addr.c328
-rw-r--r--lib/libatm/cache_key.c105
-rw-r--r--lib/libatm/ioctl_subr.c461
-rw-r--r--lib/libatm/ip_addr.c160
-rw-r--r--lib/libatm/ip_checksum.c92
-rw-r--r--lib/libatm/libatm.h117
-rw-r--r--lib/libatm/timer.c258
8 files changed, 1562 insertions, 0 deletions
diff --git a/lib/libatm/Makefile b/lib/libatm/Makefile
new file mode 100644
index 0000000..921d3ff
--- /dev/null
+++ b/lib/libatm/Makefile
@@ -0,0 +1,41 @@
+# ===================================
+# HARP | Host ATM Research Platform
+# ===================================
+#
+# This Host ATM Research Platform ("HARP") file (the "Software") is
+# made available by Network Computing Services, Inc. ("NetworkCS")
+# "AS IS". NetworkCS does not provide maintenance, improvements or
+# support of any kind.
+#
+# NETWORKCS MAKES NO WARRANTIES OR REPRESENTATIONS, EXPRESS OR IMPLIED,
+# INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY
+# AND FITNESS FOR A PARTICULAR PURPOSE, AS TO ANY ELEMENT OF THE
+# SOFTWARE OR ANY SUPPORT PROVIDED IN CONNECTION WITH THIS SOFTWARE.
+# In no event shall NetworkCS be responsible for any damages, including
+# but not limited to consequential damages, arising from or relating to
+# any use of the Software or related support.
+#
+# Copyright 1994-1998 Network Computing Services, Inc.
+#
+# Copies of this Software may be made, however, the above copyright
+# notice must be reproduced on all copies.
+#
+# @(#) $Id: Makefile,v 1.5 1998/07/10 16:01:58 jpt Exp $
+# $FreeBSD$
+
+LIB= atm
+SHLIB_MAJOR= 5
+SHLIBDIR?= /lib
+SRCS= atm_addr.c cache_key.c ioctl_subr.c ip_addr.c ip_checksum.c timer.c
+INCS= libatm.h
+
+DPADD= ${LIBMD}
+LDADD= -lmd
+
+.if ${MACHINE_ARCH} == "arm"
+WARNS?= 3
+.else
+WARNS?= 6
+.endif
+
+.include <bsd.lib.mk>
diff --git a/lib/libatm/atm_addr.c b/lib/libatm/atm_addr.c
new file mode 100644
index 0000000..f4c65f2
--- /dev/null
+++ b/lib/libatm/atm_addr.c
@@ -0,0 +1,328 @@
+/*
+ *
+ * ===================================
+ * HARP | Host ATM Research Platform
+ * ===================================
+ *
+ *
+ * This Host ATM Research Platform ("HARP") file (the "Software") is
+ * made available by Network Computing Services, Inc. ("NetworkCS")
+ * "AS IS". NetworkCS does not provide maintenance, improvements or
+ * support of any kind.
+ *
+ * NETWORKCS MAKES NO WARRANTIES OR REPRESENTATIONS, EXPRESS OR IMPLIED,
+ * INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE, AS TO ANY ELEMENT OF THE
+ * SOFTWARE OR ANY SUPPORT PROVIDED IN CONNECTION WITH THIS SOFTWARE.
+ * In no event shall NetworkCS be responsible for any damages, including
+ * but not limited to consequential damages, arising from or relating to
+ * any use of the Software or related support.
+ *
+ * Copyright 1994-1998 Network Computing Services, Inc.
+ *
+ * Copies of this Software may be made, however, the above copyright
+ * notice must be reproduced on all copies.
+ */
+
+#ifndef lint
+#if 0 /* original (broken) import id */
+static char *RCSid = "@(#) $Id: atm_addr.c,v 1.1 1998/07/09 21:45:18 johnc Exp $";
+#endif
+#endif
+#include <sys/cdefs.h>
+__FBSDID("$FreeBSD$");
+
+/*
+ * User Space Library Functions
+ * ----------------------------
+ *
+ * ATM address utility functions
+ *
+ */
+
+#include <sys/types.h>
+#include <sys/param.h>
+#include <sys/socket.h>
+#include <net/if.h>
+#include <netinet/in.h>
+#include <netatm/port.h>
+#include <netatm/atm.h>
+#include <netatm/atm_if.h>
+#include <netatm/atm_sap.h>
+#include <netatm/atm_sys.h>
+#include <netatm/atm_ioctl.h>
+
+#include <stdio.h>
+#include <string.h>
+
+#include "libatm.h"
+
+extern char *prog;
+
+/*
+ * Get NSAP, NSAP prefix or MAC address
+ *
+ * Arguments:
+ * in pointer to an address in ASCII
+ * out pointer to a buffer for the converted address
+ * len the length of the output buffer
+ *
+ * Returns:
+ * 0 error in format
+ * len the length of the data in the output buffer
+ *
+ */
+int
+get_hex_atm_addr(const char *in, u_char *out, int len)
+{
+ int c_type, c_value, i, out_len, state, val = 0;
+
+ /*
+ * Character table
+ */
+ static struct {
+ char c;
+ int type;
+ int value;
+ } char_table[] = {
+ {'.', 0, 0}, /* Type 0 -- period */
+ {':', 0, 0}, /* Type 0 -- colon */
+ {'0', 1, 0}, /* Type 1 -- hex digit */
+ {'1', 1, 1},
+ {'2', 1, 2},
+ {'3', 1, 3},
+ {'4', 1, 4},
+ {'5', 1, 5},
+ {'6', 1, 6},
+ {'7', 1, 7},
+ {'8', 1, 8},
+ {'9', 1, 9},
+ {'a', 1, 10},
+ {'b', 1, 11},
+ {'c', 1, 12},
+ {'d', 1, 13},
+ {'e', 1, 14},
+ {'f', 1, 15},
+ {'A', 1, 10},
+ {'B', 1, 11},
+ {'C', 1, 12},
+ {'D', 1, 13},
+ {'E', 1, 14},
+ {'F', 1, 15},
+ {'\0', 2, 0}, /* Type 2 -- end of input */
+ };
+
+ /*
+ * State table
+ */
+ static struct {
+ int action;
+ int state;
+ } state_table[3][3] = {
+ /* Period Hex End */
+ { { 0, 0 }, { 1, 1 }, { 2, 0} }, /* Init */
+ { { 4, 0 }, { 3, 2 }, { 4, 0} }, /* C1 */
+ { { 0, 2 }, { 1, 1 }, { 2, 0} }, /* C2 */
+ };
+
+ /*
+ * Initialize
+ */
+ state = 0;
+ out_len = 0;
+ if (!strncasecmp(in, "0x", 2)) {
+ in += 2;
+ }
+
+ /*
+ * Loop through input until state table says to return
+ */
+ while (1) {
+ /*
+ * Get the character type and value
+ */
+ for (i=0; char_table[i].c; i++)
+ if (char_table[i].c == *in)
+ break;
+ if (char_table[i].c != *in)
+ return(0);
+ c_type = char_table[i].type;
+ c_value = char_table[i].value;
+
+ /*
+ * Process next character based on state and type
+ */
+ switch(state_table[state][c_type].action) {
+ case 0:
+ /*
+ * Ignore the character
+ */
+ break;
+
+ case 1:
+ /*
+ * Save the character's value
+ */
+ val = c_value;
+ break;
+
+ case 2:
+ /*
+ * Return the assembled NSAP
+ */
+ return(out_len);
+
+ case 3:
+ /*
+ * Assemble and save the output byte
+ */
+ val = val << 4;
+ val += c_value;
+ out[out_len] = (u_char) val;
+ out_len++;
+ if (out_len > len)
+ (void)fprintf(stderr, "%s() out_len > len (%d > %d)\n",
+ __func__, out_len, len);
+
+ break;
+
+ case 4:
+ /*
+ * Invalid input sequence
+ */
+ return(0);
+
+ default:
+ return(0);
+ }
+
+ /*
+ * Set the next state and go on to the next character
+ */
+ state = state_table[state][c_type].state;
+ in++;
+ }
+}
+
+
+/*
+ * Format an ATM address into a string
+ *
+ * Arguments:
+ * addr pointer to an atm address
+ *
+ * Returns:
+ * none
+ *
+ */
+char *
+format_atm_addr(const Atm_addr *addr)
+{
+ int i;
+ const char *nsap_format;
+ const Atm_addr_nsap *atm_nsap;
+ const Atm_addr_e164 *atm_e164;
+ const Atm_addr_spans *atm_spans;
+ const Atm_addr_pvc *atm_pvc;
+ static char str[256];
+ union {
+ int w;
+ char c[4];
+ } u1, u2;
+
+ static const char nsap_format_DCC[] = "0x%02x.%02x%02x.%02x.%02x%02x%02x.%02x%02x.%02x%02x.%02x%02x.%02x%02x%02x%02x%02x%02x.%02x";
+ static const char nsap_format_ICD[] = "0x%02x.%02x%02x.%02x.%02x%02x%02x.%02x%02x.%02x%02x.%02x%02x.%02x%02x%02x%02x%02x%02x.%02x";
+ static const char nsap_format_E164[] = "0x%02x.%02x%02x%02x%02x%02x%02x%02x%02x.%02x%02x.%02x%02x.%02x%02x%02x%02x%02x%02x.%02x";
+
+ /*
+ * Clear the returned string
+ */
+ bzero(str, sizeof(str));
+ strcpy(str, "-");
+
+ /*
+ * Print format is determined by address type
+ */
+ switch (addr->address_format) {
+ case T_ATM_ENDSYS_ADDR:
+ atm_nsap = (const Atm_addr_nsap *)addr->address;
+ switch(atm_nsap->aan_afi) {
+ default:
+ case AFI_DCC:
+ nsap_format = nsap_format_DCC;
+ break;
+ case AFI_ICD:
+ nsap_format = nsap_format_ICD;
+ break;
+ case AFI_E164:
+ nsap_format = nsap_format_E164;
+ break;
+ }
+ sprintf(str, nsap_format,
+ atm_nsap->aan_afi,
+ atm_nsap->aan_afspec[0],
+ atm_nsap->aan_afspec[1],
+ atm_nsap->aan_afspec[2],
+ atm_nsap->aan_afspec[3],
+ atm_nsap->aan_afspec[4],
+ atm_nsap->aan_afspec[5],
+ atm_nsap->aan_afspec[6],
+ atm_nsap->aan_afspec[7],
+ atm_nsap->aan_afspec[8],
+ atm_nsap->aan_afspec[9],
+ atm_nsap->aan_afspec[10],
+ atm_nsap->aan_afspec[11],
+ atm_nsap->aan_esi[0],
+ atm_nsap->aan_esi[1],
+ atm_nsap->aan_esi[2],
+ atm_nsap->aan_esi[3],
+ atm_nsap->aan_esi[4],
+ atm_nsap->aan_esi[5],
+ atm_nsap->aan_sel);
+ break;
+
+ case T_ATM_E164_ADDR:
+ atm_e164 = (const Atm_addr_e164 *)addr->address;
+ for(i=0; i<addr->address_length; i++) {
+ sprintf(&str[strlen(str)], "%c",
+ atm_e164->aae_addr[i]);
+ }
+ break;
+
+ case T_ATM_SPANS_ADDR:
+ /*
+ * Print SPANS address as two words, xxxx.yyyy
+ */
+ atm_spans = (const Atm_addr_spans *)addr->address;
+ u1.c[0] = atm_spans->aas_addr[0];
+ u1.c[1] = atm_spans->aas_addr[1];
+ u1.c[2] = atm_spans->aas_addr[2];
+ u1.c[3] = atm_spans->aas_addr[3];
+
+ u2.c[0] = atm_spans->aas_addr[4];
+ u2.c[1] = atm_spans->aas_addr[5];
+ u2.c[2] = atm_spans->aas_addr[6];
+ u2.c[3] = atm_spans->aas_addr[7];
+
+ if (!(u1.w == 0 && u2.w == 0))
+ sprintf(str, "0x%08lx.%08lx",
+ (u_long)ntohl(u1.w), (u_long)ntohl(u2.w));
+ break;
+
+ case T_ATM_PVC_ADDR:
+ /*
+ * Print PVC as VPI, VCI
+ */
+ atm_pvc = (const Atm_addr_pvc *)addr->address;
+ sprintf(str, "%d, %d",
+ ATM_PVC_GET_VPI(atm_pvc),
+ ATM_PVC_GET_VCI(atm_pvc));
+ break;
+
+ case T_ATM_ABSENT:
+ default:
+ break;
+ }
+
+ return(str);
+}
diff --git a/lib/libatm/cache_key.c b/lib/libatm/cache_key.c
new file mode 100644
index 0000000..7bfeac2
--- /dev/null
+++ b/lib/libatm/cache_key.c
@@ -0,0 +1,105 @@
+/*
+ *
+ * ===================================
+ * HARP | Host ATM Research Platform
+ * ===================================
+ *
+ *
+ * This Host ATM Research Platform ("HARP") file (the "Software") is
+ * made available by Network Computing Services, Inc. ("NetworkCS")
+ * "AS IS". NetworkCS does not provide maintenance, improvements or
+ * support of any kind.
+ *
+ * NETWORKCS MAKES NO WARRANTIES OR REPRESENTATIONS, EXPRESS OR IMPLIED,
+ * INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE, AS TO ANY ELEMENT OF THE
+ * SOFTWARE OR ANY SUPPORT PROVIDED IN CONNECTION WITH THIS SOFTWARE.
+ * In no event shall NetworkCS be responsible for any damages, including
+ * but not limited to consequential damages, arising from or relating to
+ * any use of the Software or related support.
+ *
+ * Copyright 1994-1998 Network Computing Services, Inc.
+ *
+ * Copies of this Software may be made, however, the above copyright
+ * notice must be reproduced on all copies.
+ */
+
+#include <sys/cdefs.h>
+__FBSDID("$FreeBSD$");
+
+/*
+ * User Space Library Functions
+ * ----------------------------
+ *
+ * SCSP cache key computation
+ *
+ */
+
+#include <sys/types.h>
+#include <sys/param.h>
+#include <sys/socket.h>
+#include <net/if.h>
+#include <netinet/in.h>
+#include <netatm/port.h>
+#include <netatm/atm.h>
+#include <netatm/atm_if.h>
+#include <netatm/atm_sap.h>
+#include <netatm/atm_sys.h>
+#include <netatm/atm_ioctl.h>
+
+#include <md5.h>
+#include <string.h>
+
+#include "libatm.h"
+
+/*
+ * Compute an SCSP cache key
+ *
+ * Arguments:
+ * ap pointer to an Atm_addr with the ATM address
+ * ip pointer to a struct in_addr with the IP address
+ * ol the required length of the cache key
+ * op pointer to receive cache key
+ *
+ * Returns:
+ * none
+ *
+ */
+void
+scsp_cache_key(const Atm_addr *ap, const struct in_addr *ip, int ol, char *op)
+{
+ int i, len;
+ char buff[32];
+ unsigned char digest[16];
+ MD5_CTX context;
+
+ /*
+ * Initialize
+ */
+ bzero(buff, sizeof(buff));
+
+ /*
+ * Copy the addresses into a buffer for MD5 computation
+ */
+ len = sizeof(struct in_addr) + ap->address_length;
+ if (len > (int)sizeof(buff))
+ len = sizeof(buff);
+ bcopy(ip, buff, sizeof(struct in_addr));
+ bcopy(ap->address, &buff[sizeof(struct in_addr)],
+ len - sizeof(struct in_addr));
+
+ /*
+ * Compute the MD5 digest of the combined IP and ATM addresses
+ */
+ MD5Init(&context);
+ MD5Update(&context, buff, len);
+ MD5Final(digest, &context);
+
+ /*
+ * Fold the 16-byte digest to the required length
+ */
+ bzero((caddr_t)op, ol);
+ for (i = 0; i < 16; i++) {
+ op[i % ol] = op[i % ol] ^ digest[i];
+ }
+}
diff --git a/lib/libatm/ioctl_subr.c b/lib/libatm/ioctl_subr.c
new file mode 100644
index 0000000..f7b15f1
--- /dev/null
+++ b/lib/libatm/ioctl_subr.c
@@ -0,0 +1,461 @@
+/*
+ *
+ * ===================================
+ * HARP | Host ATM Research Platform
+ * ===================================
+ *
+ *
+ * This Host ATM Research Platform ("HARP") file (the "Software") is
+ * made available by Network Computing Services, Inc. ("NetworkCS")
+ * "AS IS". NetworkCS does not provide maintenance, improvements or
+ * support of any kind.
+ *
+ * NETWORKCS MAKES NO WARRANTIES OR REPRESENTATIONS, EXPRESS OR IMPLIED,
+ * INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE, AS TO ANY ELEMENT OF THE
+ * SOFTWARE OR ANY SUPPORT PROVIDED IN CONNECTION WITH THIS SOFTWARE.
+ * In no event shall NetworkCS be responsible for any damages, including
+ * but not limited to consequential damages, arising from or relating to
+ * any use of the Software or related support.
+ *
+ * Copyright 1994-1998 Network Computing Services, Inc.
+ *
+ * Copies of this Software may be made, however, the above copyright
+ * notice must be reproduced on all copies.
+ */
+
+#include <sys/cdefs.h>
+__FBSDID("$FreeBSD$");
+
+/*
+ * User Space Library Functions
+ * ----------------------------
+ *
+ * IOCTL subroutines
+ *
+ */
+
+#include <sys/types.h>
+#include <sys/param.h>
+#include <sys/socket.h>
+#include <sys/sockio.h>
+#include <net/if.h>
+#include <netinet/in.h>
+#include <netatm/port.h>
+#include <netatm/atm.h>
+#include <netatm/atm_if.h>
+#include <netatm/atm_sap.h>
+#include <netatm/atm_sys.h>
+#include <netatm/atm_ioctl.h>
+
+#include <errno.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+
+#include "libatm.h"
+
+#ifndef TRUE
+#define TRUE 1
+#endif
+
+#ifndef FALSE
+#define FALSE 0
+#endif
+
+extern char *prog;
+
+
+/*
+ * Issue an informational IOCTL
+ *
+ * The user fills out the opcode and any subtype information. This
+ * routine will allocate a buffer and issue the IOCTL. If the request
+ * fails because the buffer wasn't big enough, this routine will double
+ * the buffer size and retry the request repeatedly. The buffer must
+ * be freed by the caller.
+ *
+ * Arguments:
+ * req pointer to an ATM information request IOCTL structure
+ * buf_len length of buffer to be allocated
+ *
+ * Returns:
+ * -1 error encountered (reason in errno)
+ * int length of the returned VCC information
+ *
+ */
+ssize_t
+do_info_ioctl(struct atminfreq *req, size_t buf_len)
+{
+ int rc, s;
+ caddr_t buf;
+
+ /*
+ * Open a socket for the IOCTL
+ */
+ s = socket(AF_ATM, SOCK_DGRAM, 0);
+ if (s < 0) {
+ return(-1);
+ }
+
+ /*
+ * Get memory for returned information
+ */
+mem_retry:
+ buf = malloc(buf_len);
+ if (buf == NULL) {
+ errno = ENOMEM;
+ return(-1);
+ }
+ bzero(buf, buf_len);
+
+ /*
+ * Set the buffer address and length in the request
+ */
+ req->air_buf_addr = buf;
+ req->air_buf_len = buf_len;
+
+ /*
+ * Issue the IOCTL
+ */
+ rc = ioctl(s, AIOCINFO, (caddr_t)req);
+ if (rc) {
+ free(buf);
+ if (errno == ENOSPC) {
+ buf_len = buf_len * 2;
+ goto mem_retry;
+ }
+ return(-1);
+ }
+ (void)close(s);
+ /*
+ * Set a pointer to the returned info in the request
+ * and return its length
+ */
+ req->air_buf_addr = buf;
+ return(req->air_buf_len);
+}
+
+
+/*
+ * Get VCC information
+ *
+ * Arguments:
+ * intf pointer to interface name (or null string)
+ * vccp pointer to a pointer to a struct air_vcc_rsp for the
+ * address of the returned VCC information
+ *
+ * Returns:
+ * int length of the retuned VCC information
+ *
+ */
+ssize_t
+get_vcc_info(const char *intf, struct air_vcc_rsp **vccp)
+{
+ size_t buf_len = sizeof(struct air_vcc_rsp) * 100;
+ struct atminfreq air;
+
+ /*
+ * Initialize IOCTL request
+ */
+ air.air_opcode = AIOCS_INF_VCC;
+ bzero(air.air_vcc_intf, sizeof(air.air_vcc_intf));
+ if (intf != NULL && strlen(intf) != 0)
+ strncpy(air.air_vcc_intf, intf, IFNAMSIZ - 1);
+
+ buf_len = do_info_ioctl(&air, buf_len);
+
+ /*
+ * Return a pointer to the VCC info and its length
+ */
+ *vccp = (struct air_vcc_rsp *)(void *)air.air_buf_addr;
+ return(buf_len);
+}
+
+
+/*
+ * Get subnet mask
+ *
+ * Arguments:
+ * intf pointer to an interface name
+ * mask pointer to a struct sockaddr_in to receive the mask
+ *
+ * Returns:
+ * 0 good completion
+ * -1 error
+ *
+ */
+int
+get_subnet_mask(const char *intf, struct sockaddr_in *mask)
+{
+ int rc, s;
+ struct ifreq req;
+ struct sockaddr_in *ip_mask;
+
+ /*
+ * Check parameters
+ */
+ if (!intf || !mask ||
+ strlen(intf) == 0 ||
+ strlen(intf) > IFNAMSIZ-1)
+ return(-1);
+
+ /*
+ * Open a socket for the IOCTL
+ */
+ s = socket(AF_INET, SOCK_DGRAM, 0);
+ if (s < 0)
+ return(-1);
+
+ /*
+ * Set up and issue the IOCTL
+ */
+ bzero(&req, sizeof(req));
+ strcpy(req.ifr_name, intf);
+ rc = ioctl(s, SIOCGIFNETMASK, (caddr_t)&req);
+ (void)close(s);
+ if (rc)
+ return(-1);
+
+ /*
+ * Give the answer back to the caller
+ */
+ ip_mask = (struct sockaddr_in *)(void *)&req.ifr_addr;
+ *mask = *ip_mask;
+ mask->sin_family = AF_INET;
+
+ return(0);
+}
+
+
+/*
+ * Get an interface's MTU
+ *
+ * Arguments:
+ * intf pointer to an interface name
+ * mtu pointer to an int to receive the MTU
+ *
+ * Returns:
+ * >= 0 interface MTU
+ * -1 error
+ *
+ */
+int
+get_mtu(const char *intf)
+{
+ int rc, s;
+ struct ifreq req;
+
+ /*
+ * Check parameters
+ */
+ if (!intf || strlen(intf) == 0 ||
+ strlen(intf) > IFNAMSIZ-1)
+ return(-1);
+
+ /*
+ * Open a socket for the IOCTL
+ */
+ s = socket(AF_INET, SOCK_DGRAM, 0);
+ if (s < 0)
+ return(-1);
+
+ /*
+ * Set up and issue the IOCTL
+ */
+ bzero(&req, sizeof(req));
+ strcpy(req.ifr_name, intf);
+ rc = ioctl(s, SIOCGIFMTU, (caddr_t)&req);
+ (void)close(s);
+
+ /*
+ * Set the appropriate return value
+ */
+ if (rc)
+ return(-1);
+ else
+ return(req.ifr_mtu);
+}
+
+
+/*
+ * Verify netif name
+ *
+ * This routine issues an IOCTL to check whether the passed string is
+ * a valid network interface name.
+ *
+ * Arguments:
+ * req pointer to an ATM information request IOCTL structure
+ *
+ * Returns:
+ * -1 error encountered
+ * FALSE (0) the string is not a NIF name
+ * TRUE (> 0) the string is a valid NIF name
+ *
+ */
+int
+verify_nif_name(const char *name)
+{
+ int rc, s;
+ struct atminfreq air;
+ struct air_netif_rsp *nif_info;
+
+ /*
+ * Check whether name is of a valid length
+ */
+ if (strlen(name) > IFNAMSIZ - 1 ||
+ strlen(name) < 1) {
+ return(FALSE);
+ }
+
+ /*
+ * Open a socket for the IOCTL
+ */
+ s = socket(AF_ATM, SOCK_DGRAM, 0);
+ if (s < 0) {
+ return(-1);
+ }
+
+ /*
+ * Get memory for returned information
+ */
+ nif_info = malloc(sizeof(struct air_netif_rsp));
+ if (nif_info == NULL) {
+ errno = ENOMEM;
+ return(-1);
+ }
+ bzero(nif_info, sizeof(struct air_netif_rsp));
+
+ /*
+ * Set up the request
+ */
+ air.air_opcode = AIOCS_INF_NIF;
+ air.air_buf_addr = (caddr_t)nif_info;
+ air.air_buf_len = sizeof(struct air_netif_rsp);
+ bzero(air.air_netif_intf, sizeof(air.air_netif_intf));
+ strcpy(air.air_netif_intf, name);
+
+ /*
+ * Issue the IOCTL
+ */
+ rc = ioctl(s, AIOCINFO, (caddr_t)&air);
+ free(nif_info);
+ (void)close(s);
+
+ /*
+ * Base return value on IOCTL return code
+ */
+ if (rc)
+ return(FALSE);
+ else
+ return(TRUE);
+}
+
+/*
+ * Get Config information
+ *
+ * Arguments:
+ * intf pointer to interface name (or null string)
+ * cfgp pointer to a pointer to a struct air_cfg_rsp for the
+ * address of the returned Config information
+ *
+ * Returns:
+ * int length of returned Config information
+ *
+ */
+ssize_t
+get_cfg_info(const char *intf, struct air_cfg_rsp **cfgp)
+{
+ size_t buf_len = sizeof(struct air_cfg_rsp) * 4;
+ struct atminfreq air;
+
+ /*
+ * Initialize IOCTL request
+ */
+ air.air_opcode = AIOCS_INF_CFG;
+ bzero ( air.air_cfg_intf, sizeof(air.air_cfg_intf));
+ if ( intf != NULL && strlen(intf) != 0 )
+ strncpy(air.air_cfg_intf, intf, IFNAMSIZ - 1);
+
+ buf_len = do_info_ioctl ( &air, buf_len );
+
+ /*
+ * Return a pointer to the Config info and its length
+ */
+ *cfgp = (struct air_cfg_rsp *)(void *)air.air_buf_addr;
+ return ( buf_len );
+
+}
+
+/*
+ * Get Physical Interface information
+ *
+ * Arguments:
+ * intf pointer to interface name (or null string)
+ * intp pointer to a pointer to a struct air_cfg_rsp for the
+ * address of the returned Config information
+ *
+ * Returns:
+ * int length of returned Config information
+ *
+ */
+ssize_t
+get_intf_info(const char *intf, struct air_int_rsp **intp)
+{
+ size_t buf_len = sizeof(struct air_int_rsp) * 4;
+ struct atminfreq air;
+
+ /*
+ * Initialize IOCTL request
+ */
+ air.air_opcode = AIOCS_INF_INT;
+ bzero ( air.air_int_intf, sizeof(air.air_int_intf));
+ if ( intf != NULL && strlen(intf) != 0 )
+ strncpy(air.air_int_intf, intf, IFNAMSIZ - 1);
+
+ buf_len = do_info_ioctl ( &air, buf_len );
+
+ /*
+ * Return a pointer to the Physical Interface info and its length
+ */
+ *intp = (struct air_int_rsp *)(void *)air.air_buf_addr;
+ return ( buf_len );
+
+}
+
+
+/*
+ * Get Netif information
+ *
+ * Arguments:
+ * intf pointer to interface name (or null string)
+ * netp pointer to a pointer to a struct air_netif_rsp for the
+ * address of the returned Netif information
+ *
+ * Returns:
+ * int length of returned Netif information
+ *
+ */
+ssize_t
+get_netif_info(const char *intf, struct air_netif_rsp **netp)
+{
+ size_t buf_len = sizeof(struct air_netif_rsp) * 10;
+ struct atminfreq air;
+
+ /*
+ * Initialize IOCTL request
+ */
+ air.air_opcode = AIOCS_INF_NIF;
+ bzero ( air.air_int_intf, sizeof(air.air_int_intf) );
+ if ( intf != NULL && strlen(intf) != 0 )
+ strncpy(air.air_int_intf, intf, IFNAMSIZ - 1);
+
+ buf_len = do_info_ioctl ( &air, buf_len );
+
+ /*
+ * Return a pointer to the Netif info and its length
+ */
+ *netp = (struct air_netif_rsp *) air.air_buf_addr;
+ return ( buf_len );
+
+}
diff --git a/lib/libatm/ip_addr.c b/lib/libatm/ip_addr.c
new file mode 100644
index 0000000..d3a5276
--- /dev/null
+++ b/lib/libatm/ip_addr.c
@@ -0,0 +1,160 @@
+/*
+ *
+ * ===================================
+ * HARP | Host ATM Research Platform
+ * ===================================
+ *
+ *
+ * This Host ATM Research Platform ("HARP") file (the "Software") is
+ * made available by Network Computing Services, Inc. ("NetworkCS")
+ * "AS IS". NetworkCS does not provide maintenance, improvements or
+ * support of any kind.
+ *
+ * NETWORKCS MAKES NO WARRANTIES OR REPRESENTATIONS, EXPRESS OR IMPLIED,
+ * INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE, AS TO ANY ELEMENT OF THE
+ * SOFTWARE OR ANY SUPPORT PROVIDED IN CONNECTION WITH THIS SOFTWARE.
+ * In no event shall NetworkCS be responsible for any damages, including
+ * but not limited to consequential damages, arising from or relating to
+ * any use of the Software or related support.
+ *
+ * Copyright 1994-1998 Network Computing Services, Inc.
+ *
+ * Copies of this Software may be made, however, the above copyright
+ * notice must be reproduced on all copies.
+ */
+
+#include <sys/cdefs.h>
+__FBSDID("$FreeBSD$");
+
+/*
+ * User Space Library Functions
+ * ----------------------------
+ *
+ * IP address utilities
+ *
+ */
+
+#include <sys/types.h>
+#include <sys/param.h>
+#include <sys/socket.h>
+#include <stdio.h>
+#include <net/if.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+#include <netatm/port.h>
+#include <netatm/atm.h>
+#include <netatm/atm_if.h>
+#include <netatm/atm_sap.h>
+#include <netatm/atm_sys.h>
+#include <netatm/atm_ioctl.h>
+
+#include <netdb.h>
+#include <string.h>
+
+#include "libatm.h"
+
+/*
+ * Get IP address
+ *
+ * Return an IP address in a socket address structure, given a character
+ * string with a domain name or a dotted decimal number.
+ *
+ * Arguments:
+ * p pointer to a host name or IP address
+ *
+ * Returns:
+ * null error was encountered
+ * struct sockaddr_in * a pointer to a socket address with the
+ * requested IP address
+ *
+ */
+struct sockaddr_in *
+get_ip_addr(const char *p)
+{
+ struct hostent *ip_host;
+ static struct sockaddr_in s;
+
+ /*
+ * Get IP address of specified host name
+ */
+ bzero(&s, sizeof(s));
+ s.sin_family = AF_INET;
+ if (p[0] >= '0' && p[0] <= '9') {
+ /*
+ * IP address is in dotted decimal format
+ */
+ if ((s.sin_addr.s_addr = inet_addr(p)) == INADDR_NONE) {
+ return((struct sockaddr_in *)0);
+ }
+ } else {
+ /*
+ * Host name is in domain name system format
+ */
+ ip_host = gethostbyname(p);
+ if (!ip_host ||
+ ip_host->h_addrtype != AF_INET) {
+ return((struct sockaddr_in *)0);
+ }
+ memcpy(&s.sin_addr.s_addr, ip_host->h_addr_list[0],
+ sizeof(s.sin_addr.s_addr));
+ }
+ return(&s);
+}
+
+
+/*
+ * Format an IP address
+ *
+ * Return a text-formatted string with an IP address and domain name
+ * given a sockaddr_in with an IP address.
+ *
+ * Arguments:
+ * addr pointer to sockaddr_in with an IP address
+ *
+ * Returns:
+ * char * pointer to a text-formatted string
+ *
+ */
+const char *
+format_ip_addr(const struct in_addr *addr)
+{
+ static char host_name[MAXHOSTNAMELEN + 18];
+ char *ip_num;
+ struct hostent *ip_host;
+
+ /*
+ * Initialize
+ */
+ bzero(host_name, sizeof(host_name));
+
+ /*
+ * Check for a zero address
+ */
+ if (!addr || addr->s_addr == 0) {
+ return("-");
+ }
+
+ /*
+ * Get address in dotted decimal format
+ */
+ ip_num = inet_ntoa(*addr);
+
+ /*
+ * Look up name in DNS
+ */
+ ip_host = gethostbyaddr((const char *)addr, sizeof(addr), AF_INET);
+ if (ip_host && ip_host->h_name && strlen(ip_host->h_name)) {
+ /*
+ * Return host name followed by dotted decimal address
+ */
+ snprintf(host_name, sizeof(host_name), "%s (%s)",
+ ip_host->h_name, ip_num);
+ return (host_name);
+ } else {
+ /*
+ * No host name -- just return dotted decimal address
+ */
+ return(ip_num);
+ }
+}
diff --git a/lib/libatm/ip_checksum.c b/lib/libatm/ip_checksum.c
new file mode 100644
index 0000000..2881c24
--- /dev/null
+++ b/lib/libatm/ip_checksum.c
@@ -0,0 +1,92 @@
+/*
+ *
+ * ===================================
+ * HARP | Host ATM Research Platform
+ * ===================================
+ *
+ *
+ * This Host ATM Research Platform ("HARP") file (the "Software") is
+ * made available by Network Computing Services, Inc. ("NetworkCS")
+ * "AS IS". NetworkCS does not provide maintenance, improvements or
+ * support of any kind.
+ *
+ * NETWORKCS MAKES NO WARRANTIES OR REPRESENTATIONS, EXPRESS OR IMPLIED,
+ * INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE, AS TO ANY ELEMENT OF THE
+ * SOFTWARE OR ANY SUPPORT PROVIDED IN CONNECTION WITH THIS SOFTWARE.
+ * In no event shall NetworkCS be responsible for any damages, including
+ * but not limited to consequential damages, arising from or relating to
+ * any use of the Software or related support.
+ *
+ * Copyright 1994-1998 Network Computing Services, Inc.
+ *
+ * Copies of this Software may be made, however, the above copyright
+ * notice must be reproduced on all copies.
+ */
+
+#include <sys/cdefs.h>
+__FBSDID("$FreeBSD$");
+
+/*
+ * User Space Library Functions
+ * ----------------------------
+ *
+ * IP checksum computation
+ *
+ */
+
+#include <sys/types.h>
+#include <sys/param.h>
+#include <sys/socket.h>
+#include <net/if.h>
+#include <netinet/in.h>
+#include <netatm/port.h>
+#include <netatm/atm.h>
+#include <netatm/atm_if.h>
+#include <netatm/atm_sap.h>
+#include <netatm/atm_sys.h>
+#include <netatm/atm_ioctl.h>
+
+#include "libatm.h"
+
+/*
+ * Compute an IP checksum
+ *
+ * This code was taken from RFC 1071.
+ *
+ * "The following "C" code algorithm computes the checksum with an inner
+ * loop that sums 16 bits at a time in a 32-bit accumulator."
+ *
+ * Arguments:
+ * addr pointer to the buffer whose checksum is to be computed
+ * count number of bytes to include in the checksum
+ *
+ * Returns:
+ * the computed checksum
+ *
+ */
+short
+ip_checksum(const char *addr, int count)
+{
+ /* Compute Internet Checksum for "count" bytes
+ * beginning at location "addr".
+ */
+ long sum = 0;
+
+ while( count > 1 ) {
+ /* This is the inner loop */
+ sum += ntohs(* (const unsigned short *)(const void *)addr);
+ addr += sizeof(unsigned short);
+ count -= sizeof(unsigned short);
+ }
+
+ /* Add left-over byte, if any */
+ if( count > 0 )
+ sum += * (const unsigned char *) addr;
+
+ /* Fold 32-bit sum to 16 bits */
+ while (sum>>16)
+ sum = (sum & 0xffff) + (sum >> 16);
+
+ return((short)~sum);
+}
diff --git a/lib/libatm/libatm.h b/lib/libatm/libatm.h
new file mode 100644
index 0000000..1c2088f
--- /dev/null
+++ b/lib/libatm/libatm.h
@@ -0,0 +1,117 @@
+/*
+ *
+ * ===================================
+ * HARP | Host ATM Research Platform
+ * ===================================
+ *
+ *
+ * This Host ATM Research Platform ("HARP") file (the "Software") is
+ * made available by Network Computing Services, Inc. ("NetworkCS")
+ * "AS IS". NetworkCS does not provide maintenance, improvements or
+ * support of any kind.
+ *
+ * NETWORKCS MAKES NO WARRANTIES OR REPRESENTATIONS, EXPRESS OR IMPLIED,
+ * INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE, AS TO ANY ELEMENT OF THE
+ * SOFTWARE OR ANY SUPPORT PROVIDED IN CONNECTION WITH THIS SOFTWARE.
+ * In no event shall NetworkCS be responsible for any damages, including
+ * but not limited to consequential damages, arising from or relating to
+ * any use of the Software or related support.
+ *
+ * Copyright 1994-1998 Network Computing Services, Inc.
+ *
+ * Copies of this Software may be made, however, the above copyright
+ * notice must be reproduced on all copies.
+ *
+ * @(#) $FreeBSD$
+ *
+ */
+
+/*
+ * User Space Library Functions
+ * ----------------------------
+ *
+ * Library functions
+ *
+ */
+
+#ifndef _HARP_LIBHARP_H
+#define _HARP_LIBHARP_H
+
+/*
+ * Start a HARP user-space timer
+ *
+ * tp pointer to timer control block
+ * time number of seconds for timer to run
+ * fp pointer to function to call at expiration
+ */
+#define HARP_TIMER(tp, time, fp) \
+{ \
+ (tp)->ht_ticks = (time); \
+ (tp)->ht_mark = 0; \
+ (tp)->ht_func = (fp); \
+ LINK2HEAD((tp), Harp_timer, harp_timer_head, ht_next); \
+}
+
+/*
+ * Cancel a HARP user-space timer
+ *
+ * tp pointer to timer control block
+ */
+#define HARP_CANCEL(tp) \
+{ \
+ UNLINK((tp), Harp_timer, harp_timer_head, ht_next); \
+}
+
+
+/*
+ * HARP user-space timer control block
+ */
+struct harp_timer {
+ struct harp_timer *ht_next; /* Timer chain */
+ int ht_ticks; /* Seconds till exp */
+ int ht_mark; /* Processing flag */
+ void (*ht_func)(struct harp_timer *); /* Function to call */
+};
+typedef struct harp_timer Harp_timer;
+
+
+/*
+ * Externally-visible variables and functions
+ */
+
+/* atm_addr.c */
+extern int get_hex_atm_addr(const char *, u_char *, int);
+extern char *format_atm_addr(const Atm_addr *);
+
+/* cache_key.c */
+extern void scsp_cache_key(const Atm_addr *,
+ const struct in_addr *, int, char *);
+
+/* ioctl_subr.c */
+extern ssize_t do_info_ioctl(struct atminfreq *, size_t);
+extern ssize_t get_vcc_info(const char *, struct air_vcc_rsp **);
+extern int get_subnet_mask(const char *, struct sockaddr_in *);
+extern int get_mtu(const char *);
+extern int verify_nif_name(const char *);
+extern ssize_t get_cfg_info(const char *, struct air_cfg_rsp **);
+extern ssize_t get_intf_info(const char *, struct air_int_rsp **);
+extern ssize_t get_netif_info(const char *, struct air_netif_rsp **);
+
+/* ip_addr.c */
+extern struct sockaddr_in *get_ip_addr(const char *);
+extern const char *format_ip_addr(const struct in_addr *);
+
+/* ip_checksum.c */
+extern short ip_checksum(const char *, int);
+
+/* timer.c */
+extern Harp_timer *harp_timer_head;
+extern int harp_timer_exec;
+extern void timer_proc(void);
+extern int init_timer(void);
+extern int block_timer(void);
+extern void enable_timer(int);
+
+
+#endif /* _HARP_LIBHARP_H */
diff --git a/lib/libatm/timer.c b/lib/libatm/timer.c
new file mode 100644
index 0000000..1870e55
--- /dev/null
+++ b/lib/libatm/timer.c
@@ -0,0 +1,258 @@
+/*
+ *
+ * ===================================
+ * HARP | Host ATM Research Platform
+ * ===================================
+ *
+ *
+ * This Host ATM Research Platform ("HARP") file (the "Software") is
+ * made available by Network Computing Services, Inc. ("NetworkCS")
+ * "AS IS". NetworkCS does not provide maintenance, improvements or
+ * support of any kind.
+ *
+ * NETWORKCS MAKES NO WARRANTIES OR REPRESENTATIONS, EXPRESS OR IMPLIED,
+ * INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS FOR A PARTICULAR PURPOSE, AS TO ANY ELEMENT OF THE
+ * SOFTWARE OR ANY SUPPORT PROVIDED IN CONNECTION WITH THIS SOFTWARE.
+ * In no event shall NetworkCS be responsible for any damages, including
+ * but not limited to consequential damages, arising from or relating to
+ * any use of the Software or related support.
+ *
+ * Copyright 1994-1998 Network Computing Services, Inc.
+ *
+ * Copies of this Software may be made, however, the above copyright
+ * notice must be reproduced on all copies.
+ */
+
+#include <sys/cdefs.h>
+__FBSDID("$FreeBSD$");
+
+/*
+ * User Space Library Functions
+ * ----------------------------
+ *
+ * Timer functions
+ *
+ */
+
+#include <sys/types.h>
+#include <sys/param.h>
+#include <sys/socket.h>
+#include <net/if.h>
+#include <netinet/in.h>
+#include <netatm/port.h>
+#include <netatm/queue.h>
+#include <netatm/atm.h>
+#include <netatm/atm_if.h>
+#include <netatm/atm_sap.h>
+#include <netatm/atm_sys.h>
+#include <netatm/atm_ioctl.h>
+
+#include <errno.h>
+#include <signal.h>
+
+#include "libatm.h"
+
+Harp_timer *harp_timer_head;
+int harp_timer_exec;
+
+
+/*
+ * Process a HARP timer tick
+ *
+ * This function is called via the SIGALRM signal. It increments
+ * harp_timer_exec. The user should check this flag frequently and
+ * call timer_proc when it is set.
+ *
+ * Arguments:
+ * None
+ *
+ * Returns:
+ * None
+ *
+ */
+static void
+timer_tick(void)
+{
+ /*
+ * Bump the timer flag
+ */
+ harp_timer_exec++;
+}
+
+
+/*
+ * Process HARP timers
+ *
+ * This function is called after a SIGALRM signal is posted. It runs
+ * down the list of timer entries, calling the specified functions
+ * for any timers that have expired.
+ *
+ * Arguments:
+ * None
+ *
+ * Returns:
+ * None
+ *
+ */
+void
+timer_proc(void)
+{
+ Harp_timer *htp;
+ void (*f)(Harp_timer *);
+
+ /*
+ * Reset marks in all timers on the queue
+ */
+ for (htp = harp_timer_head; htp; htp = htp->ht_next) {
+ htp->ht_mark = -1;
+ }
+
+ /*
+ * Run through timer chain decrementing each timer.
+ * If an expired timer is found, take the timer block
+ * off the chain and call the specified function. A
+ * timer's action can result in other timers being
+ * cancelled (taken off the queue), so every time we
+ * call a user function, we start over from the top of
+ * the list.
+ */
+timer_cont:
+ for (htp = harp_timer_head; htp; htp = htp->ht_next) {
+ /*
+ * Make sure we only process each entry once and
+ * don't process entries that are put on the queue
+ * by user functions we call for this tick
+ */
+ if (htp->ht_mark == -1) {
+ /*
+ * Decrement the timer and mark that we've
+ * processed the entry
+ */
+ htp->ht_ticks -= harp_timer_exec;
+ htp->ht_mark = 1;
+
+ /*
+ * Check whether the timer is expired
+ */
+ if (htp->ht_ticks <= 0) {
+ /*
+ * Unlink the timer block and call
+ * the user function
+ */
+ f = htp->ht_func;
+ UNLINK(htp, Harp_timer, harp_timer_head,
+ ht_next);
+ f(htp);
+
+ /*
+ * Start over
+ */
+ goto timer_cont;
+ }
+ }
+ }
+
+ /*
+ * Reset the timer exec flag
+ */
+ harp_timer_exec = 0;
+}
+
+
+/*
+ * Start the timer
+ *
+ * Set up the SIGALRM signal handler and set up the real-time
+ * timer to tick once per second.
+ *
+ * Arguments:
+ * None
+ *
+ * Returns:
+ * 0 success
+ * errno reason for failure
+ *
+ */
+int
+init_timer()
+{
+ int rc = 0;
+ struct itimerval timeval;
+
+ /*
+ * Clear the timer flag
+ */
+ harp_timer_exec = 0;
+
+ /*
+ * Set up signal handler
+ */
+ if (signal(SIGALRM, (sig_t)timer_tick) == SIG_ERR) {
+ return(errno);
+ }
+
+ /*
+ * Start timer
+ */
+ timeval.it_value.tv_sec = 1;
+ timeval.it_value.tv_usec = 0;
+ timeval.it_interval.tv_sec = 1;
+ timeval.it_interval.tv_usec = 0;
+
+ if (setitimer(ITIMER_REAL, &timeval,
+ (struct itimerval *)0) == -1) {
+ rc = errno;
+ (void)signal(SIGALRM, SIG_DFL);
+ }
+
+ return(rc);
+}
+
+
+/*
+ * Block timers from firing
+ *
+ * Block the SIGALRM signal.
+ *
+ * Arguments:
+ * None
+ *
+ * Returns:
+ * mask the previous blocked signal mask
+ *
+ */
+int
+block_timer()
+{
+ /*
+ * Block the SIGALRM signal
+ */
+ return(sigblock(sigmask(SIGALRM)));
+}
+
+
+/*
+ * Re-enable timers
+ *
+ * Restore the signal mask (presumably one that was returned by
+ * block_timer).
+ *
+ * Arguments:
+ * mask the signal mask to be restored
+ *
+ * Returns:
+ * mask the previous blocked signal mask
+ *
+ */
+void
+enable_timer(mask)
+ int mask;
+{
+ /*
+ * Set the signal mask
+ */
+ sigsetmask(mask);
+
+ return;
+}
OpenPOWER on IntegriCloud