Skip to content

Commit

Permalink
btf: Handle Tags when making copies
Browse files Browse the repository at this point in the history
d4b2f8c introduced Tags on different types implementing btf.Type. Tags
arrays are initialized at load time from declTag-s referring to the
respective type.

Type-s are explicitly copied with btf.Copy, also implicitly when copying
a btf.Spec. Semantically, it is a deep copy, hence Tags must be cloned
as well.

Signed-off-by: Nick Zavaritsky <[email protected]>
  • Loading branch information
mejedi authored and ti-mo committed Oct 10, 2024
1 parent d6606c0 commit c63a00b
Show file tree
Hide file tree
Showing 2 changed files with 30 additions and 0 deletions.
24 changes: 24 additions & 0 deletions btf/types.go
Original file line number Diff line number Diff line change
Expand Up @@ -183,6 +183,7 @@ func (s *Struct) size() uint32 { return s.Size }
func (s *Struct) copy() Type {
cpy := *s
cpy.Members = copyMembers(s.Members)
cpy.Tags = copyTags(cpy.Tags)
return &cpy
}

Expand Down Expand Up @@ -210,6 +211,7 @@ func (u *Union) size() uint32 { return u.Size }
func (u *Union) copy() Type {
cpy := *u
cpy.Members = copyMembers(u.Members)
cpy.Tags = copyTags(cpy.Tags)
return &cpy
}

Expand All @@ -220,6 +222,18 @@ func (u *Union) members() []Member {
func copyMembers(orig []Member) []Member {
cpy := make([]Member, len(orig))
copy(cpy, orig)
for i, member := range cpy {
cpy[i].Tags = copyTags(member.Tags)
}
return cpy
}

func copyTags(orig []string) []string {
if orig == nil { // preserve nil vs zero-len slice distinction
return nil
}
cpy := make([]string, len(orig))
copy(cpy, orig)
return cpy
}

Expand Down Expand Up @@ -348,6 +362,7 @@ func (td *Typedef) TypeName() string { return td.Name }

func (td *Typedef) copy() Type {
cpy := *td
cpy.Tags = copyTags(td.Tags)
return &cpy
}

Expand Down Expand Up @@ -434,6 +449,14 @@ func (f *Func) TypeName() string { return f.Name }

func (f *Func) copy() Type {
cpy := *f
cpy.Tags = copyTags(f.Tags)
if f.ParamTags != nil { // preserve nil vs zero-len slice distinction
ptCopy := make([][]string, len(f.ParamTags))
for i, tags := range f.ParamTags {
ptCopy[i] = copyTags(tags)
}
cpy.ParamTags = ptCopy
}
return &cpy
}

Expand Down Expand Up @@ -477,6 +500,7 @@ func (v *Var) TypeName() string { return v.Name }

func (v *Var) copy() Type {
cpy := *v
cpy.Tags = copyTags(v.Tags)
return &cpy
}

Expand Down
6 changes: 6 additions & 0 deletions btf/types_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ func TestSizeof(t *testing.T) {

func TestCopy(t *testing.T) {
i := &Int{Size: 4}
tags := []string{"bar:foo"}

got := Copy(&Struct{
Members: []Member{
Expand All @@ -60,6 +61,11 @@ func TestCopy(t *testing.T) {
{"void", (*Void)(nil)},
{"int", i},
{"cyclical", newCyclicalType(2)},
{"struct tags", &Struct{Tags: tags, Members: []Member{{Tags: tags}}}},
{"union tags", &Union{Tags: tags, Members: []Member{{Tags: tags}}}},
{"typedef tags", &Typedef{Type: i, Tags: tags}},
{"var tags", &Var{Type: i, Tags: tags}},
{"func tags", &Func{Tags: tags, ParamTags: [][]string{tags}}},
} {
t.Run(test.name, func(t *testing.T) {
cpy := Copy(test.typ)
Expand Down

0 comments on commit c63a00b

Please sign in to comment.