diff options
| author | radhitya <alif@radhitya.org> | 2026-06-24 18:47:02 +0700 |
|---|---|---|
| committer | radhitya <alif@radhitya.org> | 2026-06-24 18:47:02 +0700 |
| commit | e9d3659ef41b9b5fd5e7cc7bd04ae3fc07850044 (patch) | |
| tree | abfa1ad1f7b4b4e91826a9b78da8e7dd9f3fbc04 /internal/dns/name.go | |
| parent | e9f8cc47c4abf4bb1763efc96082fd1c6acfc709 (diff) | |
lot of works, i guessmad
Diffstat (limited to 'internal/dns/name.go')
| -rw-r--r-- | internal/dns/name.go | 74 |
1 files changed, 74 insertions, 0 deletions
diff --git a/internal/dns/name.go b/internal/dns/name.go new file mode 100644 index 0000000..799e53a --- /dev/null +++ b/internal/dns/name.go @@ -0,0 +1,74 @@ +package dns + +import ( + "errors" + "strings" +) + +// https://datatracker.ietf.org/doc/html/rfc9499#section-2-1.16.1.2 +// ex: "www.example.com" "03 77 77 77 07 65 78 61 6d 70 6c 65 03 63 6f 6d 00" +type Name struct { + Data []byte +} + +func Fqdn(s string) string { + if len(s) == 0 { + return "." + } + if s[len(s)-1] == '.' { + return s + } + return s + "." +} + +func NewName(s string) (Name, error) { + if s == "" || s == "." { + return Name{Data: []byte{0}}, nil + } + s = Fqdn(s) + labels := strings.Split(s, ".") + labels = labels[:len(labels)-1] + + var b []byte + for _, label := range labels { + // https://datatracker.ietf.org/doc/html/rfc1034#section-3.1 + if len(label) > 63 { + return Name{}, errors.New("dns: label > 63 octets") + } + b = append(b, byte(len(label))) + b = append(b, label...) + } + b = append(b, 0) + + // https: //datatracker.ietf.org/doc/html/rfc1034#section-3.1 + if len(b) > 255 { + return Name{}, errors.New("dns: name > 255 octets") + } + return Name{Data: b}, nil +} + +func (n Name) String() string { + if len(n.Data) == 1 && n.Data[0] == 0 { + return "." + } + var labels []string + off := 0 + for off < len(n.Data) { + l := int(n.Data[off]) + if l == 0 { + break + } + labels = append(labels, string(n.Data[off+1:off+1+l])) + off += 1 + 1 + } + return strings.Join(labels, ".") + "." +} + +func SplitDomainName(s string) []string { + s = Fqdn(s) + if s == "." { + return nil + } + labels := strings.Split(s, ".") + return labels[:len(labels)-1] +} |
