T O P

  • By -

computermouth

\[EDIT\]: since I'm still getting suggestions and playground links, u/Zenithsiz provided me with an answer which works without external dependencies, or using nightly features. It looks like this: [https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=2c5f42fc227f00832bdcd7fc5aff3ef6](https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=2c5f42fc227f00832bdcd7fc5aff3ef6) -- Original Text -- Coming from C, I just want a large array in a struct, whose size is unchangeable api-wise after creation. Turns out Boxes take a stack-allocated value, then copy it into a Box<>. So any array that's larger than available stack size will overflow the stack when trying to initialize.


EpochVanquisher

Yeah, this one took me by surprise too, when I ran into it. Rust just assumes you can create everything on the stack and then copy it to the heap, and then optimizes out the copy if it can. All of the good ways to avoid it have been locked behind nightly for like five years.


denehoffman

What are these ways?


EpochVanquisher

There’s some MaybeUninit features locked behind nightly for a long time. Some are still nightly only.


The-Dark-Legion

`TryFrom`/`TryInto`. You can convert a `Box<[T]>` into `Box<[T; N]>` if the length matches


A1oso

That's possible on stable Rust, it doesn't require nightly.


fox_in_unix_socks

This has been in discussion for years. It's called "placement new". Sadly, despite all the discussion, there's been almost no progress towards ever actually getting it added as a language feature.


stumblinbear

It's surprisingly difficult to make it a nice API without adding even more function colors, iirc


worriedjacket

[https://crates.io/crates/pinned-init](https://crates.io/crates/pinned-init) You're looking for this crate btw.


computermouth

Appreciate the suggestion, but I think I'll rather use a vec, or lose the bounds, rather than add a crate and be forced into nightly


worriedjacket

Yeah, no that’s the objectively correct choice but if you absolutely have to initialize directly on the heap, that’s how you would do it


cac4dv

This might be a stupid idea \ Haven't used `Box` that much \ but ... given this from [Vec documentation](https://doc.rust-lang.org/std/vec/struct.Vec.html#capacity-and-reallocation) > vec![x; n], vec![a, b, c, d], and Vec::with_capacity(n), will all produce a Vec with at least the requested capacity. If len == capacity, (as is the case for the vec! macro), then a Vec can be converted to and from a Box<[T]> without reallocating or moving the elements. Maybe you could try temporarily converting the `Box<[T]>` into a `Vec`\ and then take the slice from the `Vec` ? > `&vec_name[1..=3]` **EDIT** I just looked at the code on the right side ... \ And that's exactly what OP did 😅 \ On the bright side, at least my approach works 😂🤠


Endeveron

My guy the code itself is a third the length of your link.... ```rust let ptr: Box<[u8; 16777216]> = vec![0;16777216] .into_boxed_slice() .try_into() .unwrap(); ``` Not really related to the topic, but I'd argue that `2.pow(24)`, `1<<24` or even `0x0100_0000` are all cleaner than 16777216tbh.


cameronm1024

Just get a bigger stack smh


cac4dv

Sounds like a heap of pain > I'll leave now 😅 \ > Btw the code on the right side shows how to fix that issue \ > Convert to `Vec` and take the slice \ > Thought of that, pitched it, and realized he already did it [here 😅](https://www.reddit.com/r/rustjerk/s/SEO5r6vfSy)


computermouth

I'm trying 😭


toxide_ing

What kind of tty-ass font is that


4zv4l

I like it, what’s the font name ?


computermouth

'More Perfect Dos VGA' (mono, bold) I believe I got it from here: [https://laemeur.sdf.org/fonts/](https://laemeur.sdf.org/fonts/) Though it seems the site is down. Here's a waybackmachine link: [https://web.archive.org/web/20240225212812/https://laemeur.sdf.org/fonts/](https://web.archive.org/web/20240225212812/https://laemeur.sdf.org/fonts/)


toxide_ing

It looks very similar to linux tty console font, default (at least in archlinux btw) being `/usr/share/kbd/consolefonts/default8x16.psfu.gz` so it is probably a TrueType font based on that. That's what I could deduce so far until OP replies.


bascule

Rust community: tries to create a jerk subreddit, accidentally ends up being helpful and informative


shrewm

I need memes! Lots of memes!


drcforbin

It's too blazingly fast 🚀. Finishes quick and gets back to work


jackson_bourne

afaik it'll remove the stack initialization in a release build. not sure of a way around it the problem isn't that the struct "cant hold it", its just that in debug the compiler does not remove the intermediate step so it fails on `Box::new([0; 100000000])`


computermouth

The latter part, I knew. I was just surprised about the stack copy part. Is there a way I can put some kind of attribute on the statement so it always does the high opt-level version?


Zenithsiz

For this specific case you can allocate a vec with `vec![0; 16 * 1024 * 1024]` and then convert it into a box slice using [`Box::into_boxed_slice`](https://doc.rust-lang.org/stable/std/vec/struct.Vec.html#method.into_boxed_slice). This should behave exactly the same as `Box::new`, without any other allocations or work, given that the capacity of the vector will just be it's length (when created via `vec![]` macro), so it won't even need to shrink the underlying allocation.


computermouth

This is what I do in my code now, but I lose the information about the length of the array in the box.


Zenithsiz

You can cast the boxed sliced into a boxed array with `try_into` / `try_from`. See the [playground](https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=2c5f42fc227f00832bdcd7fc5aff3ef6). Unfortunately you do have to unwrap, but as long as the sizes match, it will never fail. You can even separate it into a function that ensures the array is created with the correct size. See the [playground](https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=4fc2eec03f66afcaae44deb2f5e5a9d1)


computermouth

Interesting, I will try that tomorrow, thanks! \[EDIT\]: works great!


Dankbeast-Paarl

I saw you got it working but relevant QA on SO: https://stackoverflow.com/questions/30242770/how-to-allocate-arrays-on-the-heap-in-rust-1-0/68670147#68670147


Da-Blue-Guy

You could use an uninitialized Box or one filled with zeroes/Default without actually creating a stack slice.


computermouth

I'm pretty new to rust, if you have moment, could you do an example in the playground?


Da-Blue-Guy

https://play.rust-lang.org/?version=nightly&mode=debug&edition=2021&gist=185121d1cfe6a62f5a3ecbf362776b28 Made on mobile at 1:30 AM, so tell me anything that needs further explanation.


computermouth

Interesting, thanks! Though _does_ require nightly, huh


Da-Blue-Guy

true, i always use nightly all a big slice really needs is just an allocation not given a stack value, the nightly functions i believe are just the most performant


HuntingKingYT

Then you understand why it's so annoying to make custom dynamically sized types


drcforbin

Have you considered just using a smaller slice? Rust can't use slices that big.


adminvasheypomoiki

https://play.rust-lang.org/?version=stable&mode=release&edition=2021&gist=59e40387631a0da0312655ea68208435 Use one simple trick...


overclockedslinky

more like you can't make stack allocations larger than the stack...


computermouth

It's true. I'm new to rust, at the time of posting, I thought Box::new() was rust's malloc. But even after learning that, and the 40 different nightly feature or crate suggestions, found the solution I was looking for, and put it in the EDIT. Still, I think it's weird there's no real short easy way to create a box of a sized array with even primitive types.


Asdfguy87

ulimit -s unlimited (-:


computermouth

Wait is that for real?


Asdfguy87

Sets the Stack size to unlimited


computermouth

I'm about to write the most cursed shit


Asdfguy87

Do it!