Skip to content

Commit e852bbe

Browse files
committed
Fix incorrect overloading resolution for polymorphic functions when called with empty set literals as arguments. Fix handling of duplicate polymorphic function definitions with empty bodies. Fixes #875.
1 parent 51e0d7a commit e852bbe

File tree

4 files changed

+22
-6
lines changed

4 files changed

+22
-6
lines changed

changes.rst

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,10 @@ Bug fixes:
4040
the bounds cannot be computed (:bugref:`917`).
4141
- Fix an incorrect comparison function that could trigger assertions in debug builds
4242
(and likely incorrect behaviour in optimised builds).
43+
- Fix incorrect overloading resolution for polymorphic functions when called
44+
with empty set literals as arguments (:bugref:`875`).
45+
- Fix handling of duplicate polymorphic function definitions with empty bodies
46+
(:bugref:`875`).
4347

4448
.. _v2.9.3:
4549

lib/ast.cpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1569,13 +1569,13 @@ Type return_type(EnvI& env, FunctionI* fi, const std::vector<T>& ta, Expression*
15691569
if (tii->ranges().size() == 1 && isa_tiid(tii->ranges()[0]->domain())) {
15701570
ASTString tiid = Expression::cast<TIId>(tii->ranges()[0]->domain())->v();
15711571
Type orig_tiit = get_type(cur.second);
1572-
if (orig_tiit.dim() == 0) {
1572+
if (orig_tiit.dim() == 0 && !orig_tiit.isSet()) {
15731573
std::ostringstream ss;
15741574
ss << "type-inst variable $" << tiid << " must be an array index";
15751575
throw TypeError(env, get_loc(cur.second, call, fi), ss.str());
15761576
}
1577-
Type tiit = Type::top(orig_tiit.dim());
1578-
if (orig_tiit.typeId() != 0) {
1577+
Type tiit = Type::top(orig_tiit.dim() == 0 && orig_tiit.isSet() ? 1 : orig_tiit.dim());
1578+
if (orig_tiit.typeId() != 0 && orig_tiit.dim() != 0) {
15791579
std::vector<unsigned int> enumIds = env.getArrayEnum(orig_tiit.typeId());
15801580
enumIds[enumIds.size() - 1] = 0;
15811581
tiit.typeId(env.registerArrayEnum(enumIds));

lib/model.cpp

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -480,7 +480,9 @@ bool Model::registerFn(EnvI& env, FunctionI* fi, bool keepSorted, bool throwIfDu
480480
fi->ann().add(deprecated);
481481
}
482482
FunctionI* old_fi = i.fi;
483-
i = FnEntry(env, fi);
483+
if (!fe.isPolymorphic) {
484+
i = fe;
485+
}
484486
// If we are replacing a polymorphic function using a new polymorphic function, then
485487
// replace in all entries generated using addPolymorphicInstances
486488
if (i.isPolymorphic) {
@@ -924,10 +926,11 @@ FunctionI* Model::matchFn(EnvI& env, const ASTString& id, const std::vector<Expr
924926
if (matched.size() == 1) {
925927
return matched[0];
926928
}
927-
Type t = matched[0]->ti()->type();
929+
auto t = matched[0]->rtype(env, args, nullptr, false);
928930
t.mkPar(env);
929931
for (unsigned int i = 1; i < matched.size(); i++) {
930-
if (!env.isSubtype(t, matched[i]->ti()->type(), strictEnums)) {
932+
auto rt = matched[i]->rtype(env, args, nullptr, false);
933+
if (!env.isSubtype(t, rt, strictEnums)) {
931934
throw TypeError(env, Expression::loc(botarg),
932935
"ambiguous overloading on return type of function");
933936
}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
/***
2+
!Test
3+
solvers: [gecode]
4+
expected: !Result
5+
solution: !Solution
6+
***/
7+
8+
function set of $T: 'union'(set of $T:x, set of $T: y);
9+
any: x = {1,2,3} union {};

0 commit comments

Comments
 (0)