Skip to content

Commit fb5ef41

Browse files
committed
[NFC] Remove switch on opcode by inheriting from SPIRVInstTemplateBase
Make the following classes inherit from SPIRVInstTemplateBase: - SPIRVSelect - SPIRVVectorShuffle - SPIRVCompositeExtract - SPIRVCompositeInsert This allows removing a switch on opcode in SPIRVInstruction.cpp. Fixes #1072
1 parent 211c7dc commit fb5ef41

File tree

3 files changed

+67
-150
lines changed

3 files changed

+67
-150
lines changed

lib/SPIRV/libSPIRV/SPIRVInstruction.cpp

Lines changed: 2 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -244,39 +244,8 @@ SPIRVInstruction *createInstFromSpecConstantOp(SPIRVSpecConstantOp *Inst) {
244244
assert(isSpecConstantOpAllowedOp(OC) &&
245245
"Op code not allowed for OpSpecConstantOp");
246246
Ops.erase(Ops.begin(), Ops.begin() + 1);
247-
switch (OC) {
248-
case OpVectorShuffle: {
249-
std::vector<SPIRVWord> Comp;
250-
for (auto I = Ops.begin() + 2, E = Ops.end(); I != E; ++I) {
251-
Comp.push_back(*I);
252-
}
253-
return new SPIRVVectorShuffle(Inst->getId(), Inst->getType(), Ops[0],
254-
Ops[1], Comp, nullptr, Inst->getModule());
255-
}
256-
case OpCompositeExtract: {
257-
std::vector<SPIRVWord> Indices;
258-
for (auto I = Ops.begin() + 1, E = Ops.end(); I != E; ++I) {
259-
Indices.push_back(*I);
260-
}
261-
return new SPIRVCompositeExtract(Inst->getType(), Inst->getId(), Ops[0],
262-
Indices, nullptr, Inst->getModule());
263-
}
264-
case OpCompositeInsert: {
265-
std::vector<SPIRVWord> Indices;
266-
for (auto I = Ops.begin() + 2, E = Ops.end(); I != E; ++I) {
267-
Indices.push_back(*I);
268-
}
269-
return new SPIRVCompositeInsert(Inst->getType(), Inst->getId(), Ops[0],
270-
Ops[1], Indices, nullptr,
271-
Inst->getModule());
272-
}
273-
case OpSelect:
274-
return new SPIRVSelect(Inst->getId(), Inst->getType(), Ops[0], Ops[1],
275-
Ops[2], nullptr, Inst->getModule());
276-
default:
277-
return SPIRVInstTemplateBase::create(OC, Inst->getType(), Inst->getId(),
278-
Ops, nullptr, Inst->getModule());
279-
}
247+
return SPIRVInstTemplateBase::create(OC, Inst->getType(), Inst->getId(), Ops,
248+
nullptr, Inst->getModule());
280249
}
281250

282251
} // namespace SPIRV

lib/SPIRV/libSPIRV/SPIRVInstruction.h

Lines changed: 46 additions & 103 deletions
Original file line numberDiff line numberDiff line change
@@ -971,27 +971,18 @@ _SPIRV_OP(Ordered)
971971
_SPIRV_OP(Unordered)
972972
#undef _SPIRV_OP
973973

974-
class SPIRVSelect : public SPIRVInstruction {
974+
class SPIRVSelectBase : public SPIRVInstTemplateBase {
975975
public:
976-
// Complete constructor
977-
SPIRVSelect(SPIRVId TheId, SPIRVType *TheType, SPIRVId TheCondition,
978-
SPIRVId TheOp1, SPIRVId TheOp2, SPIRVBasicBlock *TheBB,
979-
SPIRVModule *TheM)
980-
: SPIRVInstruction(6, OpSelect, TheType, TheId, TheBB, TheM),
981-
Condition(TheCondition), Op1(TheOp1), Op2(TheOp2) {
982-
validate();
983-
}
984-
// Incomplete constructor
985-
SPIRVSelect()
986-
: SPIRVInstruction(OpSelect), Condition(SPIRVID_INVALID),
987-
Op1(SPIRVID_INVALID), Op2(SPIRVID_INVALID) {}
988-
SPIRVValue *getCondition() { return getValue(Condition); }
989-
SPIRVValue *getTrueValue() { return getValue(Op1); }
990-
SPIRVValue *getFalseValue() { return getValue(Op2); }
976+
SPIRVValue *getCondition() { return getValue(Ops[0]); }
977+
SPIRVValue *getTrueValue() { return getValue(Ops[1]); }
978+
SPIRVValue *getFalseValue() { return getValue(Ops[2]); }
991979

992980
protected:
993-
_SPIRV_DEF_ENCDEC5(Type, Id, Condition, Op1, Op2)
994981
void validate() const override {
982+
SPIRVId Condition = Ops[0];
983+
SPIRVId Op1 = Ops[1];
984+
SPIRVId Op2 = Ops[2];
985+
995986
SPIRVInstruction::validate();
996987
if (getValue(Condition)->isForward() || getValue(Op1)->isForward() ||
997988
getValue(Op2)->isForward())
@@ -1005,11 +996,10 @@ class SPIRVSelect : public SPIRVInstruction {
1005996
assert(getType() == getValueType(Op1) && getType() == getValueType(Op2) &&
1006997
"Inconsistent type");
1007998
}
1008-
SPIRVId Condition;
1009-
SPIRVId Op1;
1010-
SPIRVId Op2;
1011999
};
10121000

1001+
typedef SPIRVInstTemplate<SPIRVSelectBase, OpSelect, true, 6> SPIRVSelect;
1002+
10131003
class SPIRVSelectionMerge : public SPIRVInstruction {
10141004
public:
10151005
static const Op OC = OpSelectionMerge;
@@ -1899,87 +1889,58 @@ class SPIRVCompositeConstruct : public SPIRVInstruction {
18991889
std::vector<SPIRVId> Constituents;
19001890
};
19011891

1902-
class SPIRVCompositeExtract : public SPIRVInstruction {
1892+
class SPIRVCompositeExtractBase : public SPIRVInstTemplateBase {
19031893
public:
1904-
const static Op OC = OpCompositeExtract;
1905-
// Complete constructor
1906-
SPIRVCompositeExtract(SPIRVType *TheType, SPIRVId TheId, SPIRVId TheComposite,
1907-
const std::vector<SPIRVWord> &TheIndices,
1908-
SPIRVBasicBlock *TheBB, SPIRVModule *TheM)
1909-
: SPIRVInstruction(TheIndices.size() + 4, OC, TheType, TheId, TheBB,
1910-
TheM),
1911-
Composite(TheComposite), Indices(TheIndices) {
1912-
validate();
1894+
SPIRVValue *getComposite() { return getValue(Ops[0]); }
1895+
const std::vector<SPIRVWord> getIndices() const {
1896+
return std::vector<SPIRVWord>(Ops.begin() + 1, Ops.end());
19131897
}
1914-
// Incomplete constructor
1915-
SPIRVCompositeExtract() : SPIRVInstruction(OC), Composite(SPIRVID_INVALID) {}
1916-
1917-
SPIRVValue *getComposite() { return getValue(Composite); }
1918-
const std::vector<SPIRVWord> &getIndices() const { return Indices; }
19191898

19201899
protected:
1921-
void setWordCount(SPIRVWord TheWordCount) override {
1922-
SPIRVEntry::setWordCount(TheWordCount);
1923-
Indices.resize(TheWordCount - 4);
1924-
}
1925-
_SPIRV_DEF_ENCDEC4(Type, Id, Composite, Indices)
19261900
// ToDo: validate the result type is consistent with the base type and indices
19271901
// need to trace through the base type for struct types
19281902
void validate() const override {
19291903
SPIRVInstruction::validate();
1904+
assert(OpCode == OpCompositeExtract);
1905+
SPIRVId Composite = Ops[0];
1906+
(void)Composite;
19301907
assert(getValueType(Composite)->isTypeArray() ||
19311908
getValueType(Composite)->isTypeStruct() ||
19321909
getValueType(Composite)->isTypeVector());
19331910
}
1934-
SPIRVId Composite;
1935-
std::vector<SPIRVWord> Indices;
19361911
};
19371912

1938-
class SPIRVCompositeInsert : public SPIRVInstruction {
1913+
typedef SPIRVInstTemplate<SPIRVCompositeExtractBase, OpCompositeExtract, true,
1914+
4, true>
1915+
SPIRVCompositeExtract;
1916+
1917+
class SPIRVCompositeInsertBase : public SPIRVInstTemplateBase {
19391918
public:
1940-
const static Op OC = OpCompositeInsert;
1941-
const static SPIRVWord FixedWordCount = 5;
1942-
// Complete constructor
1943-
SPIRVCompositeInsert(SPIRVType *TheType, SPIRVId TheId, SPIRVId TheObject,
1944-
SPIRVId TheComposite,
1945-
const std::vector<SPIRVWord> &TheIndices,
1946-
SPIRVBasicBlock *TheBB, SPIRVModule *TheM)
1947-
: SPIRVInstruction(TheIndices.size() + FixedWordCount, OC, TheType, TheId,
1948-
TheBB, TheM),
1949-
Object(TheObject), Composite(TheComposite), Indices(TheIndices) {
1950-
validate();
1919+
SPIRVValue *getObject() { return getValue(Ops[0]); }
1920+
SPIRVValue *getComposite() { return getValue(Ops[1]); }
1921+
const std::vector<SPIRVWord> getIndices() const {
1922+
return std::vector<SPIRVWord>(Ops.begin() + 2, Ops.end());
19511923
}
1952-
// Incomplete constructor
1953-
SPIRVCompositeInsert()
1954-
: SPIRVInstruction(OC), Object(SPIRVID_INVALID),
1955-
Composite(SPIRVID_INVALID) {}
1956-
1957-
SPIRVValue *getObject() { return getValue(Object); }
1958-
SPIRVValue *getComposite() { return getValue(Composite); }
1959-
const std::vector<SPIRVWord> &getIndices() const { return Indices; }
19601924

19611925
protected:
1962-
void setWordCount(SPIRVWord TheWordCount) override {
1963-
SPIRVEntry::setWordCount(TheWordCount);
1964-
Indices.resize(TheWordCount - FixedWordCount);
1965-
}
1966-
_SPIRV_DEF_ENCDEC5(Type, Id, Object, Composite, Indices)
19671926
// ToDo: validate the object type is consistent with the base type and indices
19681927
// need to trace through the base type for struct types
19691928
void validate() const override {
19701929
SPIRVInstruction::validate();
1971-
assert(OpCode == OC);
1972-
assert(WordCount == Indices.size() + FixedWordCount);
1930+
assert(OpCode == OpCompositeInsert);
1931+
SPIRVId Composite = Ops[1];
1932+
(void)Composite;
19731933
assert(getValueType(Composite)->isTypeArray() ||
19741934
getValueType(Composite)->isTypeStruct() ||
19751935
getValueType(Composite)->isTypeVector());
19761936
assert(Type == getValueType(Composite));
19771937
}
1978-
SPIRVId Object;
1979-
SPIRVId Composite;
1980-
std::vector<SPIRVWord> Indices;
19811938
};
19821939

1940+
typedef SPIRVInstTemplate<SPIRVCompositeInsertBase, OpCompositeInsert, true, 5,
1941+
true>
1942+
SPIRVCompositeInsert;
1943+
19831944
class SPIRVCopyObject : public SPIRVInstruction {
19841945
public:
19851946
const static Op OC = OpCopyObject;
@@ -2176,52 +2137,34 @@ class SPIRVVectorInsertDynamic : public SPIRVInstruction {
21762137
SPIRVId ComponentId;
21772138
};
21782139

2179-
class SPIRVVectorShuffle : public SPIRVInstruction {
2140+
class SPIRVVectorShuffleBase : public SPIRVInstTemplateBase {
21802141
public:
2181-
const static Op OC = OpVectorShuffle;
2182-
const static SPIRVWord FixedWordCount = 5;
2183-
// Complete constructor
2184-
SPIRVVectorShuffle(SPIRVId TheId, SPIRVType *TheType, SPIRVId TheVector1,
2185-
SPIRVId TheVector2,
2186-
const std::vector<SPIRVWord> &TheComponents,
2187-
SPIRVBasicBlock *TheBB, SPIRVModule *TheM)
2188-
: SPIRVInstruction(TheComponents.size() + FixedWordCount, OC, TheType,
2189-
TheId, TheBB, TheM),
2190-
Vector1(TheVector1), Vector2(TheVector2), Components(TheComponents) {
2191-
validate();
2142+
SPIRVValue *getVector1() { return getValue(Ops[0]); }
2143+
SPIRVValue *getVector2() { return getValue(Ops[1]); }
2144+
const std::vector<SPIRVWord> getComponents() const {
2145+
return std::vector<SPIRVWord>(Ops.begin() + 2, Ops.end());
21922146
}
2193-
// Incomplete constructor
2194-
SPIRVVectorShuffle()
2195-
: SPIRVInstruction(OC), Vector1(SPIRVID_INVALID),
2196-
Vector2(SPIRVID_INVALID) {}
2197-
2198-
SPIRVValue *getVector1() { return getValue(Vector1); }
2199-
SPIRVValue *getVector2() { return getValue(Vector2); }
2200-
const std::vector<SPIRVWord> &getComponents() const { return Components; }
22012147

22022148
protected:
2203-
void setWordCount(SPIRVWord TheWordCount) override {
2204-
SPIRVEntry::setWordCount(TheWordCount);
2205-
Components.resize(TheWordCount - FixedWordCount);
2206-
}
2207-
_SPIRV_DEF_ENCDEC5(Type, Id, Vector1, Vector2, Components)
22082149
void validate() const override {
22092150
SPIRVInstruction::validate();
2210-
assert(OpCode == OC);
2211-
assert(WordCount == Components.size() + FixedWordCount);
2151+
SPIRVId Vector1 = Ops[0];
2152+
SPIRVId Vector2 = Ops[1];
2153+
assert(OpCode == OpVectorShuffle);
22122154
assert(Type->isTypeVector());
22132155
assert(Type->getVectorComponentType() ==
22142156
getValueType(Vector1)->getVectorComponentType());
22152157
if (getValue(Vector1)->isForward() || getValue(Vector2)->isForward())
22162158
return;
22172159
assert(getValueType(Vector1) == getValueType(Vector2));
2218-
assert(Components.size() == Type->getVectorComponentCount());
2160+
assert(Ops.size() - 2 == Type->getVectorComponentCount());
22192161
}
2220-
SPIRVId Vector1;
2221-
SPIRVId Vector2;
2222-
std::vector<SPIRVWord> Components;
22232162
};
22242163

2164+
typedef SPIRVInstTemplate<SPIRVVectorShuffleBase, OpVectorShuffle, true, 5,
2165+
true>
2166+
SPIRVVectorShuffle;
2167+
22252168
class SPIRVControlBarrier : public SPIRVInstruction {
22262169
public:
22272170
static const Op OC = OpControlBarrier;

lib/SPIRV/libSPIRV/SPIRVModule.cpp

Lines changed: 19 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1382,9 +1382,11 @@ SPIRVInstruction *SPIRVModuleImpl::addVectorInsertDynamicInst(
13821382
SPIRVValue *SPIRVModuleImpl::addVectorShuffleInst(
13831383
SPIRVType *Type, SPIRVValue *Vec1, SPIRVValue *Vec2,
13841384
const std::vector<SPIRVWord> &Components, SPIRVBasicBlock *BB) {
1385-
return addInstruction(new SPIRVVectorShuffle(getId(), Type, Vec1->getId(),
1386-
Vec2->getId(), Components, BB,
1387-
this),
1385+
std::vector<SPIRVId> Ops{Vec1->getId(), Vec2->getId()};
1386+
Ops.insert(Ops.end(), Components.begin(), Components.end());
1387+
1388+
return addInstruction(SPIRVInstTemplateBase::create(OpVectorShuffle, Type,
1389+
getId(), Ops, BB, this),
13881390
BB);
13891391
}
13901392

@@ -1441,10 +1443,11 @@ SPIRVInstruction *SPIRVModuleImpl::addSelectInst(SPIRVValue *Condition,
14411443
SPIRVValue *Op1,
14421444
SPIRVValue *Op2,
14431445
SPIRVBasicBlock *BB) {
1444-
return addInstruction(new SPIRVSelect(getId(), Op1->getType(),
1445-
Condition->getId(), Op1->getId(),
1446-
Op2->getId(), BB, this),
1447-
BB);
1446+
return addInstruction(
1447+
SPIRVInstTemplateBase::create(
1448+
OpSelect, Op1->getType(), getId(),
1449+
getVec(Condition->getId(), Op1->getId(), Op2->getId()), BB, this),
1450+
BB);
14481451
}
14491452

14501453
SPIRVInstruction *SPIRVModuleImpl::addSelectionMergeInst(
@@ -1526,19 +1529,21 @@ SPIRVInstruction *
15261529
SPIRVModuleImpl::addCompositeExtractInst(SPIRVType *Type, SPIRVValue *TheVector,
15271530
const std::vector<SPIRVWord> &Indices,
15281531
SPIRVBasicBlock *BB) {
1529-
return addInstruction(new SPIRVCompositeExtract(Type, getId(),
1530-
TheVector->getId(), Indices,
1531-
BB, this),
1532+
return addInstruction(SPIRVInstTemplateBase::create(
1533+
OpCompositeExtract, Type, getId(),
1534+
getVec(TheVector->getId(), Indices), BB, this),
15321535
BB);
15331536
}
15341537

15351538
SPIRVInstruction *SPIRVModuleImpl::addCompositeInsertInst(
15361539
SPIRVValue *Object, SPIRVValue *Composite,
15371540
const std::vector<SPIRVWord> &Indices, SPIRVBasicBlock *BB) {
1538-
return addInstruction(
1539-
new SPIRVCompositeInsert(Composite->getType(), getId(), Object->getId(),
1540-
Composite->getId(), Indices, BB, this),
1541-
BB);
1541+
std::vector<SPIRVId> Ops{Object->getId(), Composite->getId()};
1542+
Ops.insert(Ops.end(), Indices.begin(), Indices.end());
1543+
return addInstruction(SPIRVInstTemplateBase::create(OpCompositeInsert,
1544+
Composite->getType(),
1545+
getId(), Ops, BB, this),
1546+
BB);
15421547
}
15431548

15441549
SPIRVInstruction *SPIRVModuleImpl::addCopyObjectInst(SPIRVType *TheType,

0 commit comments

Comments
 (0)