Lokathor / wide

A crate to help you go wide. By which I mean use SIMD stuff.
https://docs.rs/wide
zlib License
279 stars 23 forks source link

Add f32x4::trunc_int and f32x8::trunc_int #67

Closed RazrFalcon closed 3 years ago

RazrFalcon commented 3 years ago

Closes #66

RazrFalcon commented 3 years ago

I've added this method only to f32x4, because I have no idea how it should be implemented for other types.

Also, looks like f32::trunc is not available in core.

Lokathor commented 3 years ago

hmm, since normal trunc is f32 output, this should probably be called trunc_int to indicate it's changing the type.

funny that you'd submit this today of all days, stdsimd has a similar pr just this morning: https://github.com/rust-lang/stdsimd/pull/34

You should be able to do this at least for f32x8 I think.

And yeah, so you'd have to cfg around this (i forget if wide has a std feature yet?) or implement a truncation function. You could use libm for inspiration here.

RazrFalcon commented 3 years ago

this should probably be called trunc_int

Ok.

Yes, this is an interesting coincidence. I blame the fact that it's weekends.

Yes, I'm using std feature for this method.

I have a strange bug, where 3.7_f32.trunc() returns 4 on i586. Investigating.

PS: Can I use stdsimd now or is it just for std?

Lokathor commented 3 years ago

stdsimd is not yet available in the standard library. You can use it as a stand alone crate on nightly, but i don't think it's published on crates.io even. It's super new and super bare bones. Probably give it a few months to grow.

Lokathor commented 3 years ago

and yeah, uh, i586 is problem-town. you could cfg around that if you want, i wouldn't mind. Just make the method not exist at all on that platform (and ditto on the test). if someone actually uses i586 they can fix it then, but i don't think anyone really does much with it.

RazrFalcon commented 3 years ago

Ok, I will wait for it.

Just make the method not exist at all on that platform

Is there a way to do this?

Lokathor commented 3 years ago

You can place a cfg on the method itself

#[cfg(cond)]
fn foo(self) -> out {
  //
}

then it will just only exist on select targets

RazrFalcon commented 3 years ago

Yes, of course. I've meant the actual condition. We don't have i586 target_arch.

Lokathor commented 3 years ago

oh! x86 or x86_64 target_arch but not target_feature sse

RazrFalcon commented 3 years ago

Done. I've also added it to f32x8.

RazrFalcon commented 3 years ago

On the other hand, I actually need a fallback implementation.

RazrFalcon commented 3 years ago

It passes all the tests, but it will not compile on ARM...

Lokathor commented 3 years ago

actually, sorry, i was answering via my phone for a bit and just sat down and re-read it properly.

Are you saying that the standard library f32::trunc can give bad results on i586?

RazrFalcon commented 3 years ago

Yes, it returns 4 for 3.7

https://github.com/Lokathor/wide/runs/1239019400

PS: i586 is tier2, so anything could happen, I guess.

Lokathor commented 3 years ago

That's uh... a fun bug. @workingjubilee you might add that to your collection of i586 weirdness

RazrFalcon commented 3 years ago

Yes... So the question is how to ignore i586 via cfg.

Lokathor commented 3 years ago

So, on the function you'd probably want to have

#[cfg(any(
  target_feature = "sse",
  all(feature = "std", not(any(target_arch = "x86", target_arch = "x86_64")))
))]

"if we have sse, or if we have the standard library on some other arch"

RazrFalcon commented 3 years ago

And I though that I had to add just one line of code... This is why I want to use an existing SIMD crate instead of custom one.

RazrFalcon commented 3 years ago

Looks like it's done.

Lokathor commented 3 years ago

Released wide-0.5.6

workingjubilee commented 3 years ago

this utter nonsense of a bug

LOVIN' IT.

Lokathor commented 3 years ago

Correction: wide-0.5.6 is yanked, released as wide-0.6.0

programmerjake commented 3 years ago

Yes, it returns 4 for 3.7

https://github.com/Lokathor/wide/runs/1239019400

PS: i586 is tier2, so anything could happen, I guess.

It's obviously wrong since you're rounding then calling trunc, so round converts 3.7 to 4 and then trunc converts 4 to 4. No wonder it causes tests to fail!

RazrFalcon commented 3 years ago

@programmerjake Good catch. I've simply copy-pasted the round_int code... Still strange that it has different results.

programmerjake commented 3 years ago

Also, sorry if I came across as insulting, that wasn't intended

RazrFalcon commented 3 years ago

@programmerjake No worry =)