예제 #1
0
파일: Lease.cs 프로젝트: ydk2/DnsServer
        internal Lease(BinaryReader bR)
        {
            switch (bR.ReadByte())
            {
            case 1:
                _type             = (LeaseType)bR.ReadByte();
                _clientIdentifier = DhcpOption.Parse(bR.BaseStream) as ClientIdentifierOption;
                _clientIdentifier.ParseOptionValue();

                _hostName = bR.ReadShortString();
                if (_hostName == "")
                {
                    _hostName = null;
                }

                _hardwareAddress = bR.ReadBuffer();
                _address         = IPAddressExtension.Parse(bR);
                _leaseObtained   = bR.ReadDate();
                _leaseExpires    = bR.ReadDate();
                break;

            default:
                throw new InvalidDataException("Lease data format version not supported.");
            }
        }
예제 #2
0
            public StatCounter(BinaryReader bR)
            {
                if (Encoding.ASCII.GetString(bR.ReadBytes(2)) != "SC") //format
                {
                    throw new InvalidDataException("StatCounter format is invalid.");
                }

                byte version = bR.ReadByte();

                switch (version)
                {
                case 1:
                    _totalQueries       = bR.ReadInt32();
                    _totalNoError       = bR.ReadInt32();
                    _totalServerFailure = bR.ReadInt32();
                    _totalNameError     = bR.ReadInt32();
                    _totalRefused       = bR.ReadInt32();
                    _totalBlocked       = bR.ReadInt32();

                    {
                        int count = bR.ReadInt32();
                        for (int i = 0; i < count; i++)
                        {
                            _queryDomains.TryAdd(bR.ReadShortString(), new Counter(bR.ReadInt32()));
                        }
                    }

                    {
                        int count = bR.ReadInt32();
                        for (int i = 0; i < count; i++)
                        {
                            _queryBlockedDomains.TryAdd(bR.ReadShortString(), new Counter(bR.ReadInt32()));
                        }
                    }

                    {
                        int count = bR.ReadInt32();
                        for (int i = 0; i < count; i++)
                        {
                            _queryTypes.TryAdd((DnsResourceRecordType)bR.ReadUInt16(), new Counter(bR.ReadInt32()));
                        }
                    }

                    {
                        int count = bR.ReadInt32();
                        for (int i = 0; i < count; i++)
                        {
                            _clientIpAddresses.TryAdd(IPAddressExtension.Parse(bR), new Counter(bR.ReadInt32()));
                        }
                    }
                    break;

                default:
                    throw new InvalidDataException("StatCounter version not supported.");
                }

                _locked = true;
            }
예제 #3
0
 /// <summary>
 /// Creates a new account data container class instance
 /// </summary>
 public Account(BinaryReader binaryReader)
 {
     ID               = binaryReader.ReadInt64();
     IsBlocked        = binaryReader.ReadBoolean();
     Level            = binaryReader.ReadByte();
     Name             = new Username(binaryReader);
     Passhash         = new Passhash(binaryReader);
     EmailAddress     = new EmailAddress(binaryReader);
     AccessToken      = new Token(binaryReader);
     LastUseIpAddress = IPAddressExtension.FromBytes(binaryReader);
 }
예제 #4
0
        public void ChangeNetwork(IPAddress startingAddress, IPAddress endingAddress, IPAddress subnetMask)
        {
            if (startingAddress.AddressFamily != AddressFamily.InterNetwork)
            {
                throw new ArgumentException("Address family not supported.", nameof(startingAddress));
            }

            if (endingAddress.AddressFamily != AddressFamily.InterNetwork)
            {
                throw new ArgumentException("Address family not supported.", nameof(endingAddress));
            }

            if (subnetMask.AddressFamily != AddressFamily.InterNetwork)
            {
                throw new ArgumentException("Address family not supported.", nameof(subnetMask));
            }

            uint startingAddressNumber = startingAddress.ConvertIpToNumber();
            uint endingAddressNumber   = endingAddress.ConvertIpToNumber();

            if (startingAddressNumber >= endingAddressNumber)
            {
                throw new ArgumentException("Ending address must be greater than starting address.");
            }

            _startingAddress = startingAddress;
            _endingAddress   = endingAddress;
            _subnetMask      = subnetMask;

            //compute other parameters
            uint subnetMaskNumber       = _subnetMask.ConvertIpToNumber();
            uint networkAddressNumber   = startingAddressNumber & subnetMaskNumber;
            uint broadcastAddressNumber = networkAddressNumber | ~subnetMaskNumber;

            if (networkAddressNumber == startingAddressNumber)
            {
                throw new ArgumentException("Starting address cannot be same as the network address.");
            }

            if (broadcastAddressNumber == endingAddressNumber)
            {
                throw new ArgumentException("Ending address cannot be same as the broadcast address.");
            }

            _networkAddress   = IPAddressExtension.ConvertNumberToIp(networkAddressNumber);
            _broadcastAddress = IPAddressExtension.ConvertNumberToIp(broadcastAddressNumber);
            _reverseZone      = Zone.GetReverseZone(_networkAddress, _subnetMask);

            lock (_lastAddressOfferedLock)
            {
                _lastAddressOffered = IPAddressExtension.ConvertNumberToIp(startingAddressNumber - 1u);
            }
        }
예제 #5
0
        public DnsProvider(BinaryReader bR)
        {
            this.Name      = bR.ReadShortString();
            this.Addresses = new List <IPAddress>();

            int count = bR.ReadInt32();

            for (int i = 0; i < count; i++)
            {
                this.Addresses.Add(IPAddressExtension.Parse(bR));
            }
        }
            public Route(Stream s)
            {
                int subnetMaskWidth = s.ReadByte();

                if (subnetMaskWidth < 0)
                {
                    throw new EndOfStreamException();
                }

                byte[] destinationBuffer = new byte[4];
                s.ReadBytes(destinationBuffer, 0, Convert.ToInt32(Math.Ceiling(Convert.ToDecimal(subnetMaskWidth) / 8)));
                _destination = new IPAddress(destinationBuffer);

                _subnetMask = IPAddressExtension.GetSubnetMask(subnetMaskWidth);

                _router = new IPAddress(s.ReadBytes(4));
            }
예제 #7
0
파일: Lease.cs 프로젝트: Cossey/DnsServer
        internal Lease(BinaryReader bR)
        {
            byte version = bR.ReadByte();

            switch (version)
            {
            case 1:
            case 2:
                _type             = (LeaseType)bR.ReadByte();
                _clientIdentifier = DhcpOption.Parse(bR.BaseStream) as ClientIdentifierOption;
                _clientIdentifier.ParseOptionValue();

                _hostName = bR.ReadShortString();
                if (string.IsNullOrWhiteSpace(_hostName))
                {
                    _hostName = null;
                }

                _hardwareAddress = bR.ReadBuffer();
                _address         = IPAddressExtension.Parse(bR);

                if (version >= 2)
                {
                    _comments = bR.ReadShortString();
                    if (string.IsNullOrWhiteSpace(_comments))
                    {
                        _comments = null;
                    }
                }

                _leaseObtained = bR.ReadDateTime();
                _leaseExpires  = bR.ReadDateTime();
                break;

            default:
                throw new InvalidDataException("Lease data format version not supported.");
            }
        }
        public void ByteConsversion(IPAddress value)
        {
            var bytes    = new byte[IPAddressExtension.ByteSize];
            var newValue = value;

            using (var memoryStream = new MemoryStream(bytes))
            {
                using (var binaryWriter = new BinaryWriter(memoryStream))
                {
                    value.ToBytes(binaryWriter);
                    Assert.AreEqual(IPAddressExtension.ByteSize, memoryStream.Position);

                    binaryWriter.Seek(0, SeekOrigin.Begin);

                    using (var binaryReader = new BinaryReader(memoryStream))
                    {
                        newValue = IPAddressExtension.FromBytes(binaryReader);
                        Assert.AreEqual(IPAddressExtension.ByteSize, memoryStream.Position);
                    }
                }
            }

            Assert.AreEqual(value, newValue);
        }
예제 #9
0
        public Scope(BinaryReader bR)
        {
            if (Encoding.ASCII.GetString(bR.ReadBytes(2)) != "SC")
            {
                throw new InvalidDataException("DhcpServer scope file format is invalid.");
            }

            switch (bR.ReadByte())
            {
            case 1:
                _name    = bR.ReadShortString();
                _enabled = bR.ReadBoolean();

                ChangeNetwork(IPAddressExtension.Parse(bR), IPAddressExtension.Parse(bR), IPAddressExtension.Parse(bR));

                _leaseTimeDays    = bR.ReadUInt16();
                _leaseTimeHours   = bR.ReadByte();
                _leaseTimeMinutes = bR.ReadByte();

                _offerDelayTime = bR.ReadUInt16();

                _domainName = bR.ReadShortString();
                if (string.IsNullOrWhiteSpace(_domainName))
                {
                    _domainName = null;
                }

                _dnsTtl = bR.ReadUInt32();

                _routerAddress = IPAddressExtension.Parse(bR);
                if (_routerAddress.Equals(IPAddress.Any))
                {
                    _routerAddress = null;
                }

                {
                    int count = bR.ReadByte();
                    if (count > 0)
                    {
                        if (count == 255)
                        {
                            _useThisDnsServer = true;
                            FindThisDnsServerAddress();
                        }
                        else
                        {
                            _dnsServers = new IPAddress[count];

                            for (int i = 0; i < count; i++)
                            {
                                _dnsServers[i] = IPAddressExtension.Parse(bR);
                            }
                        }
                    }
                }

                {
                    int count = bR.ReadByte();
                    if (count > 0)
                    {
                        _winsServers = new IPAddress[count];

                        for (int i = 0; i < count; i++)
                        {
                            _winsServers[i] = IPAddressExtension.Parse(bR);
                        }
                    }
                }

                {
                    int count = bR.ReadByte();
                    if (count > 0)
                    {
                        _ntpServers = new IPAddress[count];

                        for (int i = 0; i < count; i++)
                        {
                            _ntpServers[i] = IPAddressExtension.Parse(bR);
                        }
                    }
                }

                {
                    int count = bR.ReadByte();
                    if (count > 0)
                    {
                        _staticRoutes = new ClasslessStaticRouteOption.Route[count];

                        for (int i = 0; i < count; i++)
                        {
                            _staticRoutes[i] = new ClasslessStaticRouteOption.Route(bR.BaseStream);
                        }
                    }
                }

                {
                    int count = bR.ReadByte();
                    if (count > 0)
                    {
                        _exclusions = new Exclusion[count];

                        for (int i = 0; i < count; i++)
                        {
                            _exclusions[i] = new Exclusion(IPAddressExtension.Parse(bR), IPAddressExtension.Parse(bR));
                        }
                    }
                }

                {
                    int count = bR.ReadInt32();
                    if (count > 0)
                    {
                        _reservedLeases = new Lease[count];

                        for (int i = 0; i < count; i++)
                        {
                            _reservedLeases[i] = new Lease(bR);
                        }
                    }

                    _allowOnlyReservedLeases = bR.ReadBoolean();
                }

                {
                    int count = bR.ReadInt32();
                    if (count > 0)
                    {
                        for (int i = 0; i < count; i++)
                        {
                            Lease lease = new Lease(bR);

                            _leases.TryAdd(lease.ClientIdentifier, lease);
                        }
                    }
                }

                break;

            default:
                throw new InvalidDataException("Scope data format version not supported.");
            }
        }
예제 #10
0
        internal Lease GetOffer(DhcpMessage request)
        {
            if (_leases.TryGetValue(request.ClientIdentifier, out Lease existingLease))
            {
                //lease already exists
                return(existingLease);
            }

            if (_reservedLeases != null)
            {
                ClientIdentifierOption clientIdentifierKey = new ClientIdentifierOption(1, request.ClientHardwareAddress);
                foreach (Lease reservedLease in _reservedLeases)
                {
                    if (reservedLease.ClientIdentifier.Equals(clientIdentifierKey))
                    {
                        //reserved address exists
                        IPAddress reservedLeaseAddress = reservedLease.Address;

                        if (!IsAddressAvailable(ref reservedLeaseAddress))
                        {
                            break; //reserved lease address is already allocated so ignore reserved lease
                        }
                        Lease reservedOffer = new Lease(LeaseType.Reserved, request.ClientIdentifier, request.HostName?.HostName, request.ClientHardwareAddress, reservedLease.Address, null, GetLeaseTime());

                        return(_offers.AddOrUpdate(request.ClientIdentifier, reservedOffer, delegate(ClientIdentifierOption key, Lease existingValue)
                        {
                            return reservedOffer;
                        }));
                    }
                }
            }

            if (_allowOnlyReservedLeases)
            {
                throw new DhcpServerException("DHCP Server failed to offer IP address to " + request.GetClientFullIdentifier() + ": scope allows only reserved lease allocations.");
            }

            Lease dummyOffer    = new Lease(LeaseType.None, null, null, null, null, null, 0);
            Lease existingOffer = _offers.GetOrAdd(request.ClientIdentifier, dummyOffer);

            if (dummyOffer != existingOffer)
            {
                if (existingOffer.Type == LeaseType.None)
                {
                    return(null); //dummy offer so another thread is handling offer; do nothing
                }
                //offer already exists
                existingOffer.ExtendLease(GetLeaseTime());

                return(existingOffer);
            }

            //find offer ip address
            IPAddress offerAddress = null;

            if (request.RequestedIpAddress != null)
            {
                //client wish to get this address
                IPAddress requestedAddress = request.RequestedIpAddress.Address;

                if (IsAddressInRange(requestedAddress) && IsAddressAvailable(ref requestedAddress))
                {
                    offerAddress = requestedAddress;
                }
            }

            if (offerAddress == null)
            {
                lock (_lastAddressOfferedLock)
                {
                    //find free address from scope
                    offerAddress = _lastAddressOffered;
                    uint endingAddressNumber         = _endingAddress.ConvertIpToNumber();
                    bool offerAddressWasResetFromEnd = false;

                    while (true)
                    {
                        uint nextOfferAddressNumber = offerAddress.ConvertIpToNumber() + 1u;

                        if (nextOfferAddressNumber > endingAddressNumber)
                        {
                            if (offerAddressWasResetFromEnd)
                            {
                                throw new DhcpServerException("DHCP Server failed to offer IP address to " + request.GetClientFullIdentifier() + ": address unavailable due to address pool exhaustion.");
                            }

                            offerAddress = IPAddressExtension.ConvertNumberToIp(_startingAddress.ConvertIpToNumber() - 1u);
                            offerAddressWasResetFromEnd = true;
                            continue;
                        }

                        offerAddress = IPAddressExtension.ConvertNumberToIp(nextOfferAddressNumber);

                        if (IsAddressAvailable(ref offerAddress))
                        {
                            break;
                        }
                    }

                    _lastAddressOffered = offerAddress;
                }
            }

            Lease offerLease = new Lease(LeaseType.Dynamic, request.ClientIdentifier, request.HostName?.HostName, request.ClientHardwareAddress, offerAddress, null, GetLeaseTime());

            return(_offers.AddOrUpdate(request.ClientIdentifier, offerLease, delegate(ClientIdentifierOption key, Lease existingValue)
            {
                return offerLease;
            }));
        }
예제 #11
0
        public AuthZoneInfo(BinaryReader bR)
        {
            byte version = bR.ReadByte();

            switch (version)
            {
            case 1:
            case 2:
                _name     = bR.ReadShortString();
                _type     = (AuthZoneType)bR.ReadByte();
                _disabled = bR.ReadBoolean();

                if (version >= 2)
                {
                    {
                        _zoneTransfer = (AuthZoneTransfer)bR.ReadByte();

                        int count = bR.ReadByte();
                        if (count > 0)
                        {
                            IPAddress[] nameServers = new IPAddress[count];

                            for (int i = 0; i < count; i++)
                            {
                                nameServers[i] = IPAddressExtension.Parse(bR);
                            }

                            _zoneTransferNameServers = nameServers;
                        }
                    }

                    {
                        _notify = (AuthZoneNotify)bR.ReadByte();

                        int count = bR.ReadByte();
                        if (count > 0)
                        {
                            IPAddress[] nameServers = new IPAddress[count];

                            for (int i = 0; i < count; i++)
                            {
                                nameServers[i] = IPAddressExtension.Parse(bR);
                            }

                            _notifyNameServers = nameServers;
                        }
                    }
                }
                else
                {
                    switch (_type)
                    {
                    case AuthZoneType.Primary:
                        _zoneTransfer = AuthZoneTransfer.AllowOnlyZoneNameServers;
                        _notify       = AuthZoneNotify.ZoneNameServers;
                        break;

                    default:
                        _zoneTransfer = AuthZoneTransfer.Deny;
                        _notify       = AuthZoneNotify.None;
                        break;
                    }
                }

                switch (_type)
                {
                case AuthZoneType.Secondary:
                    _expiry = bR.ReadDate();
                    break;

                case AuthZoneType.Stub:
                    _expiry = bR.ReadDate();
                    break;
                }

                break;

            default:
                throw new InvalidDataException("AuthZoneInfo format version not supported.");
            }
        }
예제 #12
0
        public AuthZoneInfo(BinaryReader bR)
        {
            byte version = bR.ReadByte();

            switch (version)
            {
            case 1:
            case 2:
            case 3:
            case 4:
                _name     = bR.ReadShortString();
                _type     = (AuthZoneType)bR.ReadByte();
                _disabled = bR.ReadBoolean();

                if (version >= 2)
                {
                    {
                        _zoneTransfer = (AuthZoneTransfer)bR.ReadByte();

                        int count = bR.ReadByte();
                        if (count > 0)
                        {
                            IPAddress[] nameServers = new IPAddress[count];

                            for (int i = 0; i < count; i++)
                            {
                                nameServers[i] = IPAddressExtension.Parse(bR);
                            }

                            _zoneTransferNameServers = nameServers;
                        }
                    }

                    {
                        _notify = (AuthZoneNotify)bR.ReadByte();

                        int count = bR.ReadByte();
                        if (count > 0)
                        {
                            IPAddress[] nameServers = new IPAddress[count];

                            for (int i = 0; i < count; i++)
                            {
                                nameServers[i] = IPAddressExtension.Parse(bR);
                            }

                            _notifyNameServers = nameServers;
                        }
                    }
                }
                else
                {
                    switch (_type)
                    {
                    case AuthZoneType.Primary:
                        _zoneTransfer = AuthZoneTransfer.AllowOnlyZoneNameServers;
                        _notify       = AuthZoneNotify.ZoneNameServers;
                        break;

                    default:
                        _zoneTransfer = AuthZoneTransfer.Deny;
                        _notify       = AuthZoneNotify.None;
                        break;
                    }
                }

                switch (_type)
                {
                case AuthZoneType.Primary:
                    if (version >= 3)
                    {
                        int count = bR.ReadInt32();
                        DnsResourceRecord[] zoneHistory = new DnsResourceRecord[count];

                        for (int i = 0; i < count; i++)
                        {
                            zoneHistory[i]     = new DnsResourceRecord(bR.BaseStream);
                            zoneHistory[i].Tag = new DnsResourceRecordInfo(bR, zoneHistory[i].Type == DnsResourceRecordType.SOA);
                        }

                        _zoneHistory = zoneHistory;
                    }

                    if (version >= 4)
                    {
                        int count = bR.ReadByte();
                        Dictionary <string, object> tsigKeyNames = new Dictionary <string, object>(count);

                        for (int i = 0; i < count; i++)
                        {
                            tsigKeyNames.Add(bR.ReadShortString(), null);
                        }

                        _tsigKeyNames = tsigKeyNames;
                    }
                    break;

                case AuthZoneType.Secondary:
                    _expiry = bR.ReadDateTime();

                    if (version >= 4)
                    {
                        int count = bR.ReadInt32();
                        DnsResourceRecord[] zoneHistory = new DnsResourceRecord[count];

                        for (int i = 0; i < count; i++)
                        {
                            zoneHistory[i]     = new DnsResourceRecord(bR.BaseStream);
                            zoneHistory[i].Tag = new DnsResourceRecordInfo(bR, zoneHistory[i].Type == DnsResourceRecordType.SOA);
                        }

                        _zoneHistory = zoneHistory;
                    }

                    if (version >= 4)
                    {
                        int count = bR.ReadByte();
                        Dictionary <string, object> tsigKeyNames = new Dictionary <string, object>(count);

                        for (int i = 0; i < count; i++)
                        {
                            tsigKeyNames.Add(bR.ReadShortString(), null);
                        }

                        _tsigKeyNames = tsigKeyNames;
                    }
                    break;

                case AuthZoneType.Stub:
                    _expiry = bR.ReadDateTime();
                    break;
                }

                break;

            default:
                throw new InvalidDataException("AuthZoneInfo format version not supported.");
            }
        }