Skip to content

Commit

Permalink
feat: pseudo.PointerTo()
Browse files Browse the repository at this point in the history
  • Loading branch information
ARR4N committed Sep 11, 2024
1 parent 00506bc commit cc36bed
Show file tree
Hide file tree
Showing 2 changed files with 44 additions and 0 deletions.
21 changes: 21 additions & 0 deletions libevm/pseudo/type.go
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,27 @@ func Zero[T any]() *Pseudo[T] {
return From[T](x)
}

// PointerTo is equivalent to [From] called with a pointer to the payload
// carried by `t`. It first confirms that the payload is of type `T`.
func PointerTo[T any](t *Type) (*Pseudo[*T], error) {
c, ok := t.val.(*concrete[T])
if !ok {
var want *T
return nil, fmt.Errorf("cannot create *Pseudo[%T] from *Type carrying %T", want, t.val.get())
}
return From(&c.val), nil
}

// MustPointerTo is equivalent to [PointerTo] except that it panics instead of
// returning an error.
func MustPointerTo[T any](t *Type) *Pseudo[*T] {
p, err := PointerTo[T](t)
if err != nil {
panic(err)
}
return p
}

// Interface returns the wrapped value as an `any`, equivalent to
// [reflect.Value.Interface]. Prefer [Value.Get].
func (t *Type) Interface() any { return t.val.get() }
Expand Down
23 changes: 23 additions & 0 deletions libevm/pseudo/type_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -77,3 +77,26 @@ func ExamplePseudo_TypeAndValue() {
_ = typ
_ = val
}

func TestPointer(t *testing.T) {
type carrier struct {
payload int
}

typ, val := From(carrier{42}).TypeAndValue()

t.Run("invalid type", func(t *testing.T) {
_, err := PointerTo[int](typ)
require.Errorf(t, err, "PointerTo[int](%T)", carrier{})
})

t.Run("valid type", func(t *testing.T) {
ptrVal := MustPointerTo[carrier](typ).Value

assert.Equal(t, 42, val.Get().payload, "before setting via pointer")
var ptr *carrier = ptrVal.Get()
ptr.payload = 314159
assert.Equal(t, 314159, val.Get().payload, "after setting via pointer")
})

}

0 comments on commit cc36bed

Please sign in to comment.