System.Net.IPAddress constructor still not fixed?

  • Thread starter Thread starter Guest
  • Start date Start date
G

Guest

This code throws a System.ArgumentException, why?

Imports System.Net
Dim addressBytes As Byte() = IPAddress.Parse("127.0.0.1").GetAddressBytes()
Dim objIPAddress As IPAddress = New IPAddress(addressBytes)

The constructor for this class in .NET FW 1.0 was terrible, does the new one
in 1.1 even work? The byte array returned by GetAddressBytes looks like this
(which seems intuitive):
New Byte() {127, 0, 0, 1}

Of course, this array has Length 4 and I suppose that is the cause of the
ArgumentException. According to the documentation the byte array must be of
Length 16 (?), but I can find no examples of what a valid byte array for
calling this constructor looks like.

Can someone shed some light on this? What am I missing?
 
Mathias said:
This code throws a System.ArgumentException, why?

Imports System.Net
Dim addressBytes As Byte() =
IPAddress.Parse("127.0.0.1").GetAddressBytes()
Dim objIPAddress As IPAddress = New IPAddress(addressBytes)

The constructor for this class in .NET FW 1.0 was terrible, does the new
one
in 1.1 even work? The byte array returned by GetAddressBytes looks like
this
(which seems intuitive):
New Byte() {127, 0, 0, 1}

Of course, this array has Length 4 and I suppose that is the cause of the
ArgumentException. According to the documentation the byte array must be
of
Length 16 (?), but I can find no examples of what a valid byte array for
calling this constructor looks like.

Can someone shed some light on this? What am I missing?

That constructor is for an IP6 address which is 16 bytes, and doesn't work
for an IP4 address.

You can use IPAddress(long) to set an IP4 address from the bytes

Dim b() As Byte = {127, 0, 0, 1}
Dim addr As New Net.IPAddress(CLng(BitConverter.ToInt32(b, 0)))
Console.WriteLine(addr.ToString())

David
 
That constructor is for an IP6 address which is 16 bytes, and doesn't work
for an IP4 address.

You can use IPAddress(long) to set an IP4 address from the bytes

Dim b() As Byte = {127, 0, 0, 1}
Dim addr As New Net.IPAddress(CLng(BitConverter.ToInt32(b, 0)))
Console.WriteLine(addr.ToString())

Thank you for your answer. I'm going to rant a little here. This is not to
critique you personally who actually just wanted to help.

The current interface is rude when it comes to creating instances and has
been since it was first released. A client of a class should not have to
worry about internal representations of IP addresses like this. It breaks
encapsulation. Also, if the class is designed to represent both the old an
new type of IPAdresses, this should be documented clearly. If constructors or
other methods "assume" either type of representation, this should also be
both documented well and, more importantly, be visible by using self
documenting member names whenever possible.

Possible improvements:
- Modify the byte array construtor to accept byte arrays of length 4 and
treat this as an IP4 address internally. Both length 16 and length 4 should
be valid if the class is designed to represent both IP4 and IP6. If it is
valid enough to return from GetAddressBytes(), then it should be valid to
create an instance with. This is just common sense. Anything else is
ridiculous and is not ok in any OOP lecture.

- Add more static/shared factory methods or add more constructors so callers
don't have to worry about casting longs and whatnot. Parse() is good, but not
enough. For instance, if instance creating code accepts only a specialized
parameters to create a special type of instance it probably should not be a
constructor. For instance, the current implementation of the 'New(b() As
Byte' constructor should have been designed as a shared/static member called
'CreateIP6Address(b() As Byte) As IPAddress' since it can not create all
valid instances of the class and does not accept all valid input. A version
for the IP4 address could have been added as well. Both methods can then have
strong type checks for either address representation parameters.

- The Long constructor hurts my eye, but I can understand why it can't be
dropped. It probably would not hurt my eye if there were more and better ways
to create instances of this class and I did not have to use it.

If somebody who manages the framework teams reads this I hope you managers
give your FW designers more chance to do design review for the next release
of the framework. Two mistakes in a row is probably a systematic problem.
Make changes if you have to. Don't make the same mistake three times. We have
to live with what you guys ship out here for a long time, but you guys know
that already.

Last, the .NET FW is a great framework and that's part of why I bother to
write this in the first place. It just irritates me when the few things that
are bad does not get fixed when there's no reason they can't get fixed.
 
Back
Top