# Trait for enforcing type size constraints

**URL:** <https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901>\
**Category:** Uncategorized\
**Created:** [November 14, 2015, 6:09pm UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901 "2015-11-14T18:09:33Z")\
**Posts on this page:** 13\
**Page:** 1

<div class="post-metadata">

**Author:** ![ebfull](https://avatars.discourse-cdn.com/v4/letter/e/9e8a1a/32.png) [@ebfull](https://internals.rust-lang.org/u/ebfull)\
**Post date:** [November 14, 2015, 6:09pm UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/1 "2015-11-14T18:09:33Z")

</div>

It would be helpful if there were a trait like `SameSize<T>: Sized` implemented for all `U: Sized` where `T` and `U` are the same size. In my use case, it’s to ensure that a closure is the same size as `()` so that I don’t need to box it. I can just use it as a stack allocated dynamically sized type ([stack\_dst](https://github.com/thepowersgang/stack_dst-rs)).

Right now the only way to ensure that the closure is size zero is to try to transmute it to `()`, but this has a number of downsides:

- it requires a macro (downstream from the API) most of the time because you cannot transmute unsubstituted type parameters
- in order to enforce use of the macro you need a wrapper type
- the transmute takes ownership, so you have to rely on LLVM optimizations to make it a NOP at runtime

---

<div class="post-metadata">

**Author:** ![sanxiyn](https://sea2.discourse-cdn.com/flex002/user_avatar/internals.rust-lang.org/sanxiyn/32/8824_2.png) [@sanxiyn](https://internals.rust-lang.org/u/sanxiyn)\
**Post date:** [November 15, 2015, 4:43am UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/2 "2015-11-15T04:43:14Z")

</div>

I think this is a good use case for `static_assert`. We had `static_assert`, but [RFC 1096](https://github.com/rust-lang/rfcs/pull/1096) removed it just before 1.0 because it was unsatisfactory (but it worked) and it was hoped that something better will come along. Sadly, that didn’t happen so far.

[RFC issue 1146](https://github.com/rust-lang/rfcs/issues/1146) is an issue to design that something better. Actually, the issue calls out “checking that the size of two structs is equal” as the main use case! I am not sure whether trait is the best interface for this, but I think you definitely should comment there.

---

<div class="post-metadata">

**Author:** ![huon](https://sea2.discourse-cdn.com/flex002/user_avatar/internals.rust-lang.org/huon/32/3698_2.png) [@huon](https://internals.rust-lang.org/u/huon)\
**Post date:** [November 15, 2015, 8:31am UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/3 "2015-11-15T08:31:03Z")

</div>

> [@sanxiyn](#):
>
> (but it worked)

I don't think that `static_assert` would've worked for this purpose, for several reasons:

- `size_of` needs to be `const`-evaluable.
- nested items cannot refer to the type parameters of things they contain, e.g. this fails to compile:

```rust
fn foo<T>() {
   static FOO: *const () = 0 as *const T as *const ();
}

fn main() {}

```

---

<div class="post-metadata">

**Author:** ![bluss](https://sea2.discourse-cdn.com/flex002/user_avatar/internals.rust-lang.org/bluss/32/2264_2.png) [@bluss](https://internals.rust-lang.org/u/bluss)\
**Post date:** [November 16, 2015, 6:10pm UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/4 "2015-11-16T18:10:38Z")

</div>

Static assert doesn’t help, it needs to be a trait bound for the function using it to be parametric.

---

<div class="post-metadata">

**Author:** ![kristof](https://sea2.discourse-cdn.com/flex002/user_avatar/internals.rust-lang.org/kristof/32/1213_2.png) [@kristof](https://internals.rust-lang.org/u/kristof)\
**Post date:** [November 18, 2015, 10:11am UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/5 "2015-11-18T10:11:02Z")

</div>

Why don’t we just wait until type level integers and make it an associated type of the Sized trait?

---

<div class="post-metadata">

**Author:** ![huon](https://sea2.discourse-cdn.com/flex002/user_avatar/internals.rust-lang.org/huon/32/3698_2.png) [@huon](https://internals.rust-lang.org/u/huon)\
**Post date:** [November 18, 2015, 11:19am UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/6 "2015-11-18T11:19:32Z")

</div>

There is [a loose plan](https://github.com/rust-lang/rfcs/pull/1168) to make it an associated constant of `Sized`.

---

<div class="post-metadata">

**Author:** ![ebfull](https://avatars.discourse-cdn.com/v4/letter/e/9e8a1a/32.png) [@ebfull](https://internals.rust-lang.org/u/ebfull)\
**Post date:** [November 19, 2015, 4:03am UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/7 "2015-11-19T04:03:37Z")

</div>

It would also be interesting if it were possible to expose (via traits somehow) that a type “fits” within another type, which afaik an associated constant wouldn’t give us alone (?). This is a more general desire of both my use case but also a lot of goofy tricks like `stack_dst` itself. Safe and efficient abstractions could be written which avoid allocations or reuse memory in tricky ways based on this principle.

---

<div class="post-metadata">

**Author:** ![kristof](https://sea2.discourse-cdn.com/flex002/user_avatar/internals.rust-lang.org/kristof/32/1213_2.png) [@kristof](https://internals.rust-lang.org/u/kristof)\
**Post date:** [November 21, 2015, 8:38am UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/8 "2015-11-21T08:38:18Z")

</div>

Well if static assert works the way I think it does, then you could always compare the associated const of one type to another at compile time.

---

<div class="post-metadata">

**Author:** ![gnzlbg](https://sea2.discourse-cdn.com/flex002/user_avatar/internals.rust-lang.org/gnzlbg/32/3858_2.png) [@gnzlbg](https://internals.rust-lang.org/u/gnzlbg)\
**Post date:** [December 22, 2015, 2:13pm UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/9 "2015-12-22T14:13:01Z")

</div>

This came up while trying to improve `num::PrimInt`.

The problem is: How to use `mem::transmute` in a function implementation within a generic trait?

Right now this is hard (or impossible) since there is no easy way to constrain the trait types to be `SameSize` or `Transmutable`.

I think this could be solved by lifting part of the magic behind `mem::transmute` into a `SameSize` or `Transmutable` trait, and then constraining `mem::transmute` on it. This would allow user defined generic functions/methods/traits to constrain on it as well and easily be able to call `mem::transmute` from them.

---

<div class="post-metadata">

**Author:** ![jschievink](https://sea2.discourse-cdn.com/flex002/user_avatar/internals.rust-lang.org/jschievink/32/3063_2.png) [@jschievink](https://internals.rust-lang.org/u/jschievink)\
**Post date:** [December 24, 2015, 3:14pm UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/10 "2015-12-24T15:14:02Z")

</div>

This is also potentially useful for `Vec::map_in_place` (which no longer exists)

---

<div class="post-metadata">

**Author:** ![LilianMoraru](https://sea2.discourse-cdn.com/flex002/user_avatar/internals.rust-lang.org/lilianmoraru/32/1661_2.png) [@LilianMoraru](https://internals.rust-lang.org/u/LilianMoraru)\
**Post date:** [March 6, 2017, 11:17pm UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/11 "2017-03-06T23:17:09Z")

</div>

This should be possible now with `macros 1.1`, although I don’t think that the feature should come from libraries, this seems like a core feature. At least, in C++ I use A Lot `static_assert` to enforce correct API usage(although, for most of the things I use it for, Rust has trait bounds).

---

<div class="post-metadata">

**Author:** ![kornel](https://sea2.discourse-cdn.com/flex002/user_avatar/internals.rust-lang.org/kornel/32/2711_2.png) [@kornel](https://internals.rust-lang.org/u/kornel)\
**Post date:** [March 10, 2017, 12:49am UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/12 "2017-03-10T00:49:51Z")

</div>

I could use it too. In image processing libraries it’s often valuable to do conversions in-place, while leaving types very flexible to allow various color spaces and newtypes.

---

<div class="post-metadata">

**Author:** ![system](https://sea2.discourse-cdn.com/flex002/user_avatar/internals.rust-lang.org/system/32/14092_2.png) [@system](https://internals.rust-lang.org/u/system)\
**Post date:** [March 25, 2019, 8:25am UTC](https://internals.rust-lang.org/t/trait-for-enforcing-type-size-constraints/2901/13 "2019-03-25T08:25:28Z")

</div>

This topic was automatically closed 90 days after the last reply. New replies are no longer allowed.
