xls icon indicating copy to clipboard operation
xls copied to clipboard

Assigning bit-slices to tuple with pattern matching ?

Open hzeller opened this issue 2 years ago • 3 comments

Sometimes, the bit-splicing operations can get a bit hard to read, in particular when extracting multiple ranges.

What would be good is to have an option to write assigning to a tuple in a pattern-matching style. Since the right-hand side is of known width, we can assign bits to the left-hand side to a tuple that sums up to the exact same number of bits (and even determine one unknown bit-width).

In the IR, this would just be regular bit-slices.

 let x = u32:42;
 let (foo:u1, bar:u2, baz:u29) = x;     // bit-splice with all widths defined
 let (sign:u1, exp, mantissa:u23) = x;  // bit-splice, auto-determine width of exp
 let (sign, exp, mantissa:u23) = x;     // ERROR: two fields without width
 let (sign:u1, _, rounding:u1) = x;     // can also be used for "don't care"

Possible relevant issue for discussion: bit-endianness needs to be intuitive ( Similar issue with with other bit-slice operations). Most intuitive would be if it behaves opposite to ++:

let (sign:u1, exp, mantissa:u23) = x; 
let y = sign ++ exp ++ mantissa;
assert_eq(x, y);

hzeller avatar Oct 31 '23 22:10 hzeller

Just putting my thoughts from xls-dev in here.

Imo this is something we probably want to have a more explicit std magic function for.

The rest of dslx is really against any sort of automatic conversion (even let x: u8 = ...; let y : u16 = x needs a cast) so I don't see this as any different.

I'd advocate for something like BitSlice!<(u1, u2, u3)>!(x) in the standard library implemented as a builtin.

This does prevent you from doing any sort of "don't care about the middle bits" style thing without making it even more magical.

allight avatar Oct 31 '23 23:10 allight

maybe an explicit cast from scalar to tuple would be more consistent with existing dslx semantics?

let (foo, bar, baz) = u32:41 as (u1, u2, u29);

it could even leverage @dplassgit rest of tuple operator.

let (foo, .., baz) = u32:41 as (u1, u2, u5, u24);

proppy avatar Aug 28 '24 00:08 proppy

I still kind of prefer the magic-macro version just for pushing the user to think about what they're doing but @proppy's suggestion seems fine to me.

allight avatar Aug 28 '24 00:08 allight

In the spirit of https://github.com/google/xls/issues/415, this would also provide familiarity to hardware engineers, who can use the { } assignment pattern in SystemVerilog, e.g.

assign {baz, bar, foo} = some_bigger_vector;

mikex-oss avatar Oct 29 '24 19:10 mikex-oss