Skip to content

Commit f02ef26

Browse files
author
shadowy-pycoder
committed
Fixed extractDomain parser
1 parent c38b68b commit f02ef26

File tree

1 file changed

+67
-37
lines changed

1 file changed

+67
-37
lines changed

layers/dns.go

Lines changed: 67 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ func (d *DNSMessage) String() string {
3939
d.AuthorityRRs,
4040
d.AdditionalRRs,
4141
len(d.payload),
42-
d.queries(),
42+
d.rrecords(),
4343
)
4444
}
4545

@@ -147,67 +147,97 @@ func bytesToStr(myBytes []byte) string {
147147
return unsafe.String(unsafe.SliceData(myBytes), len(myBytes))
148148
}
149149

150-
func extractDomain(data []byte, offset int) (string, int) {
151-
var parts []string
150+
func extractDomain(data []byte, tail []byte) (string, []byte) {
151+
var domainName string
152152
for {
153-
blen := int(data[offset])
154-
offset++
155-
if blen == 0 {
153+
blen := tail[0]
154+
if blen>>6 == 0b11 {
155+
offset := binary.BigEndian.Uint16(tail[0:2])&(1<<14-1) - headerSizeDNS
156+
part, _ := extractDomain(data, data[offset:])
157+
domainName += part
158+
tail = tail[2:]
156159
break
157160
}
158-
if blen == 0xc0 {
159-
offset = int(data[offset]) - headerSizeDNS
160-
blen = int(data[offset])
161-
offset++
161+
tail = tail[1:]
162+
if blen == 0 {
163+
break
162164
}
163-
parts = append(parts, bytesToStr(data[offset:offset+blen]))
164-
offset += blen
165+
domainName += bytesToStr(tail[0:blen])
166+
domainName += "."
167+
168+
tail = tail[blen:]
165169
}
166-
return strings.Join(parts, "."), offset
170+
return domainName, tail
167171
}
168172

169-
func (d *DNSMessage) queries() string {
170-
var (
171-
sb strings.Builder
172-
offset int
173-
)
173+
func (d *DNSMessage) rrecords() string {
174+
var sb strings.Builder
175+
tail := d.payload
174176
if d.Questions > 0 {
175177
sb.WriteString("- Queries:\n")
176178
for range d.Questions {
177179
var domain string
178-
domain, offset = extractDomain(d.payload, offset)
179-
typ := binary.BigEndian.Uint16(d.payload[offset : offset+2])
180-
offset += 2
181-
class := binary.BigEndian.Uint16(d.payload[offset : offset+2])
182-
offset += 2
180+
domain, tail = extractDomain(d.payload, tail)
181+
typ := binary.BigEndian.Uint16(tail[0:2])
182+
class := binary.BigEndian.Uint16(tail[2:4])
183+
tail = tail[4:]
183184
// TODO: add type and class description https://en.wikipedia.org/wiki/List_of_DNS_record_types
184185
sb.WriteString(fmt.Sprintf(" %s: type %d class %d\n", domain, typ, class))
185186
}
186187
}
187188
if d.AnswerRRs > 0 {
188189
sb.WriteString("- Answers:\n")
189190
for range d.AnswerRRs {
190-
no := binary.BigEndian.Uint16(d.payload[offset : offset+2])
191-
offset += 2
192-
domain, _ := extractDomain(d.payload, int(no&0xFF)-headerSizeDNS)
193-
typ := binary.BigEndian.Uint16(d.payload[offset : offset+2])
194-
offset += 2
195-
class := binary.BigEndian.Uint16(d.payload[offset : offset+2])
196-
offset += 2
197-
ttl := binary.BigEndian.Uint32(d.payload[offset : offset+4])
198-
offset += 4
199-
rdl := int(binary.BigEndian.Uint16(d.payload[offset : offset+2]))
200-
offset += 2
191+
var domain string
192+
domain, tail = extractDomain(d.payload, tail)
193+
typ := binary.BigEndian.Uint16(tail[0:2])
194+
class := binary.BigEndian.Uint16(tail[2:4])
195+
ttl := binary.BigEndian.Uint32(tail[4:8])
196+
rdl := int(binary.BigEndian.Uint16(tail[8:10]))
201197
//rdata := d.payload[offset : offset+rdl]
202-
offset += rdl
203-
sb.WriteString(fmt.Sprintf(" %s: type %d class %d ttl %d rdl %d\n", domain, typ, class, ttl, rdl))
198+
tail = tail[10+rdl:]
199+
sb.WriteString(fmt.Sprintf(" %s: type %d class %d ttl %08x rdl %04x\n", domain, typ, class, ttl, rdl))
204200
}
205201
}
206202
if d.AuthorityRRs > 0 {
207-
203+
sb.WriteString("- Authoritative nameservers:\n")
204+
for range d.AuthorityRRs {
205+
var domain string
206+
domain, tail = extractDomain(d.payload, tail)
207+
typ := binary.BigEndian.Uint16(tail[0:2])
208+
class := binary.BigEndian.Uint16(tail[2:4])
209+
ttl := binary.BigEndian.Uint32(tail[4:8])
210+
rdl := int(binary.BigEndian.Uint16(tail[8:10]))
211+
//rdata := d.payload[offset : offset+rdl]
212+
tail = tail[10+rdl:]
213+
sb.WriteString(fmt.Sprintf(" %s: type %d class %d ttl %d rdl %d\n", domain, typ, class, ttl, rdl))
214+
}
208215
}
209216
if d.AdditionalRRs > 0 {
217+
sb.WriteString("- Additional records:\n")
218+
for range d.AdditionalRRs {
219+
if tail[0] != 0 {
220+
var domain string
221+
domain, tail = extractDomain(d.payload, tail)
222+
typ := binary.BigEndian.Uint16(tail[0:2])
223+
class := binary.BigEndian.Uint16(tail[2:4])
224+
ttl := binary.BigEndian.Uint32(tail[4:8])
225+
rdl := int(binary.BigEndian.Uint16(tail[8:10]))
226+
//rdata := d.payload[offset : offset+rdl]
227+
tail = tail[10+rdl:]
228+
sb.WriteString(fmt.Sprintf(" %s: type %d class %d ttl %d rdl %d\n", domain, typ, class, ttl, rdl))
229+
} else {
230+
tail = tail[1:]
231+
typ := binary.BigEndian.Uint16(tail[0:2])
232+
ups := binary.BigEndian.Uint16(tail[2:4])
233+
t1 := tail[4]
234+
zres := binary.BigEndian.Uint16(tail[5:7])
235+
rdl := int(binary.BigEndian.Uint16(tail[7:9]))
236+
tail = tail[9+rdl:]
237+
sb.WriteString(fmt.Sprintf(" Root: type %d UDP payload size %d t1 %d zres %d rdl %d\n", typ, ups, t1, zres, rdl))
238+
}
210239

240+
}
211241
}
212242
return sb.String()
213243
}

0 commit comments

Comments
 (0)