package dns

// Dedup removes identical RRs from rrs. It preserves the original ordering.
// The lowest TTL of any duplicates is used in the remaining one. Dedup modifies
// rrs.
// m is used to store the RRs temporary. If it is nil a new map will be allocated.
func ( []RR,  map[string]RR) []RR {

	if  == nil {
		 = make(map[string]RR)
	}
	// Save the keys, so we don't have to call normalizedString twice.
	 := make([]*string, 0, len())

	for ,  := range  {
		 := normalizedString()
		 = append(, &)
		if ,  := [];  {
			// Shortest TTL wins.
			,  := .Header(), .Header()
			if .Ttl > .Ttl {
				.Ttl = .Ttl
			}
			continue
		}

		[] = 
	}
	// If the length of the result map equals the amount of RRs we got,
	// it means they were all different. We can then just return the original rrset.
	if len() == len() {
		return 
	}

	 := 0
	for ,  := range  {
		// If keys[i] lives in the map, we should copy and remove it.
		if ,  := [*[]];  {
			delete(, *[])
			[] = 
			++
		}

		if len() == 0 {
			break
		}
	}

	return [:]
}

// normalizedString returns a normalized string from r. The TTL
// is removed and the domain name is lowercased. We go from this:
// DomainName<TAB>TTL<TAB>CLASS<TAB>TYPE<TAB>RDATA to:
// lowercasename<TAB>CLASS<TAB>TYPE...
func normalizedString( RR) string {
	// A string Go DNS makes has: domainname<TAB>TTL<TAB>...
	 := []byte(.String())

	// find the first non-escaped tab, then another, so we capture where the TTL lives.
	 := false
	,  := 0, 0
	for  := 0;  < len() &&  == 0; ++ {
		switch {
		case [] == '\\':
			 = !
		case [] == '\t' && !:
			if  == 0 {
				 = 
				continue
			}
			if  == 0 {
				 = 
			}
		case [] >= 'A' && [] <= 'Z' && !:
			[] += 32
		default:
			 = false
		}
	}

	// remove TTL.
	copy([:], [:])
	 :=  - 
	return string([:len()-])
}