TechnitiumSoftware/DnsServer · error · DnsServerException

The record type is not supported by primary zones.

Error message

The record type is not supported by primary zones.

What it means

Thrown by PrimarySubDomainZone.SetRecords() when type is FWD. The FWD (forwarder) record type is the defining record of a Conditional Forwarder zone (ForwarderZone), not a record type that belongs in a primary zone; a primary zone is authoritative and answers from its own data, so embedding a forwarder directive is semantically invalid. DnsServerException, catchable. The same restriction applies to ForwarderZone.AddRecord at line 137.

Source

Thrown at DnsServerCore/Dns/Zones/PrimarySubDomainZone.cs:90

                        break;
                }
            }

            switch (type)
            {
                case DnsResourceRecordType.SOA:
                    throw new InvalidOperationException("Cannot set SOA record on sub domain.");

                case DnsResourceRecordType.DNSKEY:
                case DnsResourceRecordType.RRSIG:
                case DnsResourceRecordType.NSEC:
                case DnsResourceRecordType.NSEC3PARAM:
                case DnsResourceRecordType.NSEC3:
                    throw new InvalidOperationException("Cannot set DNSSEC records.");

                case DnsResourceRecordType.FWD:
                    throw new DnsServerException("The record type is not supported by primary zones.");

                default:
                    if (records[0].OriginalTtlValue > _primaryZone.GetZoneSoaExpire())
                        throw new DnsServerException("Cannot set records: TTL cannot be greater than SOA EXPIRE.");

                    if (!TrySetRecords(type, records, out IReadOnlyList<DnsResourceRecord> deletedRecords))
                        throw new DnsServerException("Cannot set records. Please try again.");

                    _primaryZone.CommitAndIncrementSerial(deletedRecords, records);

                    if (_primaryZone.DnssecStatus != AuthZoneDnssecStatus.Unsigned)
                        _primaryZone.UpdateDnssecRecordsFor(this, type);

                    _primaryZone.TriggerNotify();
                    break;
            }
        }

View on GitHub (pinned to d0484b6c1e)

Solutions

  1. Do not add FWD records to a primary zone or its sub-domains; if forwarding is needed, create a Conditional Forwarder zone for that name instead.
  2. Filter FWD out of imported record sets for primary/sub-domain zones.
  3. If the goal is conditional forwarding, replace the primary zone delegation with a ForwarderZone.

Example fix

// before
subZone.SetRecords(DnsResourceRecordType.FWD, new[] { fwdRecord });

// after
// create a conditional forwarder zone instead
_dnsServer.AddForwarderZone(name, protocol, forwarder, ...);
Defensive patterns

Strategy: validation

Validate before calling

if (type == DnsResourceRecordType.FWD)
    throw new InvalidOperationException("FWD records belong to Conditional Forwarder zones, not primary zones.");
zone.SetRecords(type, records);

Type guard

static bool IsAllowedPrimaryRecordType(DnsResourceRecordType t) => t != DnsResourceRecordType.FWD;

Try / catch

try { zone.SetRecords(type, records); }
catch (DnsServerException) when (type == DnsResourceRecordType.FWD) { /* create a ForwarderZone instead */ }

Prevention

When it happens

Trigger: subZone.SetRecords(DnsResourceRecordType.FWD, records) on a PrimarySubDomainZone — e.g. importing a config that mixed forwarder records into a primary zone, or attempting to convert a delegation into a forwarder by adding a FWD record.

Common situations: Cross-zone import that does not respect zone type; UI that offers FWD as a record type on primary zones; migration scripts merging forwarder and primary zone data.

Related errors


AI-assisted analysis of TechnitiumSoftware/DnsServer@d0484b6c1e (2026-08-13). Data as JSON: /api/errors/efe83a3e851163d2. Report an issue: GitHub.