Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(300)

Side by Side Diff: src/IceInstARM32.cpp

Issue 1663053008: Fix vector load/stores in the ARM assembler. (Closed) Base URL: https://chromium.googlesource.com/native_client/pnacl-subzero.git@master
Patch Set: Fix nits. Created 4 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/IceAssemblerARM32.cpp ('k') | tests_lit/assembler/arm32/vldr-vector.ll » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 //===- subzero/src/IceInstARM32.cpp - ARM32 instruction implementation ----===// 1 //===- subzero/src/IceInstARM32.cpp - ARM32 instruction implementation ----===//
2 // 2 //
3 // The Subzero Code Generator 3 // The Subzero Code Generator
4 // 4 //
5 // This file is distributed under the University of Illinois Open Source 5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details. 6 // License. See LICENSE.TXT for details.
7 // 7 //
8 //===----------------------------------------------------------------------===// 8 //===----------------------------------------------------------------------===//
9 /// 9 ///
10 /// \file 10 /// \file
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after
58 CondARM32::Cond Opposite; 58 CondARM32::Cond Opposite;
59 const char *EmitString; 59 const char *EmitString;
60 } InstARM32CondAttributes[] = { 60 } InstARM32CondAttributes[] = {
61 #define X(tag, encode, opp, emit) \ 61 #define X(tag, encode, opp, emit) \
62 { CondARM32::opp, emit } \ 62 { CondARM32::opp, emit } \
63 , 63 ,
64 ICEINSTARM32COND_TABLE 64 ICEINSTARM32COND_TABLE
65 #undef X 65 #undef X
66 }; 66 };
67 67
68 size_t getVecElmtBitsize(Type Ty) {
69 return typeWidthInBytes(typeElementType(Ty)) * CHAR_BIT;
70 }
71
68 } // end of anonymous namespace 72 } // end of anonymous namespace
69 73
70 const char *InstARM32::getWidthString(Type Ty) { 74 const char *InstARM32::getWidthString(Type Ty) {
71 return TypeARM32Attributes[Ty].WidthString; 75 return TypeARM32Attributes[Ty].WidthString;
72 } 76 }
73 77
74 const char *InstARM32::getVecWidthString(Type Ty) { 78 const char *InstARM32::getVecWidthString(Type Ty) {
75 return TypeARM32Attributes[Ty].VecWidthString; 79 return TypeARM32Attributes[Ty].VecWidthString;
76 } 80 }
77 81
(...skipping 1478 matching lines...) Expand 10 before | Expand all | Expand 10 after
1556 return; 1560 return;
1557 Ostream &Str = Func->getContext()->getStrEmit(); 1561 Ostream &Str = Func->getContext()->getStrEmit();
1558 assert(getSrcSize() == 1); 1562 assert(getSrcSize() == 1);
1559 assert(getDest()->hasReg()); 1563 assert(getDest()->hasReg());
1560 Variable *Dest = getDest(); 1564 Variable *Dest = getDest();
1561 Type Ty = Dest->getType(); 1565 Type Ty = Dest->getType();
1562 const bool IsVector = isVectorType(Ty); 1566 const bool IsVector = isVectorType(Ty);
1563 const bool IsScalarFloat = isScalarFloatingType(Ty); 1567 const bool IsScalarFloat = isScalarFloatingType(Ty);
1564 const char *ActualOpcode = 1568 const char *ActualOpcode =
1565 IsVector ? "vld1" : (IsScalarFloat ? "vldr" : "ldr"); 1569 IsVector ? "vld1" : (IsScalarFloat ? "vldr" : "ldr");
1566 const char *VectorMarker = IsVector ? ".64" : "";
1567 const char *WidthString = IsVector ? "" : getWidthString(Ty); 1570 const char *WidthString = IsVector ? "" : getWidthString(Ty);
1568 Str << "\t" << ActualOpcode; 1571 Str << "\t" << ActualOpcode;
1569 const bool IsVInst = IsVector || IsScalarFloat; 1572 const bool IsVInst = IsVector || IsScalarFloat;
1570 if (IsVInst) { 1573 if (IsVInst) {
1571 Str << getPredicate() << WidthString; 1574 Str << getPredicate() << WidthString;
1572 } else { 1575 } else {
1573 Str << WidthString << getPredicate(); 1576 Str << WidthString << getPredicate();
1574 } 1577 }
1575 Str << VectorMarker << "\t"; 1578 if (IsVector)
1579 Str << "." << getVecElmtBitsize(Ty);
1580 Str << "\t";
1576 getDest()->emit(Func); 1581 getDest()->emit(Func);
1577 Str << ", "; 1582 Str << ", ";
1578 getSrc(0)->emit(Func); 1583 getSrc(0)->emit(Func);
1579 } 1584 }
1580 1585
1581 template <> void InstARM32Ldr::emitIAS(const Cfg *Func) const { 1586 template <> void InstARM32Ldr::emitIAS(const Cfg *Func) const {
1582 assert(getSrcSize() == 1); 1587 assert(getSrcSize() == 1);
1588 auto *Asm = Func->getAssembler<ARM32::AssemblerARM32>();
1583 Variable *Dest = getDest(); 1589 Variable *Dest = getDest();
1584 const Type DestTy = Dest->getType(); 1590 const Type DestTy = Dest->getType();
1585 auto *Asm = Func->getAssembler<ARM32::AssemblerARM32>(); 1591 switch (DestTy) {
1586 if (isScalarFloatingType(DestTy)) { 1592 default:
1587 switch (DestTy) { 1593 llvm::report_fatal_error("Ldr on unknown type: " + typeIceString(DestTy));
1588 default: 1594 case IceType_i1:
1589 // TODO(kschimpf) Does this happen? 1595 case IceType_i8:
1590 Asm->setNeedsTextFixup(); 1596 case IceType_i16:
1591 break; 1597 case IceType_i32:
1592 case IceType_f32: 1598 case IceType_i64:
1593 Asm->vldrs(Dest, getSrc(0), getPredicate(), Func->getTarget());
1594 break;
1595 case IceType_f64:
1596 Asm->vldrd(Dest, getSrc(0), getPredicate(), Func->getTarget());
1597 break;
1598 }
1599 } else if (isVectorType(DestTy))
1600 // TODO(kschimpf) Handle case.
1601 Asm->setNeedsTextFixup();
1602 else
1603 Asm->ldr(Dest, getSrc(0), getPredicate(), Func->getTarget()); 1599 Asm->ldr(Dest, getSrc(0), getPredicate(), Func->getTarget());
1604 if (Asm->needsTextFixup()) 1600 break;
1605 emitUsingTextFixup(Func); 1601 case IceType_f32:
1602 Asm->vldrs(Dest, getSrc(0), getPredicate(), Func->getTarget());
1603 break;
1604 case IceType_f64:
1605 Asm->vldrd(Dest, getSrc(0), getPredicate(), Func->getTarget());
1606 break;
1607 case IceType_v16i8:
1608 case IceType_v8i16:
1609 case IceType_v4i32:
1610 case IceType_v4f32:
1611 Asm->vld1qr(getVecElmtBitsize(DestTy), Dest, getSrc(0), Func->getTarget());
1612 break;
1613 }
1606 } 1614 }
1607 1615
1608 template <> void InstARM32Ldrex::emit(const Cfg *Func) const { 1616 template <> void InstARM32Ldrex::emit(const Cfg *Func) const {
1609 if (!BuildDefs::dump()) 1617 if (!BuildDefs::dump())
1610 return; 1618 return;
1611 Ostream &Str = Func->getContext()->getStrEmit(); 1619 Ostream &Str = Func->getContext()->getStrEmit();
1612 assert(getSrcSize() == 1); 1620 assert(getSrcSize() == 1);
1613 assert(getDest()->hasReg()); 1621 assert(getDest()->hasReg());
1614 Variable *Dest = getDest(); 1622 Variable *Dest = getDest();
1615 Type DestTy = Dest->getType(); 1623 Type DestTy = Dest->getType();
(...skipping 275 matching lines...) Expand 10 before | Expand all | Expand 10 after
1891 void InstARM32Str::emit(const Cfg *Func) const { 1899 void InstARM32Str::emit(const Cfg *Func) const {
1892 if (!BuildDefs::dump()) 1900 if (!BuildDefs::dump())
1893 return; 1901 return;
1894 Ostream &Str = Func->getContext()->getStrEmit(); 1902 Ostream &Str = Func->getContext()->getStrEmit();
1895 assert(getSrcSize() == 2); 1903 assert(getSrcSize() == 2);
1896 Type Ty = getSrc(0)->getType(); 1904 Type Ty = getSrc(0)->getType();
1897 const bool IsVectorStore = isVectorType(Ty); 1905 const bool IsVectorStore = isVectorType(Ty);
1898 const bool IsScalarFloat = isScalarFloatingType(Ty); 1906 const bool IsScalarFloat = isScalarFloatingType(Ty);
1899 const char *Opcode = 1907 const char *Opcode =
1900 IsVectorStore ? "vst1" : (IsScalarFloat ? "vstr" : "str"); 1908 IsVectorStore ? "vst1" : (IsScalarFloat ? "vstr" : "str");
1901 const char *VecEltWidthString = IsVectorStore ? ".64" : "";
1902 Str << "\t" << Opcode; 1909 Str << "\t" << Opcode;
1903 const bool IsVInst = IsVectorStore || IsScalarFloat; 1910 const bool IsVInst = IsVectorStore || IsScalarFloat;
1904 if (IsVInst) { 1911 if (IsVInst) {
1905 Str << getPredicate() << getWidthString(Ty); 1912 Str << getPredicate() << getWidthString(Ty);
1906 } else { 1913 } else {
1907 Str << getWidthString(Ty) << getPredicate(); 1914 Str << getWidthString(Ty) << getPredicate();
1908 } 1915 }
1909 Str << VecEltWidthString << "\t"; 1916 if (IsVectorStore)
1917 Str << "." << getVecElmtBitsize(Ty);
1918 Str << "\t";
1910 getSrc(0)->emit(Func); 1919 getSrc(0)->emit(Func);
1911 Str << ", "; 1920 Str << ", ";
1912 getSrc(1)->emit(Func); 1921 getSrc(1)->emit(Func);
1913 } 1922 }
1914 1923
1915 void InstARM32Str::emitIAS(const Cfg *Func) const { 1924 void InstARM32Str::emitIAS(const Cfg *Func) const {
1916 assert(getSrcSize() == 2); 1925 assert(getSrcSize() == 2);
1917 Type Ty = getSrc(0)->getType();
1918 auto *Asm = Func->getAssembler<ARM32::AssemblerARM32>(); 1926 auto *Asm = Func->getAssembler<ARM32::AssemblerARM32>();
1919 if (isScalarFloatingType(Ty)) { 1927 const Operand *Src0 = getSrc(0);
1920 switch (Ty) { 1928 const Operand *Src1 = getSrc(1);
1921 default: 1929 Type Ty = Src0->getType();
1922 // TODO(kschimpf) Does this happen? 1930 switch (Ty) {
1923 Asm->setNeedsTextFixup(); 1931 default:
1924 break; 1932 llvm::report_fatal_error("Str on unknown type: " + typeIceString(Ty));
1925 case IceType_f32: 1933 case IceType_i1:
1926 Asm->vstrs(getSrc(0), getSrc(1), getPredicate(), Func->getTarget()); 1934 case IceType_i8:
1927 break; 1935 case IceType_i16:
1928 case IceType_f64: 1936 case IceType_i32:
1929 Asm->vstrd(getSrc(0), getSrc(1), getPredicate(), Func->getTarget()); 1937 case IceType_i64:
1930 break; 1938 Asm->str(Src0, Src1, getPredicate(), Func->getTarget());
1931 } 1939 break;
1932 } else if (isVectorType(Ty)) 1940 case IceType_f32:
1933 // TODO(kschimpf) Handle case. 1941 Asm->vstrs(Src0, Src1, getPredicate(), Func->getTarget());
1934 Asm->setNeedsTextFixup(); 1942 break;
1935 else 1943 case IceType_f64:
1936 Asm->str(getSrc(0), getSrc(1), getPredicate(), Func->getTarget()); 1944 Asm->vstrd(Src0, Src1, getPredicate(), Func->getTarget());
1937 if (Asm->needsTextFixup()) 1945 break;
1938 emitUsingTextFixup(Func); 1946 case IceType_v16i8:
1947 case IceType_v8i16:
1948 case IceType_v4i32:
1949 case IceType_v4f32:
1950 Asm->vst1qr(getVecElmtBitsize(Ty), Src0, Src1, Func->getTarget());
1951 break;
1952 }
1939 } 1953 }
1940 1954
1941 void InstARM32Str::dump(const Cfg *Func) const { 1955 void InstARM32Str::dump(const Cfg *Func) const {
1942 if (!BuildDefs::dump()) 1956 if (!BuildDefs::dump())
1943 return; 1957 return;
1944 Ostream &Str = Func->getContext()->getStrDump(); 1958 Ostream &Str = Func->getContext()->getStrDump();
1945 Type Ty = getSrc(0)->getType(); 1959 Type Ty = getSrc(0)->getType();
1946 dumpOpcodePred(Str, "str", Ty); 1960 dumpOpcodePred(Str, "str", Ty);
1947 Str << " "; 1961 Str << " ";
1948 getSrc(1)->dump(Func); 1962 getSrc(1)->dump(Func);
(...skipping 584 matching lines...) Expand 10 before | Expand all | Expand 10 after
2533 2547
2534 template class InstARM32FourAddrGPR<InstARM32::Mla>; 2548 template class InstARM32FourAddrGPR<InstARM32::Mla>;
2535 template class InstARM32FourAddrGPR<InstARM32::Mls>; 2549 template class InstARM32FourAddrGPR<InstARM32::Mls>;
2536 2550
2537 template class InstARM32CmpLike<InstARM32::Cmn>; 2551 template class InstARM32CmpLike<InstARM32::Cmn>;
2538 template class InstARM32CmpLike<InstARM32::Cmp>; 2552 template class InstARM32CmpLike<InstARM32::Cmp>;
2539 template class InstARM32CmpLike<InstARM32::Tst>; 2553 template class InstARM32CmpLike<InstARM32::Tst>;
2540 2554
2541 } // end of namespace ARM32 2555 } // end of namespace ARM32
2542 } // end of namespace Ice 2556 } // end of namespace Ice
OLDNEW
« no previous file with comments | « src/IceAssemblerARM32.cpp ('k') | tests_lit/assembler/arm32/vldr-vector.ll » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698