summaryrefslogtreecommitdiff
path: root/src/expr/datatype.cpp
diff options
context:
space:
mode:
authorajreynol <andrew.j.reynolds@gmail.com>2016-12-02 14:25:07 -0600
committerajreynol <andrew.j.reynolds@gmail.com>2016-12-02 14:25:07 -0600
commitc3c8d013d2a879eaa1d205e57af32a7f8bb8c0b7 (patch)
treef4a8372d8cd693df5f33e8d49cea53dbb418349e /src/expr/datatype.cpp
parent623e701247ed08e3f59d57b18ebe42f4d4db221e (diff)
Bug fixes and refactoring of parametric datatypes, add some regressions.
Diffstat (limited to 'src/expr/datatype.cpp')
-rw-r--r--src/expr/datatype.cpp129
1 files changed, 79 insertions, 50 deletions
diff --git a/src/expr/datatype.cpp b/src/expr/datatype.cpp
index 537fc2b1a..bc39ced13 100644
--- a/src/expr/datatype.cpp
+++ b/src/expr/datatype.cpp
@@ -173,14 +173,14 @@ void Datatype::setRecord() {
d_isRecord = true;
}
-Cardinality Datatype::getCardinality() const throw(IllegalArgumentException) {
+Cardinality Datatype::getCardinality( Type t ) const throw(IllegalArgumentException) {
PrettyCheckArgument(isResolved(), this, "this datatype is not yet resolved");
std::vector< Type > processing;
- computeCardinality( processing );
+ computeCardinality( t, processing );
return d_card;
}
-Cardinality Datatype::computeCardinality( std::vector< Type >& processing ) const throw(IllegalArgumentException){
+Cardinality Datatype::computeCardinality( Type t, std::vector< Type >& processing ) const throw(IllegalArgumentException){
PrettyCheckArgument(isResolved(), this, "this datatype is not yet resolved");
if( std::find( processing.begin(), processing.end(), d_self )!=processing.end() ){
d_card = Cardinality::INTEGERS;
@@ -188,7 +188,7 @@ Cardinality Datatype::computeCardinality( std::vector< Type >& processing ) cons
processing.push_back( d_self );
Cardinality c = 0;
for(const_iterator i = begin(), i_end = end(); i != i_end; ++i) {
- c += (*i).computeCardinality( processing );
+ c += (*i).computeCardinality( t, processing );
}
d_card = c;
processing.pop_back();
@@ -196,64 +196,64 @@ Cardinality Datatype::computeCardinality( std::vector< Type >& processing ) cons
return d_card;
}
-bool Datatype::isRecursiveSingleton() const throw(IllegalArgumentException) {
+bool Datatype::isRecursiveSingleton( Type t ) const throw(IllegalArgumentException) {
PrettyCheckArgument(isResolved(), this, "this datatype is not yet resolved");
- if( d_card_rec_singleton==0 ){
+ if( d_card_rec_singleton[t]==0 ){
if( isCodatatype() ){
- Assert( d_card_u_assume.empty() );
+ Assert( d_card_u_assume[t].empty() );
std::vector< Type > processing;
- if( computeCardinalityRecSingleton( processing, d_card_u_assume ) ){
- d_card_rec_singleton = 1;
+ if( computeCardinalityRecSingleton( t, processing, d_card_u_assume[t] ) ){
+ d_card_rec_singleton[t] = 1;
}else{
- d_card_rec_singleton = -1;
+ d_card_rec_singleton[t] = -1;
}
- if( d_card_rec_singleton==1 ){
- Trace("dt-card") << "Datatype " << getName() << " is recursive singleton, dependent upon " << d_card_u_assume.size() << " uninterpreted sorts: " << std::endl;
- for( unsigned i=0; i<d_card_u_assume.size(); i++ ){
- Trace("dt-card") << " " << d_card_u_assume [i] << std::endl;
+ if( d_card_rec_singleton[t]==1 ){
+ Trace("dt-card") << "Datatype " << getName() << " is recursive singleton, dependent upon " << d_card_u_assume[t].size() << " uninterpreted sorts: " << std::endl;
+ for( unsigned i=0; i<d_card_u_assume[t].size(); i++ ){
+ Trace("dt-card") << " " << d_card_u_assume[t][i] << std::endl;
}
Trace("dt-card") << std::endl;
}
}else{
- d_card_rec_singleton = -1;
+ d_card_rec_singleton[t] = -1;
}
}
- return d_card_rec_singleton==1;
+ return d_card_rec_singleton[t]==1;
}
-unsigned Datatype::getNumRecursiveSingletonArgTypes() const throw(IllegalArgumentException) {
- return d_card_u_assume.size();
+unsigned Datatype::getNumRecursiveSingletonArgTypes( Type t ) const throw(IllegalArgumentException) {
+ return d_card_u_assume[t].size();
}
-Type Datatype::getRecursiveSingletonArgType( unsigned i ) const throw(IllegalArgumentException) {
- return d_card_u_assume[i];
+Type Datatype::getRecursiveSingletonArgType( Type t, unsigned i ) const throw(IllegalArgumentException) {
+ return d_card_u_assume[t][i];
}
-bool Datatype::computeCardinalityRecSingleton( std::vector< Type >& processing, std::vector< Type >& u_assume ) const throw(IllegalArgumentException){
+bool Datatype::computeCardinalityRecSingleton( Type t, std::vector< Type >& processing, std::vector< Type >& u_assume ) const throw(IllegalArgumentException){
if( std::find( processing.begin(), processing.end(), d_self )!=processing.end() ){
return true;
}else{
- if( d_card_rec_singleton==0 ){
+ if( d_card_rec_singleton[t]==0 ){
//if not yet computed
if( d_constructors.size()==1 ){
bool success = false;
processing.push_back( d_self );
for(unsigned i = 0; i<d_constructors[0].getNumArgs(); i++ ) {
- Type t = ((SelectorType)d_constructors[0][i].getType()).getRangeType();
+ Type tc = ((SelectorType)d_constructors[0][i].getType()).getRangeType();
//if it is an uninterpreted sort, then we depend on it having cardinality one
- if( t.isSort() ){
- if( std::find( u_assume.begin(), u_assume.end(), t )==u_assume.end() ){
- u_assume.push_back( t );
+ if( tc.isSort() ){
+ if( std::find( u_assume.begin(), u_assume.end(), tc )==u_assume.end() ){
+ u_assume.push_back( tc );
}
//if it is a datatype, recurse
- }else if( t.isDatatype() ){
- const Datatype & dt = ((DatatypeType)t).getDatatype();
- if( !dt.computeCardinalityRecSingleton( processing, u_assume ) ){
+ }else if( tc.isDatatype() ){
+ const Datatype & dt = ((DatatypeType)tc).getDatatype();
+ if( !dt.computeCardinalityRecSingleton( t, processing, u_assume ) ){
return false;
}else{
success = true;
}
//if it is a builtin type, it must have cardinality one
- }else if( !t.getCardinality().isOne() ){
+ }else if( !tc.getCardinality().isOne() ){
return false;
}
}
@@ -262,12 +262,12 @@ bool Datatype::computeCardinalityRecSingleton( std::vector< Type >& processing,
}else{
return false;
}
- }else if( d_card_rec_singleton==-1 ){
+ }else if( d_card_rec_singleton[t]==-1 ){
return false;
}else{
- for( unsigned i=0; i<d_card_u_assume.size(); i++ ){
- if( std::find( u_assume.begin(), u_assume.end(), d_card_u_assume[i] )==u_assume.end() ){
- u_assume.push_back( d_card_u_assume[i] );
+ for( unsigned i=0; i<d_card_u_assume[t].size(); i++ ){
+ if( std::find( u_assume.begin(), u_assume.end(), d_card_u_assume[t][i] )==u_assume.end() ){
+ u_assume.push_back( d_card_u_assume[t][i] );
}
}
return true;
@@ -275,7 +275,7 @@ bool Datatype::computeCardinalityRecSingleton( std::vector< Type >& processing,
}
}
-bool Datatype::isFinite() const throw(IllegalArgumentException) {
+bool Datatype::isFinite( Type t ) const throw(IllegalArgumentException) {
PrettyCheckArgument(isResolved(), this, "this datatype is not yet resolved");
// we're using some internals, so we have to set up this library context
@@ -286,7 +286,7 @@ bool Datatype::isFinite() const throw(IllegalArgumentException) {
return self.getAttribute(DatatypeFiniteAttr());
}
for(const_iterator i = begin(), i_end = end(); i != i_end; ++i) {
- if(! (*i).isFinite()) {
+ if(! (*i).isFinite( t )) {
self.setAttribute(DatatypeFiniteComputedAttr(), true);
self.setAttribute(DatatypeFiniteAttr(), false);
return false;
@@ -297,7 +297,7 @@ bool Datatype::isFinite() const throw(IllegalArgumentException) {
return true;
}
-bool Datatype::isInterpretedFinite() const throw(IllegalArgumentException) {
+bool Datatype::isInterpretedFinite( Type t ) const throw(IllegalArgumentException) {
PrettyCheckArgument(isResolved(), this, "this datatype is not yet resolved");
// we're using some internals, so we have to set up this library context
ExprManagerScope ems(d_self);
@@ -310,7 +310,7 @@ bool Datatype::isInterpretedFinite() const throw(IllegalArgumentException) {
self.setAttribute(DatatypeUFiniteComputedAttr(), true);
self.setAttribute(DatatypeUFiniteAttr(), false);
for(const_iterator i = begin(), i_end = end(); i != i_end; ++i) {
- if(! (*i).isInterpretedFinite()) {
+ if(! (*i).isInterpretedFinite( t )) {
return false;
}
}
@@ -787,7 +787,7 @@ bool DatatypeConstructor::isSygusIdFunc() const {
return d_sygus_let_args.size()==1 && d_sygus_let_args[0]==d_sygus_let_body;
}
-Cardinality DatatypeConstructor::getCardinality() const throw(IllegalArgumentException) {
+Cardinality DatatypeConstructor::getCardinality( Type t ) const throw(IllegalArgumentException) {
PrettyCheckArgument(isResolved(), this, "this datatype constructor is not yet resolved");
Cardinality c = 1;
@@ -800,15 +800,24 @@ Cardinality DatatypeConstructor::getCardinality() const throw(IllegalArgumentExc
}
/** compute the cardinality of this datatype */
-Cardinality DatatypeConstructor::computeCardinality( std::vector< Type >& processing ) const throw(IllegalArgumentException){
+Cardinality DatatypeConstructor::computeCardinality( Type t, std::vector< Type >& processing ) const throw(IllegalArgumentException){
Cardinality c = 1;
+ std::vector< Type > instTypes;
+ std::vector< Type > paramTypes;
+ if( DatatypeType(t).isParametric() ){
+ paramTypes = DatatypeType(t).getDatatype().getParameters();
+ instTypes = DatatypeType(t).getParamTypes();
+ }
for(const_iterator i = begin(), i_end = end(); i != i_end; ++i) {
- Type t = SelectorType((*i).getSelector().getType()).getRangeType();
- if( t.isDatatype() ){
- const Datatype& dt = ((DatatypeType)t).getDatatype();
- c *= dt.computeCardinality( processing );
+ Type tc = SelectorType((*i).getSelector().getType()).getRangeType();
+ if( DatatypeType(t).isParametric() ){
+ tc = tc.substitute( paramTypes, instTypes );
+ }
+ if( tc.isDatatype() ){
+ const Datatype& dt = ((DatatypeType)tc).getDatatype();
+ c *= dt.computeCardinality( t, processing );
}else{
- c *= t.getCardinality();
+ c *= tc.getCardinality();
}
}
return c;
@@ -828,7 +837,7 @@ bool DatatypeConstructor::computeWellFounded( std::vector< Type >& processing )
}
-bool DatatypeConstructor::isFinite() const throw(IllegalArgumentException) {
+bool DatatypeConstructor::isFinite( Type t ) const throw(IllegalArgumentException) {
PrettyCheckArgument(isResolved(), this, "this datatype constructor is not yet resolved");
// we're using some internals, so we have to set up this library context
@@ -838,8 +847,18 @@ bool DatatypeConstructor::isFinite() const throw(IllegalArgumentException) {
if(self.getAttribute(DatatypeFiniteComputedAttr())) {
return self.getAttribute(DatatypeFiniteAttr());
}
+ std::vector< Type > instTypes;
+ std::vector< Type > paramTypes;
+ if( DatatypeType(t).isParametric() ){
+ paramTypes = DatatypeType(t).getDatatype().getParameters();
+ instTypes = DatatypeType(t).getParamTypes();
+ }
for(const_iterator i = begin(), i_end = end(); i != i_end; ++i) {
- if(! (*i).getRangeType().getCardinality().isFinite()) {
+ Type tc = (*i).getRangeType();
+ if( DatatypeType(t).isParametric() ){
+ tc = tc.substitute( paramTypes, instTypes );
+ }
+ if(! tc.getCardinality().isFinite()) {
self.setAttribute(DatatypeFiniteComputedAttr(), true);
self.setAttribute(DatatypeFiniteAttr(), false);
return false;
@@ -850,7 +869,7 @@ bool DatatypeConstructor::isFinite() const throw(IllegalArgumentException) {
return true;
}
-bool DatatypeConstructor::isInterpretedFinite() const throw(IllegalArgumentException) {
+bool DatatypeConstructor::isInterpretedFinite( Type t ) const throw(IllegalArgumentException) {
PrettyCheckArgument(isResolved(), this, "this datatype constructor is not yet resolved");
// we're using some internals, so we have to set up this library context
ExprManagerScope ems(d_constructor);
@@ -859,9 +878,19 @@ bool DatatypeConstructor::isInterpretedFinite() const throw(IllegalArgumentExcep
if(self.getAttribute(DatatypeUFiniteComputedAttr())) {
return self.getAttribute(DatatypeUFiniteAttr());
}
+ std::vector< Type > instTypes;
+ std::vector< Type > paramTypes;
+ if( DatatypeType(t).isParametric() ){
+ paramTypes = DatatypeType(t).getDatatype().getParameters();
+ instTypes = DatatypeType(t).getParamTypes();
+ }
for(const_iterator i = begin(), i_end = end(); i != i_end; ++i) {
- TypeNode t = TypeNode::fromType( (*i).getRangeType() );
- if(!t.isInterpretedFinite()) {
+ Type tc = (*i).getRangeType();
+ if( DatatypeType(t).isParametric() ){
+ tc = tc.substitute( paramTypes, instTypes );
+ }
+ TypeNode tcn = TypeNode::fromType( tc );
+ if(!tcn.isInterpretedFinite()) {
self.setAttribute(DatatypeUFiniteComputedAttr(), true);
self.setAttribute(DatatypeUFiniteAttr(), false);
return false;
generated by cgit on debian on lair
contact matthew@masot.net with questions or feedback