Coder Social home page Coder Social logo

ipaddressrange's Introduction

IPAddressRange Class Library tests NuGet Package

This library allows you to parse range of IP address string such as "192.168.0.0/24" and "192.168.0.0/255.255.255.0" and "192.168.0.0-192.168.0.255", and can contains check. This library supports both IPv4 and IPv6.

Example

using NetTools;
...
// rangeA.Begin is "192.168.0.0", and rangeA.End is "192.168.0.255".
var rangeA = IPAddressRange.Parse("192.168.0.0/255.255.255.0");
rangeA.Contains(IPAddress.Parse("192.168.0.34")); // is True.
rangeA.Contains(IPAddress.Parse("192.168.10.1")); // is False.
rangeA.ToCidrString(); // is 192.168.0.0/24

// rangeB.Begin is "192.168.0.10", and rangeB.End is "192.168.10.20".
var rangeB1 = IPAddressRange.Parse("192.168.0.10 - 192.168.10.20");
rangeB1.Contains(IPAddress.Parse("192.168.3.45")); // is True.
rangeB1.Contains(IPAddress.Parse("192.168.0.9")); // is False.

// Support shortcut range description. 
// ("192.168.10.10-20" means range of begin:192.168.10.10 to end:192.168.10.20.)
var rangeB2 = IPAddressRange.Parse("192.168.10.10-20");

// Support CIDR expression and IPv6.
var rangeC = IPAddressRange.Parse("fe80::/10"); 
rangeC.Contains(IPAddress.Parse("fe80::d503:4ee:3882:c586%3")); // is True.
rangeC.Contains(IPAddress.Parse("::1")); // is False.

// "Contains()" method also support IPAddressRange argument.
var rangeD1 = IPAddressRange.Parse("192.168.0.0/16");
var rangeD2 = IPAddressRange.Parse("192.168.10.0/24");
rangeD1.Contains(rangeD2); // is True.

// IEnumerable<IPAddress> support, it's lazy evaluation.
foreach (var ip in IPAddressRange.Parse("192.168.0.1/23"))
{
    Console.WriteLine(ip);
}

// You can use LINQ via "AsEnumerable()" method.
var longValues = IPAddressRange.Parse("192.168.0.1/23")
  .AsEnumerable()
  .Select(ip => BitConvert.ToInt32(ip.GetAddressBytes(), 0))
  .Select(adr => adr.ToString("X8"));
Console.WriteLine(string.Join(",", longValues);

// Constructors from IPAddress objects.
var ipBegin = IPAddress.Parse("192.168.0.1");
var ipEnd = IPAddress.Parse("192.168.0.128");
var ipSubnet = IPAddress.Parse("255.255.255.0");

var rangeE = new IPAddressRange(); // This means "0.0.0.0/0".
var rangeF = new IPAddressRange(ipBegin, ipEnd);
var rangeG = new IPAddressRange(ipBegin, maskLength: 24);
var rangeH = new IPAddressRange(ipBegin, IPAddressRange.SubnetMaskLength(ipSubnet));

// Calculates Cidr subnets
var rangeI = IPAddressRange.Parse("192.168.0.0-192.168.0.254");
rangeI.ToCidrString();  // is 192.168.0.0/24

Release Note

The release notes is here.

License

Mozilla Public License 2.0

ipaddressrange's People

Contributors

dependabot[bot] avatar gregmac avatar jsakamoto avatar kamilzm avatar konrad-kruczynski avatar llcorvinsll avatar m-zuber avatar menur avatar qu3uk avatar richardlawley avatar sudoudaisuke avatar tetyys avatar vkoppaka avatar zanemayo avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

ipaddressrange's Issues

Cant parse example string

Installed IPAddressRange v. 3.2.0 via NuGet

In the comments of your source file: https://github.com/jsakamoto/ipaddressrange/blob/master/IPAddressRange/IPAddressRange.cs

We see such a comment:

// Pattern 3. Begin end range: "169.258.0.0-169.258.0.255", "fe80::1%23-fe80::ff%23"

But Your lib fails to parse this very example string!

using NetTools;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ConsoleApp2
{
    class Program
    {
        static void Main(string[] args)
        {    
            string ipstring = "169.258.0.0-169.258.0.255";
            IPAddressRange iprange = IPAddressRange.Parse(ipstring);
            Console.WriteLine(iprange.ToString());
            Console.ReadKey();
        }
    }
}

This throws! System.FormatException And TryParse returns false

[Question] How to find usable IPs?

                var range = IPAddressRange.Parse("192.168.1.100/255.255.255.0");
                IPStartBox.Text = range.Begin.ToString(); // returns 192.168.1.0
                IPEndBox.Text = range.End.ToString(); // 192.168.1.255

I need to return first and last usable IP, which should be 192.168.1.1 and 192.168.1.254.
Is this possible?

Parse fails in some situations

var testIp = IPAddressRange.Parse("192.168.009.215");

This fails with a "System.FormatException: 'An invalid IP address was specified.'" error.

Seems the issue is with IPAddress.Parse() in .NET treating leading zeros as Octal identifiers.

At least for IPv4, you can use the following to clean prior to parsing...

ipString = Regex.Replace(ipString, "0*([0-9]+)", "${1}");

Cannot parse ARIN IPv6 IP addresses

Unfortunately, the ARIN IP range database from https://www.arin.net/ contains somewhat invalid IPv6 addresses in almost all their IPv6 IP ranges.

Below are a few examples of individual IPv6 addresses. Each example below contains the start ip of an IP range:

2001:49D0:140:
2001:504:0:5:
2001:4978:100:

The reason why these IP addresses are invalid is that they end in a colon instead of a double colon.

If you can change the library to handle this type of address as well I would appreciate it.

Thanks!

Caclulate correct usable addresses in a range

CIDR ranges /32, and /31 when given to the library to parse and then querying range.Usable, I get back a (0) where the .FirstUsable and .LastUsable properties are correctly showing a valid IP Address.

image

[Breaking Change] Truncate .NET4.0 support for improving JSON serialization by JSON.NET

Problem

An IPAddressRange after v.1.4 object cann't serialize to/deserialize from JSON text by using JSON.NET.

Details

JSON.NET detect IEnumerable<IPAddress> interface prior to ISerializable.
At a result, JSON.NET try to serialize IPAddressRange as array, such as "["192.168.0.1", "192.168.0.2"]".
This is unexpected behavior. (We expect "{"Begin":"192.168.0.1", "End:"192.168.0.2"}" style JSON text that is same with DataContractJsonSerializer.)
In addition, JSON serialization with JSON.NET crash due to IPAddress cann't serialize by JSON.NET.

Work around

To avoid this JSON.NET behavior, IPAddressRange should implement more high priority interface than IEnumerable<T> in JSON.NET.
Such interfaces include the following.

  • IDictionary
  • IDictionary<TKey,TVal>
  • IReadOnlyDictionary<TKey,TVal>
    But, when IPAddressRange implement IDictionay or IDictionary<TKey,TVal>, serialization by DataContractJsonSerializer was broken.
    (Implementation of DataContractJsonSerializer is specialized for IDictionay and IDictionary<TKey,TVal>)

So there is no way without implement IReadOnlyDictionary<TKey,TVal>.

Trade off

IReadOnlyDictionary<TKey,TVal> interface doesn't exist in .NET Framework v.4.0 or before.

In order to give priority to supporting serialization by JSON.NET, I had to truncate the support for .NET Framework 4.0.
(.NET Standard 1.4 support IReadOnlyDictionary<TKey,TVal>, therefore there is no problem on .NET Core appliction.)

Binary level compatiblity

There will be no problem even if IPAddressRange.dll is replaced with the latest version.

Source code level compatiblity

You cann't apply LINQ extension methods directory to IPAddressRange object like this:

var texts = IPAddressRange.Parse("192.168.0.0/24")
    .Select(ip => ip.ToString());

Because IPAddressRange implement two types of IEnumerable<T> (IEnumerable<IPaddress> and IEnumerable<KeyValuePair<K,V>>).
It cause ambiguous compile error.

To avoid this error, you should use "AsEnumerable()" method before IEnumerable<IPAddressRange> access.

var texts = IPAddressRange.Parse("192.168.0.0/24")
    .AsEnumerable() // insert this
    .Select(ip => ip.ToString());

Plan

I'm considering to release this change as IPAddressRange ver.2.0 after a few days or around a week.

Comparison performance leaks in Contains

NetTools.Bits static class is nice example of LINQ usage, but it's really slow.

Possible improvement ideas:

  1. You can get like 33% less time spent on this when you use for cycles.
  2. You can even optimize IPv6 comparison for IPv4ToIPv6 mapped addresses to reduce number of iterations from 16 to 4.
  3. You can completely avoid some comparisons for IPv6 by checking IsIPv4MappedToIPv6
  4. For the IPv4 address family you can use IPAddress.GetHashCode() which is 32-bit number as ip address. Casting hash code to uint would be still faster than the byte array comparison.

.Contains broken when using Mask Length constuctor

This was broken in 4.1.0 by 4f75699. Most constructors had the following line added:

Operator = RangeOperatorFactory.Create(this);

This was missed in the mask length constructor: new IPAddressRange(IPAddress.Parse("10.0.0.0", 24))

This causes .Contains to throw NullReferenceException:

var range = new IPAddressRange(IPAddress.Parse("192.168.0.80"), 24);
range.Contains(range.Begin).Is(true);         // throws NullReferenceException

Signed version of the NuGet package

Hi,

Can you please add a IPAddressRange.Signed version of the NuGet package or sign the dll in the existing package? We want to use this NuGet package in several projects that is signed. I would really like to avoid having to create a locally signed version myself so I hope you will be able to do this

Parse / TryParse

The addition of such functionality would add a lot to this package

Parsing performance

Hi, thanks for the great lib, the ONLY for the ranges!!! Really really useful.

The IP ranges mught be used on some really hot paths in the app, so, did you ever consider replacing Regex.Match with something more robust & fast?

Signed package for v.2.1.1 and newer

Hi,

Any chance you can create a signed package for v.2.1.1?
Would also be nice if you can automate this so that every new version will also have a new signed package

Regards,
PashCracken

IPAddress .MapToIPv6() result doesn't parse.

I have an IPAdress object containing "10.0.0.203" if i call MapToIpv6() I get "::ffff:10.0.0.203"

If I then try and pass that in to IPAddressRange.Parse i get an exception ""Unknown IP range string."".

Any clues?

Getting string[] from IPAddressRange

Any better way of doing this?

private string[] GetIPsFromRange(string ipFrom, string ipTo)
{
	var range = new IPAddressRange(IPAddress.Parse(ipFrom), IPAddress.Parse(ipTo));
	var result = new List<string>(255); // could use range.Count here...
	foreach (var ip in range)
	{
		result.Add(ip.ToString());
	}
	return result.ToArray();
}

`TryParse` static method should catch all types of exception? or not?

Hi everyone, and contributors of this library:

Few days ago, @zijianhuang said "TryParse static method should not catch all types of exception." with pull request #23 that contains commit:e3a7917.

His comment is:

For the sake of defensive programming and safety, library code should not catch "all of types (any Exceptions)". Catching general exception should be the job of the application and CLR. Major platforms like WinForms, WPF, WCF and MVC etc. have built-in mechanism of catching uncaught exceptions. It is the responsibility of the application developers to utilize those mechanisms built-in.

(Source: Some slight QA fixes in 2 commits #23)

I partially agree his opinion. I always feel it is "foolish" that catching all types without much thought.

But, another point of view, we had an experience that ran into really unexpected type of exception caused by the mistake of my implementation. ( See also #7 and #5 ).

What should I do?

License question

Thank you for writing this and sharing it.

We are interested in using it in a commercial setting. However, the project doesn't seem to include a license. Can we use it? Are there any restrictions?

TryParse throws exception if null is passed

I don't think TryParse should be throwing an exception for any type of input. It's currently limited to FormatException and I'm not sure why to not just catch any Exception and return false.

Cidr subnets not working

Greetings,

Calculating the Cidr subnets from an IP range doesn't seem to work. Error: 192.168.0.0-192.168.0.254 is not a CIDR Subnet.

// Calculates Cidr subnets
var rangeI = IPAddressRange.Parse("192.168.0.0-192.168.0.254");
rangeI.ToCidrString(); // is 192.168.0.0/24

Range overlaps

Would you consider adding a feature to allow another IPAddressRange in .Contains()?
So you can do something like
var overlaps = range1.Contains(range2)
This would be useful to check for subnet ovelaps...

Public setter property Begin and End dose not change private member "IRangeOperator Operator"

Public setter property Begin and End dose not change private member "IRangeOperator Operator". The sample code is this.

var ipAddressRange1 = IPAddress(IPAdress.Parse(10.10.0.0), IPAdress.Parse(10.10.255.255));
var result1 = ipAddressRange1.Contains(IPAdress.Parse("10.10.0.1")); // I think this result is true, IPAddressRange 4.1.2 returns true

var ipAddressRange2 = IPAddress { Begin = IPAdress.Parse(10.10.0.0), End = IPAdress.Parse(10.10.255.255) };
var result2 = ipAddressRange2.Contains(IPAdress.Parse("10.10.0.1")); // I think this result is true, but IPAddressRange 4.1.2 returns false

Feature request: Wildcard support & multiple ranges

First of all, thanks for this great library. I haven't had a chance to use it but it looks great and covers many use-cases that I'm looking for!

I have a couple of feature requests that would compliment the current range syntax (e.g. 255.10.8.0-23) that is permitted by the library.

  1. Allow wildcard characters.
    For example 10.0.1.* which would be equivalent to 10.0.1.0-255.
  2. Have a way to parse a string into multiple ranges.
    For example 10.0.80-93.0-100. This would produce a list of 14 IP ranges.

I would be happy to look into opening a PR for this if you think either of these features are worthwhile.

Range.Contains regression 4.0.0 to 4.1.0

Hi,
First thanks for the good work.
After updating to 4.1.0, we noticed a regression in our application. I managed to narrow it down to behvaior change, either in pasing or contains method. Following test (that can be added in IPAddressRangeTest.cs) works in 4.0.0 but not in 4.1.0:

[TestMethod]
public void Is_Local_In_Range()
{
    var range = IPAddressRange.Parse("::/0");
    range.Contains(IPAddress.Parse("::1")).IsTrue();
}

I did not analyze further than this though. We downgraded to 4.0.0 as of now, so no emergency on that side.
Thanks for the help!

Lots of dependencies

Trying to NuGet your library into my .NET 4.6.2 project, there are tons of dependencies it tries to install:

image

Most likely this is because your project targets .NET Standard and it has to close the gaps from .NET 4.6.2 to .NET Standard.

Since your library effectively seems to consist of only two files (Bits.cs and IPAddressRange.cs) I feel that this is way too much for my project to justify adding so many dependencies.

My question:

Beside directly using the two sources files, is there any other NuGet solution to still get your library and benefit from updates, without adding all those dependencies?

Wrong Ip tryparse

Is it normal that ip
0037.15.0.1 parsing to 31.15.0.1
17.15.011 parsing to 17.15.0.9

should there be an exception?

NetTools namespace not available

I just installed thispackage since it was recommended in Stackoverflow. and it looks really good.

I installed both signed version and the default. however, after installing, I can not use NetTools namespace, it says is not available. The reference is correct.

My project is a web forms app on framework 4.5.1

any suggestion on which version could I use to make it work?

invalid CIDR

What is the desired action if someone passes in the following ipcidr: 128.139.251.57/3212?

The first Regex matches, but then an IndexOutOfRangeException is thrown when trying to build the BitMask.
If we where to make the first Regex stricter, there would still be a problem as this string also passes the Regex for a netmask.

-as an aside: should it be considered to let the TryParse catch more than just FormatException?

.Count() is dangerous

Not really an IPAddressRange issue, but maybe an IEnumerable issue.

But if you use IPAddressRange.Count() on a large list of IPs, it will perform bad and take minutes.

for example:
IPAddressRange.Parse("0.0.0.0/1").Count()

or even worse:
IPAddressRange.Parse("0::0/0").Count()

3.x release notes?

Where can I find release notes for 3.x? Are there any breaking changes?

UWP /Winrt port

tried to port your code to UWP (in Q&D)
missing SerializationInfo and further classes

Incorrect results when Parse (or TryParse)

Incorrect results and false positive responses when passing wrong IP addresses. For example:

IPAddressRange.TryParse("192. 168.1.0 - 192. 168.1.0", out rr);
IPAddressRange.TryParse("192.1.1 - 192.1.1", out rr);

var aa1 = IPAddressRange.Parse("192.168.1");
var aa2 = IPAddressRange.Parse("192.168.1111");

Weird parsing for weird inputs

I noticed a security issue in our product that when some "edge case" ip address is entered it is saved via the repository although it shouldn't pass validation. I initially tought that the TryParse does a full strict validation of an IP address but then I experienced this weird behavior.

IPAddress.TryParse(ipAddress, out var validatedIP)

input values:
ipAddress = 0.320

output values:
validatedIP = {0.0.1.64}

This might have something to do with conversions to binary and back

Thank you

I just want to thank you for creating and maintaining this library ๐Ÿ™.
I've built and released an ASP.NET Core library for authenticating requests based on IP using your library:

https://github.com/abdusco/Lib.AspNetCore.Auth.Intranet

If I'm not mistaken, I need to use Mozilla Public License Version 2.0 (and I have), as your license requires dependent projects to also adopt the same license. Please let me know if it needs to be changed.

When Parsing a IPAddressRange the network and broadcast Addresses should not be included..

Hi,

I saw that wen you are returning an IPAddressRange, you guys are including the network and broadcast addresses.
I don't know if this is on purpose, but these addresses are not really usable..

Can you modify this so that they are not included?

192.168.1.0 - 192.168.1.255 shoud rather be 192.168.1.1 - 192.168.1.254.
We now have to add an extra if to skip the network and broadcast addresses.

Maybe it is an idea to add a for example IPAddressRange.ToUsableHostIPRange() -> see also https://www.calculator.net/ip-subnet-calculator.html .
image

Bits static class reverses LE and GE

It looks like the LE and GE operations are reversed in the Bits class.

[Theory]
[InlineData("0.0.0.0", "255.255.255.254")]
[InlineData("192.168.10.0", "192.168.10.254")]
[InlineData("192.168.10.0", "192.168.11.254")]
[InlineData("192.168.10.0", "192.168.11.255")]
public void Bits_comparisons_are_backwards(string start, string end)
{
    var startBytes = System.Net.IPAddress.Parse(start).GetAddressBytes();
    var endBytes = System.Net.IPAddress.Parse(end).GetAddressBytes();

    Assert.False(NetTools.Bits.LE(startBytes, endBytes));
    Assert.True(NetTools.Bits.GE(startBytes, endBytes));
}

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.