compiler: alignof(func) is 1 pointer, not 2

This ensures that an embedded [0]func() never ends up being larger
than 1 pointer, which is requried by protobuf processing code.
Этот коммит содержится в:
Steven Kabbes 2022-05-21 04:19:39 -07:00 коммит произвёл Ron Evans
родитель f308d7d28c
коммит 52c61de19f
3 изменённых файлов: 14 добавлений и 6 удалений

Просмотреть файл

@ -21,12 +21,6 @@ func (s *stdSizes) Alignof(T types.Type) int64 {
// of alignment of the elements and fields, respectively.
switch t := T.Underlying().(type) {
case *types.Array:
if t.Len() == 0 {
// 0-sized arrays, always have 0 size.
// And from the spec, should have an alignment of _at least_ 1
return 1
}
// spec: "For a variable x of array type: unsafe.Alignof(x)
// is the same as unsafe.Alignof(x[0]), but at least 1."
return s.Alignof(t.Elem())
@ -51,7 +45,11 @@ func (s *stdSizes) Alignof(T types.Type) int64 {
if t.Info()&types.IsString != 0 {
return s.PtrSize
}
case *types.Signature:
// Even though functions in tinygo are 2 pointers, they are not 2 pointer aligned
return s.PtrSize
}
a := s.Sizeof(T) // may be 0
// spec: "For a variable x of any type: unsafe.Alignof(x) is at least 1."
if a < 1 {

7
testdata/reflect.go предоставленный
Просмотреть файл

@ -347,6 +347,13 @@ func main() {
println("errorValue.Implements(errorType) was true, expected false")
}
println("\nalignment / offset:")
v2 := struct {
noCompare [0]func()
data byte
}{}
println("struct{[0]func(); byte}:", unsafe.Offsetof(v2.data) == uintptr(unsafe.Pointer(&v2.data))-uintptr(unsafe.Pointer(&v2)))
println("\nstruct tags")
TestStructTag()

3
testdata/reflect.txt предоставленный
Просмотреть файл

@ -405,6 +405,9 @@ offset for int64 matches: true
offset for complex128 matches: true
type assertion succeeded for unreferenced type
alignment / offset:
struct{[0]func(); byte}: true
struct tags
blue gopher