Files
stun/fuzz_test.go
Joe Turki 8867eb8597 Update lint rules, force testify/assert for tests
Use testify's assert package instead of the standard library's testing
package.
2025-04-07 02:59:21 +02:00

141 lines
2.8 KiB
Go

// SPDX-FileCopyrightText: 2023 The Pion community <https://pion.ly>
// SPDX-License-Identifier: MIT
package stun
import (
"encoding/binary"
"errors"
"testing"
"github.com/stretchr/testify/assert"
)
func FuzzMessage(f *testing.F) {
msg1 := New()
f.Fuzz(func(t *testing.T, data []byte) {
msg1.Reset()
// Fuzzer does not know about cookies
if len(data) >= 8 {
binary.BigEndian.PutUint32(data[4:8], magicCookie)
}
// Trying to read data as message
if _, err := msg1.Write(data); err != nil {
return // We expect invalid messages to fail here
}
msg2 := New()
_, err := msg2.Write(msg1.Raw)
assert.NoError(t, err, "Failed to write")
assert.Equal(t, msg1.TransactionID, msg2.TransactionID, "Transaction ID mismatch")
assert.Equal(t, msg1.Type, msg2.Type, "Type mismatch")
assert.Equal(t, len(msg1.Attributes), len(msg2.Attributes), "Attributes length mismatch")
})
}
func FuzzType(f *testing.F) {
f.Fuzz(func(t *testing.T, data uint16) {
v := data & 0x1fff // First 3 bits are empty
t1 := MessageType{}
t1.ReadValue(v)
v2 := t1.Value()
assert.Equal(t, v, v2, "v != v2")
t2 := MessageType{}
t2.ReadValue(v2)
assert.Equal(t, t1, t2, "t2 != t1")
})
}
func FuzzSetters(f *testing.F) {
f.Fuzz(func(t *testing.T, firstByte byte, value []byte) {
var (
m1 = &Message{
Raw: make([]byte, 0, 2048),
}
m2 = &Message{
Raw: make([]byte, 0, 2048),
}
m3 = &Message{
Raw: make([]byte, 0, 2048),
}
)
attrs := attributes{
{new(Realm), AttrRealm},
{new(XORMappedAddress), AttrXORMappedAddress},
{new(Nonce), AttrNonce},
{new(Software), AttrSoftware},
{new(AlternateServer), AttrAlternateServer},
{new(ErrorCodeAttribute), AttrErrorCode},
{new(UnknownAttributes), AttrUnknownAttributes},
{new(Username), AttrUsername},
{new(MappedAddress), AttrMappedAddress},
{new(Realm), AttrRealm},
}
attr := attrs.pick(firstByte)
m1.WriteHeader()
m1.Add(attr.t, value)
err := attr.g.GetFrom(m1)
assert.False(t, errors.Is(err, ErrAttributeNotFound))
if err != nil {
return
}
m2.WriteHeader()
err = attr.g.AddTo(m2)
if err != nil {
// We allow decoding some text attributes
// when their length is too big, but
// not encoding.
if !IsAttrSizeOverflow(err) {
assert.NoError(t, err)
}
return
}
m3.WriteHeader()
v, err := m2.Get(attr.t)
assert.NoError(t, err)
m3.Add(attr.t, v)
assert.True(t, m2.Equal(m3), "Not equal: %s != %s", m2, m3)
})
}
func TestAttrPick(*testing.T) {
attrs := attributes{
{new(XORMappedAddress), AttrXORMappedAddress},
}
for i := byte(0); i < 255; i++ {
attrs.pick(i)
}
}
type attr interface {
Getter
Setter
}
type attributes []struct {
g attr
t AttrType
}
func (a attributes) pick(v byte) struct {
g attr
t AttrType
} {
idx := int(v) % len(a)
return a[idx]
}