[sgen] Clear the card table in the finishing pause
[mono.git] / mcs / class / System / Test / System.Net / IPAddressTest.cs
1 //
2 // IPAddressTest.cs - NUnit Test Cases for System.Net.IPAddress
3 //
4 // Authors:
5 //   Gonzalo Paniagua Javier (gonzalo@ximian.com)
6 //   Martin Willemoes Hansen (mwh@sysrq.dk)
7 //
8 // (C) Ximian, Inc. http://www.ximian.com
9 // (C) 2003 Martin Willemoes Hansen
10 // Copyright (C) 2005 Novell, Inc (http://www.novell.com)
11 //
12
13 using NUnit.Framework;
14 using System;
15 using System.Net;
16 using System.Net.Sockets;
17 using System.Runtime.InteropServices;
18
19 namespace MonoTests.System.Net
20 {
21
22 [TestFixture]
23 public class IPAddressTest
24 {
25         static string[] ipv6AddressList = new string[] {
26                    "::", "0:0:0:0:0:0:0:0", 
27                    "1::", "1:0:0:0:0:0:0:0",
28                    "2:2::", "2:2:0:0:0:0:0:0",
29                    "7:7:7:7:7:7:7:0", "7:7:7:7:7:7:7:0",
30                    "::1", "0:0:0:0:0:0:0:1",
31                    "::2", "0:0:0:0:0:0:0:2",
32                    "::F", "0:0:0:0:0:0:0:F",
33                    "::10", "0:0:0:0:0:0:0:10",
34                    "::A0", "0:0:0:0:0:0:0:A0",
35                    "::F0", "0:0:0:0:0:0:0:F0",
36                    "::FF", "0:0:0:0:0:0:0:FF",
37                    "::0.1.0.0", "0:0:0:0:0:0:1:0",
38                    "::0.2.0.0", "0:0:0:0:0:0:2:0",
39                    "::0.15.0.0", "0:0:0:0:0:0:F:0",
40                    "::0.16.0.0", "0:0:0:0:0:0:10:0",
41                    "::0.160.0.0", "0:0:0:0:0:0:A0:0",
42                    "::0.240.0.0", "0:0:0:0:0:0:F0:0",
43                    "::0.255.0.0", "0:0:0:0:0:0:FF:0",
44                    "::1001", "0:0:0:0:0:0:0:1001",
45                    "::1002", "0:0:0:0:0:0:0:1002",
46                    "::100F", "0:0:0:0:0:0:0:100F",
47                    "::1010", "0:0:0:0:0:0:0:1010",
48                    "::10A0", "0:0:0:0:0:0:0:10A0",
49                    "::10F0", "0:0:0:0:0:0:0:10F0",
50                    "::10FF", "0:0:0:0:0:0:0:10FF",
51                    "::0.1.0.1", "0:0:0:0:0:0:1:1",
52                    "::0.2.0.2", "0:0:0:0:0:0:2:2",
53                    "::0.15.0.15", "0:0:0:0:0:0:F:F",
54                    "::0.16.0.16", "0:0:0:0:0:0:10:10",
55                    "::0.160.0.160", "0:0:0:0:0:0:A0:A0",
56                    "::0.240.0.240", "0:0:0:0:0:0:F0:F0",
57                    "::0.255.0.255", "0:0:0:0:0:0:FF:FF",
58                    "::FFFF:0:1", "0:0:0:0:0:FFFF:0:1",
59                    "::FFFF:0:2", "0:0:0:0:0:FFFF:0:2",
60                    "::FFFF:0:F", "0:0:0:0:0:FFFF:0:F",
61                    "::FFFF:0:10", "0:0:0:0:0:FFFF:0:10",
62                    "::FFFF:0:A0", "0:0:0:0:0:FFFF:0:A0",
63                    "::FFFF:0:F0", "0:0:0:0:0:FFFF:0:F0",
64                    "::FFFF:0:FF", "0:0:0:0:0:FFFF:0:FF",
65                    "::FFFF:0.1.0.0", "0:0:0:0:0:FFFF:1:0",
66                    "::FFFF:0.2.0.0", "0:0:0:0:0:FFFF:2:0",
67                    "::FFFF:0.15.0.0", "0:0:0:0:0:FFFF:F:0",
68                    "::FFFF:0.16.0.0", "0:0:0:0:0:FFFF:10:0",
69                    "::FFFF:0.160.0.0", "0:0:0:0:0:FFFF:A0:0",
70                    "::FFFF:0.240.0.0", "0:0:0:0:0:FFFF:F0:0",
71                    "::FFFF:0.255.0.0", "0:0:0:0:0:FFFF:FF:0",
72                    "::FFFF:0:1001", "0:0:0:0:0:FFFF:0:1001",
73                    "::FFFF:0:1002", "0:0:0:0:0:FFFF:0:1002",
74                    "::FFFF:0:100F", "0:0:0:0:0:FFFF:0:100F",
75                    "::FFFF:0:1010", "0:0:0:0:0:FFFF:0:1010",
76                    "::FFFF:0:10A0", "0:0:0:0:0:FFFF:0:10A0",
77                    "::FFFF:0:10F0", "0:0:0:0:0:FFFF:0:10F0",
78                    "::FFFF:0:10FF", "0:0:0:0:0:FFFF:0:10FF",
79                    "::FFFF:0.1.0.1", "0:0:0:0:0:FFFF:1:1",
80                    "::FFFF:0.2.0.2", "0:0:0:0:0:FFFF:2:2",
81                    "::FFFF:0.15.0.15", "0:0:0:0:0:FFFF:F:F",
82                    "::FFFF:0.16.0.16", "0:0:0:0:0:FFFF:10:10",
83                    "::FFFF:0.160.0.160", "0:0:0:0:0:FFFF:A0:A0",
84                    "::FFFF:0.240.0.240", "0:0:0:0:0:FFFF:F0:F0",
85                    "::FFFF:0.255.0.255", "0:0:0:0:0:FFFF:FF:FF",
86                    "0:7:7:7:7:7:7:7", "0:7:7:7:7:7:7:7",
87                    "E::1", "E:0:0:0:0:0:0:1",
88                    "E::2:2", "E:0:0:0:0:0:2:2",
89                    "E:0:6:6:6:6:6:6", "E:0:6:6:6:6:6:6",
90                    "E:E::1", "E:E:0:0:0:0:0:1",
91                    "E:E::2:2", "E:E:0:0:0:0:2:2",
92                    "E:E:0:5:5:5:5:5", "E:E:0:5:5:5:5:5",
93                    "E:E:E::1", "E:E:E:0:0:0:0:1",
94                    "E:E:E::2:2", "E:E:E:0:0:0:2:2",
95                    "E:E:E:0:4:4:4:4", "E:E:E:0:4:4:4:4",
96                    "E:E:E:E::1", "E:E:E:E:0:0:0:1",
97                    "E:E:E:E::2:2", "E:E:E:E:0:0:2:2",
98                    "E:E:E:E:0:3:3:3", "E:E:E:E:0:3:3:3",
99                    "E:E:E:E:E::1", "E:E:E:E:E:0:0:1",
100                    "E:E:E:E:E:0:2:2", "E:E:E:E:E:0:2:2",
101                    "E:E:E:E:E:E:0:1", "E:E:E:E:E:E:0:1",
102                    "::0.2.0.2", "0:0:0:0:0:0:2:2",
103                    "::FFFF:192.168.0.1", "::FFFF:192.168.0.1",
104                    "::FFFF:0.168.0.1", "::FFFF:0.168.0.1",
105                    "::FFFF", "::0.0.255.255",
106                    "::EEEE:A00:1", "::EEEE:10.0.0.1",
107                    "::10.0.0.1", "::10.0.0.1",
108                    "1234::1234:0:0", "1234:0:0:0:0:1234:0:0",
109                    "1:0:1:0:1:0:1:0", "1:0:1:0:1:0:1:0",
110                    "1:1:1::1:1:0", "1:1:1:0:0:1:1:0",
111                    "::1234:0:0", "0:0:0:0:0:1234:0:0",
112                    "3ffe:38e1::100:1:1", "3ffe:38e1::0100:1:0001",
113                    "0:0:1:2::", "0:0:1:2:00:00:000:0000",
114                    "100:0:1:2::abcd", "100:0:1:2:0:0:000:abcd",
115                    "ffff::abcd", "ffff:0:0:0:0:0:00:abcd",
116                    "ffff:0:0:2::abcd", "ffff:0:0:2:0:0:00:abcd",
117                    "0:0:1:2::", "0:0:1:2:0:00:0000:0000",
118                    "::1:0:0", "0000:0000::1:0000:0000",
119                    "::111:234:5:6:789a:0", "0:0:111:234:5:6:789A:0",
120                    "11:22:33:44:55:66:77:8", "11:22:33:44:55:66:77:8",
121                    "0:0:7711:ab42:1230::", "::7711:ab42:1230:0:0:0",
122                    "fec0:0:0:ffff::1%1",
123         };
124
125         static string[] ipv6ParseWrong = new string[] {
126                    ":::4df",
127                    "4df:::",
128                    "0:::4df",
129                    "4df:::0",
130                    "::4df:::",
131                    "0::4df:::",
132                    " ::1",
133                    ":: 1",
134                    ":",
135                    "0:0:0:0:0:0:0:0:0",
136                    "0:0:0:0:0:0:0",
137                    "0FFFF::",
138                    "FFFF0::",
139                    "[::1",
140         };
141
142         static string[] ipv4ParseOk = new string[] {
143                 "192.168.1.1", "192.168.1.1",
144                 "0xff.0x7f.0x20.0x01", "255.127.32.1",
145                 "0xff.0x7f.0x20.0xf", "255.127.32.15",
146                 "0.0.0.0", IPAddress.Any.ToString(),
147                 "255.255.255.255", IPAddress.Broadcast.ToString(),
148                 "12.1.1.3 abc", "12.1.1.3",
149                 "12.1 .1.2", "12.0.0.1",
150                 "12.1 .zzzz.2", "12.0.0.1",
151                 "12.1.7", "12.1.0.7",
152                 "12", "0.0.0.12",
153                 "12.5.3 foo.67.test.test.7FFFFFFFFFfaFFF789FFFFFFFFFFFFFFF", "12.5.0.3",
154                 "12.1 foo.bar.test.test.baf", "12.0.0.1",
155                 "12.1.4.6 foo.bar.test.test.baf", "12.1.4.6",
156                 "12.3 foo.bar.test.test.4", "12.0.0.3",
157                 "12 foo.bar.test.test.baf", "0.0.0.12",
158                 "65536", "0.1.0.0",
159                 "65535", "0.0.255.255",
160                 "20.65535", "20.0.255.255",
161                 "0313.027035210", "203.92.58.136", // bug #411920
162                 "0313.0134.035210", "203.92.58.136", // too
163                 "1434328179", "85.126.28.115", // too
164                 "3397943208", "202.136.127.168", // too
165         };
166
167         static string [] ipv4ParseWrong = new string [] {
168                 " foo",
169                 "12.. .",
170                 "12.1.2. ",
171                 "12.1.8. ",
172                 ".1.1.6",
173                 " 12.1.1.1",
174                 "12.+1.1.4",
175                 "12.1.-1.5",
176                 "257.1.1.9",
177                 "255.1.1.256",
178                 "12.1.1.3 ",
179                 "12.1 foo.1.2.3.4.5.bar",
180                 "12.1 foo.1.2.3.4.5.",
181                 "12.1.1.3 g",
182                 " ",
183                 "",
184                 "12.1.foo.1.2.3.4.5.bar",
185                 "12.",
186                 "12.1.2.",
187                 "12...",
188                 "  ",
189                 "7848198702",
190         };
191
192         static byte [] ipv4MappedIPv6Prefix = new byte [] { 0,0, 0,0, 0,0, 0,0, 0,0, 0xFF,0xFF };
193
194         [Test]
195         public void PublicFields ()
196         {
197                 Assert.AreEqual ((long) 0, IPAddress.Any.Address, "#1");
198                 Assert.AreEqual ((long) 0xFFFFFFFF, IPAddress.Broadcast.Address, "#2");
199                 long loopback = IPAddress.HostToNetworkOrder (BitConverter.IsLittleEndian ? 
200                                                               0x7f000001 : 
201                                                               0x0100007f);
202                 Assert.AreEqual (loopback, IPAddress.Loopback.Address, "#3");
203                 Assert.AreEqual ((long) 0xFFFFFFFF, IPAddress.None.Address, "#4");
204         }
205
206         [Test]
207         public void ToStringV4 ()
208         {
209                 IPAddress ip = IPAddress.Parse ("192.168.1.1");
210                 Assert.AreEqual ("192.168.1.1", ip.ToString (), "#1");
211                 Assert.AreEqual ("0.0.0.0", IPAddress.Any.ToString (), "#2");
212                 Assert.AreEqual ("255.255.255.255", IPAddress.Broadcast.ToString (), "#3");
213                 Assert.AreEqual ("127.0.0.1", IPAddress.Loopback.ToString (), "#4");
214                 Assert.AreEqual ("255.255.255.255", IPAddress.None.ToString (), "#5");
215         }
216
217         [Test]
218         public void ToStringV6 ()
219         {
220                 for(int i=0; i<ipv6AddressList.Length/2; i++) {
221                         string addr = IPAddress.Parse (ipv6AddressList[i*2+1]).ToString().ToLower();
222                         Assert.AreEqual (ipv6AddressList[i*2].ToLower(), addr, "ToStringIPv6 #" + i);
223                 }
224         }
225
226         [Test]
227         public void IsLoopbackV4 ()
228         {
229                 IPAddress ip;
230
231                 ip = IPAddress.Parse ("127.0.0.1");
232                 Assert.IsTrue (IPAddress.IsLoopback (ip), "#1");
233                 ip = IPAddress.Any;
234                 Assert.IsFalse (IPAddress.IsLoopback (ip), "#2");
235                 ip = IPAddress.Loopback;
236                 Assert.IsTrue (IPAddress.IsLoopback (ip), "#3");
237                 ip = IPAddress.Parse ("::101");
238                 Assert.IsFalse (IPAddress.IsLoopback (ip), "#4");
239         }
240
241         [Test]
242         public void IsLoopbackV6 ()
243         {
244                 if (!Socket.SupportsIPv6)
245                         Assert.Ignore ("IPv6 must be enabled in machine.config");
246
247                 IPAddress ip = IPAddress.IPv6Loopback;
248                 Assert.IsTrue (IPAddress.IsLoopback (ip), "#1");
249
250                 ip = IPAddress.IPv6None;
251                 Assert.IsFalse (IPAddress.IsLoopback (ip), "#2");
252         }
253
254         [Test]
255         public void GetAddressBytesV4 ()
256         {
257                 byte[] dataIn   = { 10, 11, 12, 13 };
258                 byte[] dataOut  = IPAddress.Parse ("10.11.12.13").GetAddressBytes ();
259                 for (int i = 0; i < dataIn.Length; i++)
260                         Assert.AreEqual (dataOut [i], dataIn [i], "GetAddressBytesV4");
261         }
262
263         [Test]
264         public void GetAddressBytesV6 ()
265         {
266                 byte[] dataIn   = new byte[]{ 0x01, 0x23, 0x45, 0x67, 0x89, 0x98, 0x76, 0x54, 0x32, 0x10, 0x01, 0x23, 0x45, 0x67, 0x89, 0x98 };
267                 byte[] dataOut  = IPAddress.Parse ("123:4567:8998:7654:3210:0123:4567:8998").GetAddressBytes ();
268                 for (int i = 0; i < dataIn.Length; i++)
269                         Assert.AreEqual (dataOut [i], dataIn [i], "GetAddressBytesV6 #1");
270
271                 dataIn  = new byte[]{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0x01 };
272                 dataOut = IPAddress.Parse ("::FFFF:127.0.0.1").GetAddressBytes ();
273                 for (int i = 0; i < dataIn.Length; i++)
274                         Assert.AreEqual (dataOut [i], dataIn [i], "GetAddressBytesV6 #2");
275         }
276
277         [Test]
278         public void Address ()
279         {
280                 // hm, lame, anything is accepted by ms.net
281                 /*
282                 try {
283                         IPAddress ip1 = new IPAddress (0x0000000100000000);
284                         Assertion.Fail ("#1");
285                 } catch (ArgumentOutOfRangeException) {}
286                 IPAddress ip = IPAddress.Parse ("127.0.0.1");
287                 ip.Address = 0;
288                 ip.Address = 0xffffffff;
289                 try {
290                         ip.Address = -1;
291                         Assertion.Fail ("#2");
292                 } catch (ArgumentOutOfRangeException) {}
293                 try {
294                         ip.Address = 0x0000000100000000;
295                         Assertion.Fail ("#3");
296                 } catch (ArgumentOutOfRangeException) {}
297                 */
298         }
299
300         [Test]
301         public void ParseOkV4 ()
302         {
303                 for (int i = 0; i < ipv4ParseOk.Length / 2; i++) {
304                         IPAddress ip;
305                         try {
306                                 ip = IPAddress.Parse (ipv4ParseOk [i*2]);
307                                 Assert.AreEqual (ipv4ParseOk [i * 2 + 1], ip.ToString (), "ParseOkV4:" + i);
308                         } catch (FormatException) {
309                                 Assert.Fail ("Cannot parse test i=" + i + ": '" + ipv4ParseOk [i*2] + "'");
310                         }
311                 }
312         }
313
314         [Test]
315         public void ParseOkV6 ()
316         {
317                 for (int i = 0; i < ipv6AddressList.Length / 2; i++) {
318                         string source = ipv6AddressList [i*2].ToLower();
319
320                         IPAddress ip = IPAddress.Parse (source);
321                         Assert.AreEqual (ip.ToString ().ToLower (), source,
322                                 string.Format("ParseIPv6 #{0}-1: {1} != {2}", i,
323                                         ip.ToString ().ToLower (), source));
324
325                         ip = IPAddress.Parse (ipv6AddressList [i*2+1].ToLower ());
326                         Assert.AreEqual (ip.ToString ().ToLower (), source,
327                                 string.Format("ParseIPv6 #{0}-2: {1} != {2}", i,
328                                         ip.ToString ().ToLower (), source));
329                 }
330         }
331
332         [Test]
333         public void ParseWrongV4 ()
334         {
335                 for (int i = 0; i < ipv4ParseWrong.Length; i++) {
336                         string ipAddress = ipv4ParseWrong [i];
337
338                         try {
339                                 IPAddress ip = IPAddress.Parse (ipAddress);
340                                 Assert.Fail ("#1:" + i + " (" + ipAddress + ")");
341                         } catch (FormatException ex) {
342                                 Assert.AreEqual (typeof (FormatException), ex.GetType (), "#2:" + i);
343                                 Assert.IsNull (ex.InnerException, "#3:" + i);
344                                 Assert.IsNotNull (ex.Message, "#4:" + i);
345                         }
346                 }
347         }
348
349         [Test]
350         public void Parse_IpString_Null ()
351         {
352                 try {
353                         IPAddress.Parse ((string) null);
354                         Assert.Fail ("#1");
355                 } catch (ArgumentNullException ex) {
356                         Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
357                         Assert.IsNull (ex.InnerException, "#3");
358                         Assert.IsNotNull (ex.Message, "#4");
359                         Assert.AreEqual ("ipString", ex.ParamName, "#5");
360                 }
361         }
362
363         [Test]
364         public void NetworkHost ()
365         {
366                 long [] tested = new long [] { 0, 1, 1, 1};
367                 long [] expectedLE = new long [] {0, 256, 16777216, 72057594037927936 };
368                 long [] expected;
369                 
370                 expected = BitConverter.IsLittleEndian ? expectedLE : tested;
371
372                 short short0 = IPAddress.NetworkToHostOrder ((short) tested [0]);
373                 Assert.AreEqual ((short) expected [0], short0, "#A1");
374                 short0 = IPAddress.HostToNetworkOrder (short0);
375                 Assert.AreEqual ((short) tested [0], short0, "#A2");
376
377                 int int0 = IPAddress.NetworkToHostOrder ((int) tested [0]);
378                 Assert.AreEqual ((int) expected [0], int0, "#B1");
379                 int0 = IPAddress.HostToNetworkOrder (int0);
380                 Assert.AreEqual ((int) tested [0], int0, "#B2");
381                 
382                 long long0 = IPAddress.NetworkToHostOrder (tested [0]);
383                 Assert.AreEqual (expected [0], long0, "#C1");
384                 long0 = IPAddress.HostToNetworkOrder (long0);
385                 Assert.AreEqual (tested [0], long0, "#C2");
386
387                 short0 = IPAddress.NetworkToHostOrder ((short) tested [1]);
388                 Assert.AreEqual ((short) expected [1], short0, "#D1");
389                 short0 = IPAddress.HostToNetworkOrder (short0);
390                 Assert.AreEqual ((short) tested [1], short0, "#D2");
391                 
392                 int0 = IPAddress.NetworkToHostOrder ((int) tested [2]);
393                 Assert.AreEqual ((int) expected [2], int0, "#E1");
394                 int0 = IPAddress.HostToNetworkOrder (int0);
395                 Assert.AreEqual ((int) tested [2], int0, "#E2");
396                 
397                 long0 = IPAddress.NetworkToHostOrder (tested [3]);
398                 Assert.AreEqual (expected [3], long0, "#F1");
399                 long0 = IPAddress.HostToNetworkOrder (long0);
400                 Assert.AreEqual (tested [3], long0, "#F2");
401         }
402
403         [Test]
404         public void LoopbackIPv6 ()
405         {
406                 Assert.IsTrue (new Uri("http://[0:0:0:0::127.0.0.1]/").IsLoopback, "#1");
407                 Assert.IsFalse (new Uri ("http://[0:0:0:0::127.1.2.3]/").IsLoopback, "#2");
408                 Assert.IsTrue (new Uri ("http://[0:0:0:0::0.0.0.1]/").IsLoopback, "#3");
409         }
410
411         [Test] // bug #76792
412         public void Constructor0_Address_4Byte ()
413         {
414                 byte[] bytes = new byte[4] { 192, 202, 112, 37 };
415                 IPAddress i = new IPAddress (bytes);
416                 Assert.AreEqual (bytes, i.GetAddressBytes (), "#1");
417                 Assert.AreEqual ("192.202.112.37", i.ToString (), "#2");
418         }
419
420         [Test]
421         public void Constructor0_Address_Invalid ()
422         {
423                 try {
424                         new IPAddress (new byte [0]);
425                         Assert.Fail ("#A1");
426                 } catch (ArgumentException ex) {
427                         Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#A2");
428                         Assert.IsNull (ex.InnerException, "#A3");
429                         Assert.IsNotNull (ex.Message, "#A4");
430                         Assert.IsFalse (ex.Message == "address", ex.Message, "#A5");
431                         Assert.IsNotNull (ex.ParamName, "#A6");
432                         Assert.AreEqual ("address", ex.ParamName, "#A7");
433                 }
434
435                 try {
436                         new IPAddress (new byte [3] { 192, 202, 112 });
437                         Assert.Fail ("#B1");
438                 } catch (ArgumentException ex) {
439                         Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#B2");
440                         Assert.IsNull (ex.InnerException, "#B3");
441                         Assert.IsNotNull (ex.Message, "#B4");
442                         Assert.IsFalse (ex.Message == "address", ex.Message, "#B5");
443                         Assert.IsNotNull (ex.ParamName, "#B6");
444                         Assert.AreEqual ("address", ex.ParamName, "#B7");
445                 }
446
447                 try {
448                         new IPAddress (new byte [5] { 192, 202, 112, 142, 25 });
449                         Assert.Fail ("#C1");
450                 } catch (ArgumentException ex) {
451                         Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#C2");
452                         Assert.IsNull (ex.InnerException, "#C3");
453                         Assert.IsNotNull (ex.Message, "#C4");
454                         Assert.IsFalse (ex.Message == "address", "#C5");
455                         Assert.IsNotNull (ex.ParamName, "#C6");
456                         Assert.AreEqual ("address", ex.ParamName, "#C7");
457                 }
458         }
459
460         [Test]
461         public void Constructor0_Address_Null ()
462         {
463                 try {
464                         new IPAddress ((byte []) null);
465                         Assert.Fail ("#1");
466                 } catch (ArgumentNullException ex) {
467                         Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
468                         Assert.IsNull (ex.InnerException, "#3");
469                         Assert.IsNotNull (ex.Message, "#4");
470                         Assert.AreEqual ("address", ex.ParamName, "#5");
471                 }
472         }
473
474         [Test]
475         public void Constructor1_Address_4Byte ()
476         {
477                 byte [] bytes = new byte [4] { 192, 202, 112, 37 };
478                 try {
479                         new IPAddress (bytes, 0);
480                         Assert.Fail ("#1");
481                 } catch (ArgumentException ex) {
482                         Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#2");
483                         Assert.IsNull (ex.InnerException, "#3");
484                         Assert.IsNotNull (ex.Message, "#4");
485                         Assert.IsFalse (ex.Message == "address", "#5");
486                         Assert.IsNotNull (ex.ParamName, "#6");
487                         Assert.AreEqual ("address", ex.ParamName, "#7");
488                 }
489         }
490
491         [Test]
492         public void Constructor1_Address_Null ()
493         {
494                 try {
495                         new IPAddress ((byte []) null, 5);
496                         Assert.Fail ("#1");
497                 } catch (ArgumentNullException ex) {
498                         Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
499                         Assert.IsNull (ex.InnerException, "#3");
500                         Assert.IsNotNull (ex.Message, "#4");
501                         Assert.AreEqual ("address", ex.ParamName, "#5");
502                 }
503         }
504
505         [Test]
506         public void FromBytes1 ()
507         {
508                 byte[] val1 = new byte[4];
509                 val1[0] = 82;
510                 val1[1] = 165;
511                 val1[2] = 240;
512                 val1[3] = 134;
513                 CompareIPs (val1, "82.165.240.134");
514
515                 byte[] val2 = new byte[4];
516                 val2[0] = 123;
517                 val2[1] = 124;
518                 val2[2] = 125;
519                 val2[3] = 126;
520                 CompareIPs (val2, "123.124.125.126");
521         }
522
523         void CompareIPs (byte [] bytes, string address)
524         {
525                 IPAddress ip = new IPAddress (bytes);
526                 IPAddress ip2 = IPAddress.Parse (address);
527                 Assert.IsTrue (ip2.Equals (ip), "#A-" + address);
528                 Assert.IsTrue (ip.Equals (ip2), "#B-" + address);
529         }
530
531         [Test]
532         public void TryParse_IpString_Null ()
533         {
534                 IPAddress i;
535
536                 try {
537                         IPAddress.TryParse ((string) null, out i);
538                         Assert.Fail ("#1");
539                 } catch (ArgumentNullException ex) {
540                         Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
541                         Assert.IsNull (ex.InnerException, "#3");
542                         Assert.IsNotNull (ex.Message, "#4");
543                         Assert.AreEqual ("ipString", ex.ParamName, "#5");
544                 }
545         }
546
547         [Test]
548         public void TryParse ()
549         {
550                 IPAddress i;
551                 Assert.IsTrue (IPAddress.TryParse ("0.0.0.0", out i), "#1");
552                 Assert.IsTrue (IPAddress.TryParse ("127.0.0.1", out i), "#2");
553                 Assert.IsFalse (IPAddress.TryParse ("www.mono-project.com", out i), "#3");
554                 Assert.IsTrue (IPAddress.TryParse ("0001:0002:0003:0004:0005:0006:0007:0008", out i), "#4");
555                 Assert.IsTrue (IPAddress.TryParse ("1:2:3:4:5:6:7:8", out i), "#5");
556                 Assert.IsTrue (IPAddress.TryParse ("1::8", out i), "#6");
557                 Assert.IsTrue (IPAddress.TryParse ("1::3:4:5:6:7:8", out i), "#7");
558                 Assert.IsFalse (IPAddress.TryParse ("1::2:3:4:5::6:7:8", out i), "#8"); // :: ::
559                 Assert.IsFalse (IPAddress.TryParse ("1::2:3:4:5:6:7:8", out i), "#9");
560                 Assert.IsFalse (IPAddress.TryParse ("1;2:3:4:5:6:7:8", out i), "#10"); // ;
561                 // FIXME:
562                 // Assert.IsFalse (IPAddress.TryParse ("1:2:3:4:5:6:7:8/10", out i), "#11"); // subnet
563         }
564
565         [Test]
566         public void TryParseOkV4 ()
567         {
568                 for (int i = 0; i < ipv4ParseOk.Length / 2; i++) {
569                         IPAddress ip;
570                         Assert.IsTrue (IPAddress.TryParse (ipv4ParseOk [i * 2], out ip), "#1:" + i);
571                         Assert.AreEqual (ipv4ParseOk [i * 2 + 1], ip.ToString (), "#2:" + i);
572                 }
573         }
574
575         [Test]
576         public void TryParseWrongV4 ()
577         {
578                 for (int i = 0; i < ipv4ParseWrong.Length; i++) {
579                         IPAddress ip;
580                         string ipAddress = ipv4ParseWrong [i];
581
582                         Assert.IsFalse (IPAddress.TryParse (ipAddress, out ip), "#1:" + i);
583                         Assert.IsNull (ip, "#2:" + i);
584                 }
585         }
586
587         [Test]
588         public void IsIPv6LinkLocal ()
589         {
590                 Assert.IsTrue (IPAddress.Parse ("FE80::1").IsIPv6LinkLocal, "#1");
591                 Assert.IsTrue (IPAddress.Parse ("FE81::1").IsIPv6LinkLocal, "#2");
592                 Assert.IsFalse (IPAddress.Parse ("FD81::1").IsIPv6LinkLocal, "#3");
593                 Assert.IsFalse (IPAddress.Parse ("FF80::1").IsIPv6LinkLocal, "#4");
594                 Assert.IsTrue (IPAddress.Parse ("FE91::1").IsIPv6LinkLocal, "#5");
595                 Assert.IsTrue (IPAddress.Parse ("FEA0::1").IsIPv6LinkLocal, "#6");
596                 Assert.IsFalse (IPAddress.Parse ("FEC0::1").IsIPv6LinkLocal, "#7");
597         }
598
599         [Test]
600         public void IsIPv6SiteLocal ()
601         {
602                 Assert.IsTrue (IPAddress.Parse ("FEC0::1").IsIPv6SiteLocal, "#1");
603                 Assert.IsTrue (IPAddress.Parse ("FEC1::1").IsIPv6SiteLocal, "#2");
604                 Assert.IsFalse (IPAddress.Parse ("FE81::1").IsIPv6SiteLocal, "#3");
605                 Assert.IsFalse (IPAddress.Parse ("FFC0::1").IsIPv6SiteLocal, "#4");
606                 Assert.IsTrue (IPAddress.Parse ("FED1::1").IsIPv6SiteLocal, "#5");
607                 Assert.IsTrue (IPAddress.Parse ("FEE1::1").IsIPv6SiteLocal, "#6");
608         }
609
610         [Test]
611         public void IsIPv6Multicast ()
612         {
613                 Assert.IsTrue (IPAddress.Parse ("FF00::1").IsIPv6Multicast, "#1");
614                 Assert.IsTrue (IPAddress.Parse ("FF01::1").IsIPv6Multicast, "#2");
615                 Assert.IsFalse (IPAddress.Parse ("FE00::1").IsIPv6Multicast, "#3");
616         }
617
618         [Test]
619         public void IsIPv6Teredo ()
620         {
621                 Assert.IsTrue (IPAddress.Parse ("2001::1").IsIPv6Teredo, "#1");
622                 Assert.IsFalse (IPAddress.Parse ("2002::1").IsIPv6Teredo, "#2");
623         }
624
625         [Test]
626         public void ParseWrongV6 ()
627         {
628                 if (!Socket.SupportsIPv6)
629                         Assert.Ignore ("IPv6 must be enabled in machine.config");
630
631                 for (int i = 0; i < ipv6ParseWrong.Length; i++) {
632                         string ipAddress = ipv6ParseWrong [i];
633
634                         try {
635                                 IPAddress ip = IPAddress.Parse (ipAddress);
636                                 Assert.Fail ("#1:" + i + " (" + ipAddress + ")");
637                         } catch (FormatException ex) {
638                                 Assert.AreEqual (typeof (FormatException), ex.GetType (), "#2:" + i);
639                                 Assert.IsNull (ex.InnerException, "#3:" + i);
640                                 Assert.IsNotNull (ex.Message, "#4:" + i);
641                         }
642                 }
643         }
644
645 #if NET_4_5
646
647         [Test]
648         public void MapToIPv6 ()
649         {
650                 for (int i = 0; i < ipv4ParseOk.Length / 2; i++) {
651                         IPAddress v4 = IPAddress.Parse (ipv4ParseOk [i * 2]);
652                         byte [] v4bytes = v4.GetAddressBytes ();
653                         IPAddress v6 = v4.MapToIPv6 ();
654                         byte [] v6bytes = v6.GetAddressBytes ();
655                         IPAddress v4back = v6.MapToIPv4 ();
656
657                         Assert.IsTrue (StartsWith (v6bytes, ipv4MappedIPv6Prefix), "MapToIPv6 #" + i + ".1");
658                         Assert.IsTrue (v6bytes [12] == v4bytes [0], "MapToIPv6 #" + i + ".2");
659                         Assert.IsTrue (v6bytes [13] == v4bytes [1], "MapToIPv6 #" + i + ".3");
660                         Assert.IsTrue (v6bytes [14] == v4bytes [2], "MapToIPv6 #" + i + ".4");
661                         Assert.IsTrue (v6bytes [15] == v4bytes [3], "MapToIPv6 #" + i + ".5");
662                         Assert.IsTrue (v4.Equals (v4back), "MapToIPv4 #" + i);
663                 }
664
665                 //TODO: Test using MapToIPv4/6 with anything other than IPv4/6 addresses.
666                 //Currently it is not possible to do with the IPAddress implementation.
667         }
668
669         static bool StartsWith (byte [] a, byte [] b)
670         {
671                 if (a.Length < b.Length)
672                         return false;
673                 for (int i = 0; i < b.Length; i++)
674                 {
675                         if (a [i] != b [i])
676                                 return false;
677                 }
678                 return true;
679         }
680
681 #endif
682
683         [Test]
684         public void EqualsFromBytes ()
685         {
686                 for (int i = 0; i < ipv4ParseOk.Length / 2; i++) {
687                         IPAddress ip = IPAddress.Parse (ipv4ParseOk [i * 2]);
688                         IPAddress ipFromBytes = new IPAddress (ip.GetAddressBytes ());
689                         Assert.IsTrue (ip.Equals (ipFromBytes), "EqualsFromBytes #" + i);
690                 }
691
692         }
693
694 }
695 }
696