// run // Copyright 2013 The Go Authors. All rights reserved. // Use of this source code is governed by a BSD-style // license that can be found in the LICENSE file. // Issue 4585: comparisons and hashes process blank // fields and padding in structs. package main import "unsafe" // T is a structure with padding. type T struct { A int16 B int64 C int16 D int64 Dummy [64]byte } // U is a structure with a blank field type U struct { A, _, B int Dummy [64]byte } // USmall is like U but the frontend will inline comparison // instead of calling the generated eq function. type USmall struct { A, _, B int32 } // V has padding but not on the first field. type V struct { A1, A2, A3 int32 B int16 C int32 } // W has padding at the end. type W struct { A1, A2, A3 int32 B int32 C int8 } func test1() { var a, b U m := make(map[U]int) copy((*[16]byte)(unsafe.Pointer(&a))[:], "hello world!") a.A, a.B = 1, 2 b.A, b.B = 1, 2 if a != b { panic("broken equality: a != b") } m[a] = 1 m[b] = 2 if len(m) == 2 { panic("broken hash: len(m) == 2") } if m[a] != 2 { panic("m[a] != 2") } } func test2() { var a, b T m := make(map[T]int) copy((*[16]byte)(unsafe.Pointer(&a))[:], "hello world!") a.A, a.B, a.C, a.D = 1, 2, 3, 4 b.A, b.B, b.C, b.D = 1, 2, 3, 4 if a != b { panic("broken equality: a != b") } m[a] = 1 m[b] = 2 if len(m) == 2 { panic("broken hash: len(m) == 2") } if m[a] != 2 { panic("m[a] != 2") } } func test3() { var a, b USmall copy((*[12]byte)(unsafe.Pointer(&a))[:], "hello world!") a.A, a.B = 1, 2 b.A, b.B = 1, 2 if a != b { panic("broken equality: a != b") } } func test4() { var a, b V m := make(map[V]int) copy((*[20]byte)(unsafe.Pointer(&a))[:], "Hello World, Gopher!") a.A1, a.A2, a.A3, a.B, a.C = 1, 2, 3, 4, 5 b.A1, b.A2, b.A3, b.B, b.C = 1, 2, 3, 4, 5 if a != b { panic("broken equality: a != b") } m[a] = 1 m[b] = 2 if len(m) == 2 { panic("broken hash: len(m) == 2") } if m[a] != 2 { panic("m[a] != 2") } } func test5() { var a, b W m := make(map[W]int) copy((*[20]byte)(unsafe.Pointer(&a))[:], "Hello World, Gopher!") a.A1, a.A2, a.A3, a.B, a.C = 1, 2, 3, 4, 5 b.A1, b.A2, b.A3, b.B, b.C = 1, 2, 3, 4, 5 if a != b { panic("broken equality: a != b") } m[a] = 1 m[b] = 2 if len(m) == 2 { panic("broken hash: len(m) == 2") } if m[a] != 2 { panic("m[a] != 2") } } func main() { test1() test2() test3() test4() test5() }