enable -fno-strict-aliasing until the code base gets a hefty clean up to fix all...
[platform/upstream/net-tools.git] / lib / tr.c
1 /*
2  * lib/tr.c   This file contains an implementation of the "Tokenring"
3  *              support functions.
4  *
5  * Version:     $Id: tr.c,v 1.9 2005/05/16 03:15:12 ecki Exp $
6  *
7  * Author:      Fred N. van Kempen, <waltje@uwalt.nl.mugnet.org>
8  *              Copyright 1993 MicroWalt Corporation
9  *
10  *              This program is free software; you can redistribute it
11  *              and/or  modify it under  the terms of  the GNU General
12  *              Public  License as  published  by  the  Free  Software
13  *              Foundation;  either  version 2 of the License, or  (at
14  *              your option) any later version.
15  */
16 #include "config.h"
17
18 #if HAVE_HWTR
19 #include <asm/types.h>
20 #include <sys/types.h>
21 #include <sys/socket.h>
22 #include <net/if_arp.h>
23 #include <linux/if_tr.h>
24 #include <stdlib.h>
25 #include <stdio.h>
26 #include <errno.h>
27 #include <ctype.h>
28 #include <string.h>
29 #include <unistd.h>
30 #include "net-support.h"
31 #include "pathnames.h"
32 #include "intl.h"
33 #include "util.h"
34
35
36 /* actual definition at the end of file */
37 extern struct hwtype tr_hwtype;
38 #ifdef ARPHRD_IEEE802_TR
39 extern struct hwtype tr_hwtype1;
40 #endif
41
42 static char *pr_tr(unsigned char *ptr)
43 {
44     static char buff[64];
45
46     snprintf(buff, sizeof(buff), "%02X:%02X:%02X:%02X:%02X:%02X",
47              (ptr[0] & 0377), (ptr[1] & 0377), (ptr[2] & 0377),
48              (ptr[3] & 0377), (ptr[4] & 0377), (ptr[5] & 0377)
49         );
50     return (buff);
51       }
52
53
54 static int in_tr(char *bufp, struct sockaddr *sap)
55 {
56     unsigned char *ptr;
57     char c, *orig;
58     int i, val;
59
60 #ifdef ARPHRD_IEEE802_TR
61     if (kernel_version() < KRELEASE(2,3,30)) { 
62         sap->sa_family = tr_hwtype.type;
63     } else { 
64         sap->sa_family = tr_hwtype1.type;
65     }   
66 #else
67     sap->sa_family = tr_hwtype.type;
68     #warning "Limited functionality, no support for ARPHRD_IEEE802_TR (old kernel headers?)"
69 #endif
70
71     ptr = sap->sa_data;
72
73     i = 0;
74     orig = bufp;
75     while ((*bufp != '\0') && (i < TR_ALEN)) {
76         val = 0;
77         c = *bufp++;
78         if (isdigit(c))
79             val = c - '0';
80         else if (c >= 'a' && c <= 'f')
81             val = c - 'a' + 10;
82         else if (c >= 'A' && c <= 'F')
83             val = c - 'A' + 10;
84         else {
85 #ifdef DEBUG
86             fprintf(stderr, _("in_tr(%s): invalid token ring address!\n"), orig);
87 #endif
88             errno = EINVAL;
89             return (-1);
90         }
91         val <<= 4;
92         c = *bufp++;
93         if (isdigit(c))
94             val |= c - '0';
95         else if (c >= 'a' && c <= 'f')
96             val |= c - 'a' + 10;
97         else if (c >= 'A' && c <= 'F')
98             val |= c - 'A' + 10;
99         else {
100 #ifdef DEBUG
101             fprintf(stderr, _("in_tr(%s): invalid token ring address!\n"), orig);
102 #endif
103             errno = EINVAL;
104             return (-1);
105         }
106         *ptr++ = (unsigned char) (val & 0377);
107         i++;
108
109         /* We might get a semicolon here - not required. */
110         if (*bufp == ':') {
111             if (i == TR_ALEN) {
112 #ifdef DEBUG
113                 fprintf(stderr, _("in_tr(%s): trailing : ignored!\n"),
114                         orig)
115 #endif
116                     ;           /* nothing */
117             }
118             bufp++;
119         }
120     }
121
122     /* That's it.  Any trailing junk? */
123     if ((i == TR_ALEN) && (*bufp != '\0')) {
124 #ifdef DEBUG
125         fprintf(stderr, _("in_tr(%s): trailing junk!\n"), orig);
126         errno = EINVAL;
127         return (-1);
128 #endif
129     }
130 #ifdef DEBUG
131     fprintf(stderr, "in_tr(%s): %s\n", orig, pr_tr(sap->sa_data));
132 #endif
133
134     return (0);
135 }
136
137
138 struct hwtype tr_hwtype =
139 {
140     "tr", NULL /* "16/4 Mbps Token Ring" */, ARPHRD_IEEE802, TR_ALEN,
141     pr_tr, in_tr, NULL
142 };
143 #ifdef ARPHRD_IEEE802_TR
144 struct hwtype tr_hwtype1 =
145 {
146     "tr", NULL /* "16/4 Mbps Token Ring" */, ARPHRD_IEEE802_TR, TR_ALEN,
147     pr_tr, in_tr, NULL
148 };
149 #endif
150
151
152 #endif                          /* HAVE_HWTR */