by daurnimator on 4/22/20, 2:37 PM with 157 comments
by segfaultbuserr on 4/22/20, 3:53 PM
by Traster on 4/22/20, 3:38 PM
by beefhash on 4/22/20, 3:19 PM
[1] http://www.open-std.org/jtc1/sc22/wg14/www/docs/n2472.pdf
by 0xTJ on 4/22/20, 3:38 PM
by SlowRobotAhead on 4/22/20, 4:24 PM
Hmm, I haven’t been following that but it seems that...
> The result is massively larger FPGA/HLS programs than the programmer needed
And there it is.
Really seems odd to me to try and force procedural C into non-linear execution of FPGA. Like it seems super odd, and when talking about changes to C to help that... I really don’t get it.
This isn’t what C is for. What is the performance advantage over Verilog? How many people want n-bit into in C when automatically handled structures work well for most people.
Maybe I’m just not seeing the bigger picture here and that example was just poor?
by waltpad on 4/22/20, 5:02 PM
Also, what's the relationship between standard types and the new _ExtInts? Are _ExtInt(16) equivalent to shorts, or are they considered distinct and require explicit cast?
> In order to be consistent with the C Language, expressions that include a standard type will still follow integral promotion and conversion rules. All types smaller than int will be promoted, and the operation will then happen at the largest type. This can be surprising in the case where you add a short and an _ExtInt(15), where the result will be int. However, this ends up being the most consistent with the C language specification.
For instance, what if I choose to replace short by _ExtInt(16) in the above? What would be the promotion rule then?
Note that it was already possible to implement arbitrary sized ints for a size <= 64, by using bitfields (although it's possible that you could fall into UB territory in some situations, I've never used that to do modular arithmetic).
Edit: Ah, there's this notion of underlying type: one may use the nearest upper type to implement a given size, but nothing prevents to use a larger type, for instance:
struct short3_s { short value:3; };
struct longlong3_s { long long value:3; };
I don't know what the C standard says about that, but clearly these two types are not identical (sizeof will probably gives different results). What's will it be for _ExtInt? How these types will be converted?
Another idea:
what about
struct extint13_3_s {
_ExtInt(13) value:3;
};Will the above be possible? In other words, will it be possible to combine bitfields with this new feature?
I guess it's a much more complicated problem that it appears to be at first.
by jhj on 4/22/20, 5:06 PM
Every HLS vendor or language has their own, incompatible arbitrary bitwidth integer type at present. SystemC sc_int is different from Xilinx Vivado ap_int is different from Mentor Catapult ac_int is different from whatever Intel had for their Altera FPGAs. It's a real mess.
I'm hoping this is another small step to slowly move the industry into a more unified representation, or at least if LLVM support for this at the type level could enable faster simulation of designs on CPU by improving the CPU code that is emitted. What probably matters most for HLS though are the operations which are performed on the types (static or dynamic bit slicing, etc).
by derefr on 4/22/20, 4:17 PM
That “smallest type capable of storing this value” is a disappointing approach, IMHO. It’d be a lot more powerful to just be able to pass in bit patterns (base-2 literals) and have the resulting type match the lexical width of the literal. 0b0010X should have a bit-width of 4, not 2.
by dang on 4/22/20, 6:09 PM
Click 'More' at the bottom to page through it; it just keeps going.
by waynecochran on 4/22/20, 4:01 PM
by nabla9 on 4/22/20, 4:53 PM
If you have different representations in different languages it just creates unnecessary impedance mismatch. It would be better for everyone if you could just pass these types from language to language.
by rurban on 4/22/20, 6:46 PM
The feature is of course fantastic. But the syntax still looks bit overblown.
Type system-wise this seems to be more correct:
_ExtInt(a) + _ExtInt(b) => _ExtInt(MAX(a, b) +1)
And int + _ExtInt(15) might need a pragma or warning flag to warn about that promotion. One little int, or automatic int pollutes all.by fortran77 on 4/22/20, 4:37 PM
by ndesaulniers on 4/22/20, 11:09 PM
For a fun compiler bug in LLVM due to representation of arbitrary width integers, see: https://nickdesaulniers.github.io/blog/2020/04/06/off-by-two...
by Someone on 4/22/20, 10:06 PM
I don’t understand that choice. The result should be of the wider type, yes, but, for example, multiplying a _ExtInt(1) by a _ExtInt(1000) should take less hardware than multiplying two ExtInt(1000)s. So, why promote the narrower one to the wider type?
by saagarjha on 4/22/20, 3:17 PM
by ralusek on 4/22/20, 3:51 PM
Try in your browser console:
2n ** 4096n
// output (might have to scroll right)
1044388881413152506691752710716624382579964249047383780384233483283953907971557456848826811934997558340890106714439262837987573438185793607263236087851365277945956976543709998340361590134383718314428070011855946226376318839397712745672334684344586617496807908705803704071284048740118609114467977783598029006686938976881787785946905630190260940599579453432823469303026696443059025015972399867714215541693835559885291486318237914434496734087811872639496475100189041349008417061675093668333850551032972088269550769983616369411933015213796825837188091833656751221318492846368125550225998300412344784862595674492194617023806505913245610825731835380087608622102834270197698202313169017678006675195485079921636419370285375124784014907159135459982790513399611551794271106831134090584272884279791554849782954323534517065223269061394905987693002122963395687782878948440616007412945674919823050571642377154816321380631045902916136926708342856440730447899971901781465763473223850267253059899795996090799469201774624817718449867455659250178329070473119433165550807568221846571746373296884912819520317457002440926616910874148385078411929804522981857338977648103126085903001302413467189726673216491511131602920781738033436090243804708340403154190336n
To use, just add `n` after the number as literal notation, or can cast any Number x with BigInt(x). BigInts may only do operations with other BigInts, so make sure to cast any Numbers where applicable.I know this is about C, I thought I'd just mention it, since many people seem to be unaware of this.
by SloopJon on 4/22/20, 3:43 PM
Safe to say that a feature like this would be standardized by 2022 at the earliest?
by drfuchs on 4/22/20, 4:49 PM
by senozhatsky on 4/23/20, 1:37 AM
by pjmlp on 4/22/20, 6:35 PM
by mshockwave on 4/22/20, 5:27 PM
by rightbyte on 4/22/20, 3:10 PM
by xyzzy2020 on 4/22/20, 3:38 PM
by detaro on 4/22/20, 3:40 PM
> The New Clang _ExtInt Feature Provides Exact Bitwidth Integer Types