[libre-riscv-dev] [Bug 139] Add LD.X and ST.X? Strided

bugzilla-daemon at libre-riscv.org bugzilla-daemon at libre-riscv.org
Sun Oct 6 09:17:08 BST 2019


http://bugs.libre-riscv.org/show_bug.cgi?id=139

--- Comment #38 from Jacob Lifshay <programmerjake at gmail.com> ---
(In reply to Jacob Lifshay from comment #36)
> (In reply to Luke Kenneth Casson Leighton from comment #35)
> > i'm not able to say because i really do not understand how swizzle2 works.
> > i've spent several days researching it and simply cannot find anything,
> > not even based on the hints of swizzle2 being in LLVM IR.
> > 
> > can you please describe it in pseudocode in a simple loop?
> 
> sure.
> 
> https://play.rust-lang.org/?version=stable&mode=debug&edition=2018&gist=fa181fd305c70bde0372e0d99d873685
> 
> swizzle2 rd, rs1, rs2, rs3

There's also the swizzle instruction:

https://play.rust-lang.org/?version=stable&mode=debug&edition=2018&gist=17d9891a5ceae49402a948f2cbf29ba6

swizzle rd, rs1, rs2

pub trait SwizzleConstants: Copy + 'static {
    const CONSTANTS: &'static [Self; 4];
}

impl SwizzleConstants for u8 {
    const CONSTANTS: &'static [Self; 4] = &[0, 1, 0xFF, 0x7F];
}

impl SwizzleConstants for u16 {
    const CONSTANTS: &'static [Self; 4] = &[0, 1, 0xFFFF, 0x7FFF];
}

impl SwizzleConstants for f32 {
    const CONSTANTS: &'static [Self; 4] = &[0.0, 1.0, -1.0, 0.5];
}

// impl for other types too...

pub fn swizzle<Elm, Selector>(
    rd: &mut [Elm],
    rs1: &[Elm],
    rs2: &[Selector],
    vl: usize,
    destsubvl: usize,
    srcsubvl: usize)
where
    Elm: SwizzleConstants,
    // Selector is a copyable type that can be converted into u64
    Selector: Copy + Into<u64>,
{
    const FIELD_SIZE: usize = 3;
    const FIELD_MASK: u64 = 0b111;
    for vindex in 0..vl {
        let selector = rs2[vindex].into();
        // selector's type is u64
        if selector >> (FIELD_SIZE * destsubvl) != 0 {
            // handle illegal instruction trap
        }
        for i in 0..destsubvl {
            let mut sel_field = selector >> (FIELD_SIZE * i);
            sel_field &= FIELD_MASK;
            let src = if (sel_field & 0b100) == 0 {
                &rs1[(vindex * srcsubvl)..]
            } else {
                SwizzleConstants::CONSTANTS
            };
            sel_field &= 0b11;
            if sel_field as usize >= srcsubvl {
                // handle illegal instruction trap
            }
            let value = src[sel_field as usize];
            rd[vindex * destsubvl + i] = value;
        }
    }
}

-- 
You are receiving this mail because:
You are on the CC list for the bug.


More information about the libre-riscv-dev mailing list