summaryrefslogtreecommitdiff
path: root/src/arch/arm
diff options
context:
space:
mode:
authorGabe Black <gblack@eecs.umich.edu>2010-06-02 12:58:06 -0500
committerGabe Black <gblack@eecs.umich.edu>2010-06-02 12:58:06 -0500
commit3f12eb02ab3dcde6e96e2ae0d50710bf5541ec54 (patch)
tree8af9326a86c000f6ad08a219b480dbb3605d94f4 /src/arch/arm
parent29acf9516ca8aa564026a9c5588205fe129ec912 (diff)
downloadgem5-3f12eb02ab3dcde6e96e2ae0d50710bf5541ec54.tar.xz
ARM: Implement the unsigned 8 bit and 16 bit vector adds and subtracts.
Diffstat (limited to 'src/arch/arm')
-rw-r--r--src/arch/arm/isa/insts/data.isa105
1 files changed, 105 insertions, 0 deletions
diff --git a/src/arch/arm/isa/insts/data.isa b/src/arch/arm/isa/insts/data.isa
index 04e62f27b..4efbae574 100644
--- a/src/arch/arm/isa/insts/data.isa
+++ b/src/arch/arm/isa/insts/data.isa
@@ -501,4 +501,109 @@ let {{
replaceBits(resTemp, 31, 16, midRes);
Dest = resTemp;
''', flagType="none", buildCc=False)
+
+ buildRegDataInst("uadd16", '''
+ uint32_t geBits = 0;
+ resTemp = 0;
+ for (unsigned i = 0; i < 2; i++) {
+ int high = (i + 1) * 16 - 1;
+ int low = i * 16;
+ int32_t midRes = bits(Op1, high, low) +
+ bits(Op2, high, low);
+ if (midRes >= 0x10000) {
+ geBits = geBits | (0x3 << (i * 2));
+ }
+ replaceBits(resTemp, high, low, midRes);
+ }
+ Dest = resTemp;
+ resTemp = geBits;
+ ''', flagType="ge", buildNonCc=False)
+ buildRegDataInst("uadd8", '''
+ uint32_t geBits = 0;
+ resTemp = 0;
+ for (unsigned i = 0; i < 4; i++) {
+ int high = (i + 1) * 8 - 1;
+ int low = i * 8;
+ int32_t midRes = bits(Op1, high, low) +
+ bits(Op2, high, low);
+ if (midRes >= 0x100) {
+ geBits = geBits | (1 << i);
+ }
+ replaceBits(resTemp, high, low, midRes);
+ }
+ Dest = resTemp;
+ resTemp = geBits;
+ ''', flagType="ge", buildNonCc=False)
+ buildRegDataInst("usub16", '''
+ uint32_t geBits = 0;
+ resTemp = 0;
+ for (unsigned i = 0; i < 2; i++) {
+ int high = (i + 1) * 16 - 1;
+ int low = i * 16;
+ int32_t midRes = bits(Op1, high, low) -
+ bits(Op2, high, low);
+ if (midRes >= 0) {
+ geBits = geBits | (0x3 << (i * 2));
+ }
+ replaceBits(resTemp, high, low, midRes);
+ }
+ Dest = resTemp;
+ resTemp = geBits;
+ ''', flagType="ge", buildNonCc=False)
+ buildRegDataInst("usub8", '''
+ uint32_t geBits = 0;
+ resTemp = 0;
+ for (unsigned i = 0; i < 4; i++) {
+ int high = (i + 1) * 8 - 1;
+ int low = i * 8;
+ int32_t midRes = bits(Op1, high, low) -
+ bits(Op2, high, low);
+ if (midRes >= 0) {
+ geBits = geBits | (1 << i);
+ }
+ replaceBits(resTemp, high, low, midRes);
+ }
+ Dest = resTemp;
+ resTemp = geBits;
+ ''', flagType="ge", buildNonCc=False)
+ buildRegDataInst("uasx", '''
+ int32_t midRes, geBits = 0;
+ resTemp = 0;
+ int64_t arg1Low = bits(Op1.sw, 15, 0);
+ int64_t arg1High = bits(Op1.sw, 31, 16);
+ int64_t arg2Low = bits(Op2.sw, 15, 0);
+ int64_t arg2High = bits(Op2.sw, 31, 16);
+ midRes = arg1Low - arg2High;
+ if (midRes >= 0) {
+ geBits = geBits | 0x3;
+ }
+ replaceBits(resTemp, 15, 0, midRes);
+ midRes = arg1High + arg2Low;
+ if (midRes >= 0x10000) {
+ geBits = geBits | 0xc;
+ }
+ replaceBits(resTemp, 31, 16, midRes);
+ Dest = resTemp;
+ resTemp = geBits;
+ ''', flagType="ge", buildNonCc=False)
+ buildRegDataInst("usax", '''
+ int32_t midRes, geBits = 0;
+ resTemp = 0;
+ int64_t arg1Low = bits(Op1.sw, 15, 0);
+ int64_t arg1High = bits(Op1.sw, 31, 16);
+ int64_t arg2Low = bits(Op2.sw, 15, 0);
+ int64_t arg2High = bits(Op2.sw, 31, 16);
+ midRes = arg1Low + arg2High;
+ if (midRes >= 0x10000) {
+ geBits = geBits | 0x3;
+ }
+ replaceBits(resTemp, 15, 0, midRes);
+ midRes = arg1High - arg2Low;
+ if (midRes >= 0) {
+ geBits = geBits | 0xc;
+ }
+ replaceBits(resTemp, 31, 16, midRes);
+ Dest = resTemp;
+ resTemp = geBits;
+ ''', flagType="ge", buildNonCc=False)
}};