Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

amino.WithTypes accepts types being given the same name #2326

Open
grepsuzette opened this issue Jun 11, 2024 · 0 comments
Open

amino.WithTypes accepts types being given the same name #2326

grepsuzette opened this issue Jun 11, 2024 · 0 comments
Labels
amino Issues and PRs related to amino 🐞 bug Something isn't working

Comments

@grepsuzette
Copy link
Contributor

amino.WithTypes admits types with the same name

This potential issue was uncovered in #2325.

Description

Quite simply, the following code does not panic:

package amino_test

import (
	"reflect"
	"testing"
	"github.com/stretchr/testify/assert"
	amino "github.com/gnolang/gno/tm2/pkg/amino"
	"github.com/gnolang/gno/tm2/pkg/amino/tests"
)

func TestDupNamesMustPanic(t *testing.T) {
	assert.Panics(t, func() {
		amino.NewPackage(
			reflect.TypeOf(tests.EmptyStruct{}).PkgPath(),
			"amino_test",
			amino.GetCallersDirname(),
		).WithTypes(
	 		tests.EmptyStruct{}, "A",
	 		tests.PrimitivesStruct{}, "B",
	 		tests.ShortArraysStruct{}, "A", // Same name
		)
	}
}

Expected behaviour

Since codec_test.go has the following line a panic should be expected here:

// XXX Test registering duplicate names or concrete types not in a package.

Proposed solution

Existing code for WithTypes prepares a pkg.Types which can just be iterated before returning.

func (pkg *Package) WithTypes(objs ...interface{}) *Package {
var lastType *Type = nil
for _, obj := range objs {
// Initialize variables
objType := reflect.TypeOf(obj)
name := ""
pointerPreferred := false
// Two special cases.
// One: a string which follows a type declaration is a name.
if objType == reflect.TypeOf("string") {
if lastType == nil {
panic("Type names (specified via a string argument to WithTypes()) must come *after* the prototype object")
} else {
lastType.Name = obj.(string)
lastType = nil // no more updating is possible.
continue
}
}
// Two: pkg.Type{} can be specified directly
if objType.Kind() == reflect.Ptr && objType.Elem() == reflect.TypeOf(Type{}) {
panic("Use pkg.Type{}, not *pkg.Type{}")
}
if objType == reflect.TypeOf(Type{}) {
objType = obj.(Type).Type
name = obj.(Type).Name
if name != capitalize(name) {
panic(fmt.Sprintf("Type name must be capitalized, but got %v", name))
}
pointerPreferred = obj.(Type).PointerPreferred
}
// End of special cases.
// Init deref and ptr types.
objDerefType := objType
if objDerefType.Kind() == reflect.Ptr {
objDerefType = objType.Elem()
if objDerefType.Kind() == reflect.Ptr {
panic("unexpected nested pointers")
}
pointerPreferred = true
}
if objDerefType.PkgPath() != pkg.GoPkgPath {
panic(fmt.Sprintf("unexpected package for %v, expected %v got %v for obj %v obj type %v", objDerefType, pkg.GoPkgPath, objDerefType.PkgPath(), obj, objType))
}
// Check that deref type don't already exist.
_, ok := pkg.GetType(objDerefType)
if ok {
panic(fmt.Errorf("type %v already registered with package", objDerefType))
}
if name == "" {
name = objDerefType.Name()
}
lastType = &Type{ // memoize for future modification.
Type: objDerefType,
Name: name, // may get overridden later.
PointerPreferred: pointerPreferred,
}
pkg.Types = append(pkg.Types, lastType)
}
return pkg
}

The following actually fixes the test in #2325:

        (...)
		pkg.Types = append(pkg.Types, lastType)
	}

    // APPENDED HERE -------------------------------------------------------
	// Forbid duplicate names
	for i, t := range pkg.Types {
		if t.Name == "" {
			continue
		}
		for j := i + 1; j < len(pkg.Types); j++ {
			if pkg.Types[j].Name == t.Name {
				panic(fmt.Errorf("type name %s is already registered", t.Name))
			}
		}
	} // ------------------------------------------------------------------------^^^
	return pkg
}
@Kouteki Kouteki added amino Issues and PRs related to amino 🐞 bug Something isn't working labels Jun 28, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
amino Issues and PRs related to amino 🐞 bug Something isn't working
Projects
Development

No branches or pull requests

2 participants