Upgrade to OpenVPN 2.1.0
[tomato.git] / release / src / router / openvpn / tap-win32 / macinfo.c
blobc03a8c5f89bf24a6b0f8825589a864d6cbc65ebf
1 /*
2 * TAP-Win32/TAP-Win64 -- A kernel driver to provide virtual tap
3 * device functionality on Windows.
5 * This code was inspired by the CIPE-Win32 driver by Damion K. Wilson.
7 * This source code is Copyright (C) 2002-2009 OpenVPN Technologies, Inc.,
8 * and is released under the GPL version 2 (see below).
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License version 2
12 * as published by the Free Software Foundation.
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
19 * You should have received a copy of the GNU General Public License
20 * along with this program (see the file COPYING included with this
21 * distribution); if not, write to the Free Software Foundation, Inc.,
22 * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
25 #include "macinfo.h"
27 int
28 HexStringToDecimalInt (const int p_Character)
30 int l_Value = 0;
32 if (p_Character >= 'A' && p_Character <= 'F')
33 l_Value = (p_Character - 'A') + 10;
34 else if (p_Character >= 'a' && p_Character <= 'f')
35 l_Value = (p_Character - 'a') + 10;
36 else if (p_Character >= '0' && p_Character <= '9')
37 l_Value = p_Character - '0';
39 return l_Value;
42 BOOLEAN
43 ParseMAC (MACADDR dest, const char *src)
45 int c;
46 int mac_index = 0;
47 BOOLEAN high_digit = FALSE;
48 int delim_action = 1;
50 MYASSERT (src);
51 MYASSERT (dest);
53 CLEAR_MAC (dest);
55 while (c = *src++)
57 if (IsMacDelimiter (c))
59 mac_index += delim_action;
60 high_digit = FALSE;
61 delim_action = 1;
63 else if (IsHexDigit (c))
65 const int digit = HexStringToDecimalInt (c);
66 if (mac_index < sizeof (MACADDR))
68 if (!high_digit)
70 dest[mac_index] = (char)(digit);
71 high_digit = TRUE;
72 delim_action = 1;
74 else
76 dest[mac_index] = (char)(dest[mac_index] * 16 + digit);
77 ++mac_index;
78 high_digit = FALSE;
79 delim_action = 0;
82 else
83 return FALSE;
85 else
86 return FALSE;
89 return (mac_index + delim_action) >= sizeof (MACADDR);
93 * Generate a MAC using the GUID in the adapter name.
95 * The mac is constructed as 00:FF:xx:xx:xx:xx where
96 * the Xs are taken from the first 32 bits of the GUID in the
97 * adapter name. This is similar to the Linux 2.4 tap MAC
98 * generator, except linux uses 32 random bits for the Xs.
100 * In general, this solution is reasonable for most
101 * applications except for very large bridged TAP networks,
102 * where the probability of address collisions becomes more
103 * than infintesimal.
105 * Using the well-known "birthday paradox", on a 1000 node
106 * network the probability of collision would be
107 * 0.000116292153. On a 10,000 node network, the probability
108 * of collision would be 0.01157288998621678766.
111 VOID GenerateRandomMac (MACADDR mac, const unsigned char *adapter_name)
113 unsigned const char *cp = adapter_name;
114 unsigned char c;
115 unsigned int i = 2;
116 unsigned int byte = 0;
117 int brace = 0;
118 int state = 0;
120 CLEAR_MAC (mac);
122 mac[0] = 0x00;
123 mac[1] = 0xFF;
125 while (c = *cp++)
127 if (i >= sizeof (MACADDR))
128 break;
129 if (c == '{')
130 brace = 1;
131 if (IsHexDigit (c) && brace)
133 const unsigned int digit = HexStringToDecimalInt (c);
134 if (state)
136 byte <<= 4;
137 byte |= digit;
138 mac[i++] = (unsigned char) byte;
139 state = 0;
141 else
143 byte = digit;
144 state = 1;
150 VOID GenerateRelatedMAC (MACADDR dest, const MACADDR src, const int delta)
152 COPY_MAC (dest, src);
153 dest[2] += (UCHAR) delta;