mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-05-23 11:38:38 +00:00
Implement test/Regression/TableGen/ListSlices.td
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@15249 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
3aa965fbf4
commit
1dba7abdd7
@ -320,6 +320,28 @@ Init *ListInit::convertInitListSlice(const std::vector<unsigned> &Elements) {
|
|||||||
return new ListInit(Vals);
|
return new ListInit(Vals);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Init *ListInit::resolveReferences(Record &R) {
|
||||||
|
std::vector<Init*> Resolved;
|
||||||
|
Resolved.reserve(getSize());
|
||||||
|
bool Changed = false;
|
||||||
|
|
||||||
|
for (unsigned i = 0, e = getSize(); i != e; ++i) {
|
||||||
|
Init *E;
|
||||||
|
Init *CurElt = getElement(i);
|
||||||
|
|
||||||
|
do {
|
||||||
|
E = CurElt;
|
||||||
|
CurElt = CurElt->resolveReferences(R);
|
||||||
|
Changed |= E != CurElt;
|
||||||
|
} while (E != CurElt);
|
||||||
|
Resolved.push_back(E);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Changed)
|
||||||
|
return new ListInit(Resolved);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
void ListInit::print(std::ostream &OS) const {
|
void ListInit::print(std::ostream &OS) const {
|
||||||
OS << "[";
|
OS << "[";
|
||||||
for (unsigned i = 0, e = Values.size(); i != e; ++i) {
|
for (unsigned i = 0, e = Values.size(); i != e; ++i) {
|
||||||
@ -329,7 +351,7 @@ void ListInit::print(std::ostream &OS) const {
|
|||||||
OS << "]";
|
OS << "]";
|
||||||
}
|
}
|
||||||
|
|
||||||
Init *VarInit::convertInitializerBitRange(const std::vector<unsigned> &Bits) {
|
Init *TypedInit::convertInitializerBitRange(const std::vector<unsigned> &Bits) {
|
||||||
BitsRecTy *T = dynamic_cast<BitsRecTy*>(getType());
|
BitsRecTy *T = dynamic_cast<BitsRecTy*>(getType());
|
||||||
if (T == 0) return 0; // Cannot subscript a non-bits variable...
|
if (T == 0) return 0; // Cannot subscript a non-bits variable...
|
||||||
unsigned NumBits = T->getNumBits();
|
unsigned NumBits = T->getNumBits();
|
||||||
@ -345,9 +367,24 @@ Init *VarInit::convertInitializerBitRange(const std::vector<unsigned> &Bits) {
|
|||||||
return BI;
|
return BI;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Init *TypedInit::convertInitListSlice(const std::vector<unsigned> &Elements) {
|
||||||
|
ListRecTy *T = dynamic_cast<ListRecTy*>(getType());
|
||||||
|
if (T == 0) return 0; // Cannot subscript a non-list variable...
|
||||||
|
|
||||||
|
if (Elements.size() == 1)
|
||||||
|
return new VarListElementInit(this, Elements[0]);
|
||||||
|
|
||||||
|
std::vector<Init*> ListInits;
|
||||||
|
ListInits.reserve(Elements.size());
|
||||||
|
for (unsigned i = 0, e = Elements.size(); i != e; ++i)
|
||||||
|
ListInits.push_back(new VarListElementInit(this, Elements[i]));
|
||||||
|
return new ListInit(ListInits);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
Init *VarInit::resolveBitReference(Record &R, unsigned Bit) {
|
Init *VarInit::resolveBitReference(Record &R, unsigned Bit) {
|
||||||
if (R.isTemplateArg(getName()))
|
if (R.isTemplateArg(getName()))
|
||||||
return this;
|
return 0;
|
||||||
|
|
||||||
RecordVal *RV = R.getValue(getName());
|
RecordVal *RV = R.getValue(getName());
|
||||||
assert(RV && "Reference to a non-existant variable?");
|
assert(RV && "Reference to a non-existant variable?");
|
||||||
@ -359,9 +396,27 @@ Init *VarInit::resolveBitReference(Record &R, unsigned Bit) {
|
|||||||
|
|
||||||
if (!dynamic_cast<UnsetInit*>(B)) // If the bit is not set...
|
if (!dynamic_cast<UnsetInit*>(B)) // If the bit is not set...
|
||||||
return B; // Replace the VarBitInit with it.
|
return B; // Replace the VarBitInit with it.
|
||||||
return this;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Init *VarInit::resolveListElementReference(Record &R, unsigned Elt) {
|
||||||
|
if (R.isTemplateArg(getName()))
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
RecordVal *RV = R.getValue(getName());
|
||||||
|
assert(RV && "Reference to a non-existant variable?");
|
||||||
|
ListInit *LI = dynamic_cast<ListInit*>(RV->getValue());
|
||||||
|
assert(LI && "Invalid list element!");
|
||||||
|
|
||||||
|
if (Elt >= LI->getSize())
|
||||||
|
return 0; // Out of range reference.
|
||||||
|
Init *E = LI->getElement(Elt);
|
||||||
|
if (!dynamic_cast<UnsetInit*>(E)) // If the element is set
|
||||||
|
return E; // Replace the VarListElementInit with it.
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
RecTy *VarInit::getFieldType(const std::string &FieldName) const {
|
RecTy *VarInit::getFieldType(const std::string &FieldName) const {
|
||||||
if (RecordRecTy *RTy = dynamic_cast<RecordRecTy*>(getType()))
|
if (RecordRecTy *RTy = dynamic_cast<RecordRecTy*>(getType()))
|
||||||
if (const RecordVal *RV = RTy->getRecord()->getValue(FieldName))
|
if (const RecordVal *RV = RTy->getRecord()->getValue(FieldName))
|
||||||
@ -396,12 +451,29 @@ Init *VarInit::resolveReferences(Record &R) {
|
|||||||
|
|
||||||
|
|
||||||
Init *VarBitInit::resolveReferences(Record &R) {
|
Init *VarBitInit::resolveReferences(Record &R) {
|
||||||
Init *I = getVariable()->resolveBitReference(R, getBitNum());
|
if (Init *I = getVariable()->resolveBitReference(R, getBitNum()))
|
||||||
if (I != getVariable())
|
|
||||||
return I;
|
return I;
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Init *VarListElementInit::resolveReferences(Record &R) {
|
||||||
|
if (Init *I = getVariable()->resolveListElementReference(R, getElementNum()))
|
||||||
|
return I;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
Init *VarListElementInit::resolveBitReference(Record &R, unsigned Bit) {
|
||||||
|
// FIXME: This should be implemented, to support references like:
|
||||||
|
// bit B = AA[0]{1};
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
Init *VarListElementInit::resolveListElementReference(Record &R, unsigned Elt) {
|
||||||
|
// FIXME: This should be implemented, to support references like:
|
||||||
|
// int B = AA[0][1];
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
RecTy *DefInit::getFieldType(const std::string &FieldName) const {
|
RecTy *DefInit::getFieldType(const std::string &FieldName) const {
|
||||||
if (const RecordVal *RV = Def->getValue(FieldName))
|
if (const RecordVal *RV = Def->getValue(FieldName))
|
||||||
return RV->getType();
|
return RV->getType();
|
||||||
@ -417,25 +489,8 @@ void DefInit::print(std::ostream &OS) const {
|
|||||||
OS << Def->getName();
|
OS << Def->getName();
|
||||||
}
|
}
|
||||||
|
|
||||||
Init *FieldInit::convertInitializerBitRange(const std::vector<unsigned> &Bits) {
|
|
||||||
BitsRecTy *T = dynamic_cast<BitsRecTy*>(getType());
|
|
||||||
if (T == 0) return 0; // Cannot subscript a non-bits field...
|
|
||||||
unsigned NumBits = T->getNumBits();
|
|
||||||
|
|
||||||
BitsInit *BI = new BitsInit(Bits.size());
|
|
||||||
for (unsigned i = 0, e = Bits.size(); i != e; ++i) {
|
|
||||||
if (Bits[i] >= NumBits) {
|
|
||||||
delete BI;
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
BI->setBit(i, new VarBitInit(this, Bits[i]));
|
|
||||||
}
|
|
||||||
return BI;
|
|
||||||
}
|
|
||||||
|
|
||||||
Init *FieldInit::resolveBitReference(Record &R, unsigned Bit) {
|
Init *FieldInit::resolveBitReference(Record &R, unsigned Bit) {
|
||||||
Init *BitsVal = Rec->getFieldInit(R, FieldName);
|
if (Init *BitsVal = Rec->getFieldInit(R, FieldName))
|
||||||
if (BitsVal)
|
|
||||||
if (BitsInit *BI = dynamic_cast<BitsInit*>(BitsVal)) {
|
if (BitsInit *BI = dynamic_cast<BitsInit*>(BitsVal)) {
|
||||||
assert(Bit < BI->getNumBits() && "Bit reference out of range!");
|
assert(Bit < BI->getNumBits() && "Bit reference out of range!");
|
||||||
Init *B = BI->getBit(Bit);
|
Init *B = BI->getBit(Bit);
|
||||||
@ -443,7 +498,19 @@ Init *FieldInit::resolveBitReference(Record &R, unsigned Bit) {
|
|||||||
if (dynamic_cast<BitInit*>(B)) // If the bit is set...
|
if (dynamic_cast<BitInit*>(B)) // If the bit is set...
|
||||||
return B; // Replace the VarBitInit with it.
|
return B; // Replace the VarBitInit with it.
|
||||||
}
|
}
|
||||||
return this;
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
Init *FieldInit::resolveListElementReference(Record &R, unsigned Elt) {
|
||||||
|
if (Init *ListVal = Rec->getFieldInit(R, FieldName))
|
||||||
|
if (ListInit *LI = dynamic_cast<ListInit*>(ListVal)) {
|
||||||
|
if (Elt >= LI->getSize()) return 0;
|
||||||
|
Init *E = LI->getElement(Elt);
|
||||||
|
|
||||||
|
if (!dynamic_cast<UnsetInit*>(E)) // If the bit is set...
|
||||||
|
return E; // Replace the VarListElementInit with it.
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
Init *FieldInit::resolveReferences(Record &R) {
|
Init *FieldInit::resolveReferences(Record &R) {
|
||||||
|
@ -48,6 +48,7 @@ class TypedInit;
|
|||||||
class VarInit;
|
class VarInit;
|
||||||
class FieldInit;
|
class FieldInit;
|
||||||
class VarBitInit;
|
class VarBitInit;
|
||||||
|
class VarListElementInit;
|
||||||
|
|
||||||
// Other classes...
|
// Other classes...
|
||||||
class Record;
|
class Record;
|
||||||
@ -481,6 +482,13 @@ public:
|
|||||||
return Ty->convertValue(this);
|
return Ty->convertValue(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// resolveReferences - This method is used by classes that refer to other
|
||||||
|
/// variables which may not be defined at the time they expression is formed.
|
||||||
|
/// If a value is set for the variable later, this method will be called on
|
||||||
|
/// users of the value to allow the value to propagate out.
|
||||||
|
///
|
||||||
|
virtual Init *resolveReferences(Record &R);
|
||||||
|
|
||||||
virtual void print(std::ostream &OS) const;
|
virtual void print(std::ostream &OS) const;
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -495,11 +503,19 @@ public:
|
|||||||
|
|
||||||
RecTy *getType() const { return Ty; }
|
RecTy *getType() const { return Ty; }
|
||||||
|
|
||||||
|
virtual Init *convertInitializerBitRange(const std::vector<unsigned> &Bits);
|
||||||
|
virtual Init *convertInitListSlice(const std::vector<unsigned> &Elements);
|
||||||
|
|
||||||
/// resolveBitReference - This method is used to implement
|
/// resolveBitReference - This method is used to implement
|
||||||
/// VarBitInit::resolveReferences. If the bit is able to be resolved, we
|
/// VarBitInit::resolveReferences. If the bit is able to be resolved, we
|
||||||
/// simply return the resolved value, otherwise we return this.
|
/// simply return the resolved value, otherwise we return null.
|
||||||
///
|
///
|
||||||
virtual Init *resolveBitReference(Record &R, unsigned Bit) = 0;
|
virtual Init *resolveBitReference(Record &R, unsigned Bit) = 0;
|
||||||
|
|
||||||
|
/// resolveListElementReference - This method is used to implement
|
||||||
|
/// VarListElementInit::resolveReferences. If the list element is resolvable
|
||||||
|
/// now, we return the resolved value, otherwise we return null.
|
||||||
|
virtual Init *resolveListElementReference(Record &R, unsigned Elt) = 0;
|
||||||
};
|
};
|
||||||
|
|
||||||
/// VarInit - 'Opcode' - Represent a reference to an entire variable object.
|
/// VarInit - 'Opcode' - Represent a reference to an entire variable object.
|
||||||
@ -515,9 +531,8 @@ public:
|
|||||||
|
|
||||||
const std::string &getName() const { return VarName; }
|
const std::string &getName() const { return VarName; }
|
||||||
|
|
||||||
virtual Init *convertInitializerBitRange(const std::vector<unsigned> &Bits);
|
|
||||||
|
|
||||||
virtual Init *resolveBitReference(Record &R, unsigned Bit);
|
virtual Init *resolveBitReference(Record &R, unsigned Bit);
|
||||||
|
virtual Init *resolveListElementReference(Record &R, unsigned Elt);
|
||||||
|
|
||||||
virtual RecTy *getFieldType(const std::string &FieldName) const;
|
virtual RecTy *getFieldType(const std::string &FieldName) const;
|
||||||
virtual Init *getFieldInit(Record &R, const std::string &FieldName) const;
|
virtual Init *getFieldInit(Record &R, const std::string &FieldName) const;
|
||||||
@ -558,6 +573,38 @@ public:
|
|||||||
virtual Init *resolveReferences(Record &R);
|
virtual Init *resolveReferences(Record &R);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/// VarListElementInit - List[4] - Represent access to one element of a var or
|
||||||
|
/// field.
|
||||||
|
class VarListElementInit : public TypedInit {
|
||||||
|
TypedInit *TI;
|
||||||
|
unsigned Element;
|
||||||
|
public:
|
||||||
|
VarListElementInit(TypedInit *T, unsigned E)
|
||||||
|
: TypedInit(dynamic_cast<ListRecTy*>(T->getType())->getElementType()),
|
||||||
|
TI(T), Element(E) {
|
||||||
|
assert(T->getType() && dynamic_cast<ListRecTy*>(T->getType()) &&
|
||||||
|
"Illegal VarBitInit expression!");
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual Init *convertInitializerTo(RecTy *Ty) {
|
||||||
|
return Ty->convertValue(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
TypedInit *getVariable() const { return TI; }
|
||||||
|
unsigned getElementNum() const { return Element; }
|
||||||
|
|
||||||
|
virtual Init *resolveBitReference(Record &R, unsigned Bit);
|
||||||
|
|
||||||
|
/// resolveListElementReference - This method is used to implement
|
||||||
|
/// VarListElementInit::resolveReferences. If the list element is resolvable
|
||||||
|
/// now, we return the resolved value, otherwise we return null.
|
||||||
|
virtual Init *resolveListElementReference(Record &R, unsigned Elt);
|
||||||
|
|
||||||
|
virtual void print(std::ostream &OS) const {
|
||||||
|
TI->print(OS); OS << "[" << Element << "]";
|
||||||
|
}
|
||||||
|
virtual Init *resolveReferences(Record &R);
|
||||||
|
};
|
||||||
|
|
||||||
/// DefInit - AL - Represent a reference to a 'def' in the description
|
/// DefInit - AL - Represent a reference to a 'def' in the description
|
||||||
///
|
///
|
||||||
@ -596,9 +643,8 @@ public:
|
|||||||
return Ty->convertValue(this);
|
return Ty->convertValue(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual Init *convertInitializerBitRange(const std::vector<unsigned> &Bits);
|
|
||||||
|
|
||||||
virtual Init *resolveBitReference(Record &R, unsigned Bit);
|
virtual Init *resolveBitReference(Record &R, unsigned Bit);
|
||||||
|
virtual Init *resolveListElementReference(Record &R, unsigned Elt);
|
||||||
|
|
||||||
virtual Init *resolveReferences(Record &R);
|
virtual Init *resolveReferences(Record &R);
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user