Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Error 3268: Empty sequence cannot be applied appears inappropriately #689

Open
ivor-spence opened this issue Sep 3, 2018 · 16 comments
Open
Assignees
Labels
bug Incorrect behaviour of the tool language Issues in parser, TC, interpreter, POG or CG
Milestone

Comments

@ivor-spence
Copy link

Description

Error 3268 is reported even when the expression should not be evaluated.

Steps to Reproduce

In the quick interpreter type

let s = [] in forall i in set inds s & s(i) > 1

Expected behavior: [What you expect to happen]

This expression is vacuously true so I would expect the result "true"

Actual behavior: [What actually happens]

Error 3268: Empty sequence cannot be applied in 'DEFAULT' (console) at line 1:40

Reproduces how often: [What percentage of the time does it reproduce?]

Every time

Versions

Which version of Overture are you using? Also, please include the OS and what version of the OS you're running.

Overture 2.5.4 on Windows 10.

Additional Information

Any additional information, configuration or data that might be necessary to reproduce the issue.

@peterwvj peterwvj added the bug Incorrect behaviour of the tool label Sep 3, 2018
@peterwvj peterwvj added this to the v2.6.4 milestone Sep 3, 2018
@peterwvj
Copy link
Member

peterwvj commented Sep 3, 2018

Thanks for reporting. I can confirm that this problem is present in both Overture 2.6.2 and VDMJ.

@nickbattle
Copy link
Contributor

nickbattle commented Sep 5, 2018 via email

@nickbattle
Copy link
Contributor

This is interesting. It is a simple matter to suppress the check that empty sequences cannot be indexed, but then that would naively allow expressions like to pass the type check, when they are clearly going to fail. The point about the example in this bug is that the expression is never actually evaluated and so the fact that s is empty does not matter. But the type checker cannot generally distinguish (statically) what will and will not be executed.

VDMTools gives the same type checking error as VDMJ/Overture in this example - saying that an empty sequence cannot be applied, though it does also (usefully) give a warning that an empty sequence is being used in a set bind.

Not sure what's best to do in this case. Opinions?

@peterwvj
Copy link
Member

peterwvj commented Sep 12, 2018

Thanks for explaining.

Strictly speaking the interpreter should be able to evaluate the expression, I think we can agree on that. But then again I can't convince myself that writing expressions like this brings any true value. For these reaons, I think the most correct thing to do is to raise a warning instead of an error, but honestly I'm not sure it's worthwhile implementing this change. Assuming we decide to leave the tool unchanged (which I'm fine with), we could add a comment in the tool manual saying that type-checking of sequence applications is strict and does not allow application of empty sequences regardless of where the expression appears.

@tomooda
Copy link
Member

tomooda commented Sep 12, 2018

Interesting. I tink this is like inferring type in then/else clauses in some sense.
Is it possible to infer that s after the & is typed seq1 of ? and the type checker skips empty check against s(i)?

@nickbattle
Copy link
Contributor

But on what basis can we infer that "s = []" is type seq1?

@tomooda
Copy link
Member

tomooda commented Sep 13, 2018

Well,
In the forall expression, s(i) > 1 would be evaluated if and only if inds s is set1.
So, we can infer inds s is typed set1 in the context of s(i) > 1.
Then we can infer that s is typed seq1 because inds s is not empty.
Of course, inds s is actually empty, but we can assume that s is seq1 within the local context of the forall's body expression.
I think this is just like if expression. Assuming that we have if is_nat(x) then x + 1 else ..., we can assume that x in the context of x + 1 is typed nat because of the if expression regardless the actual value of x.

@nickbattle
Copy link
Contributor

Ah, I see what you mean. Interesting. But in general it's quite a tricky thing to infer - there is an arbitrary expression involving possibly multiple variables in the binding, and from that we have to infer some type-qualification of the variable(s) concerned if the clause dependent on the bind is evaluated.

It would be relatively easy to make inferences for a few common cases, perhaps. I'll have a look.

@tomooda
Copy link
Member

tomooda commented Sep 13, 2018

Yes, quantifiers part is not too many(forall, exists, exists1, iota, set/seq/map comprehension, let-be-st, for, for-all), but rules like (inds s):seq1 of ts:set of t is hard to cover all cases.
(s1 inter s2):set1s1, s2:set1
(power s1):set1s1:set1
(dunion s1):set1s1:set1
(dinter s1):set1s1:set1
(elms s):seq1 of ts:set of t
(inds s):seq1 of ts:set of t
(reverse s):seq1 of ts:set of t
are the rules that came up to my mind.
(If we had map1 type, type inference rules could be more comprehensive)

@peterwvj
Copy link
Member

I'm questioning whether this is actually worthwhile doing. I mean, why complicate type-checking just so we can handle non-sense expressions? After all, isn't it more correct to report a warning?

@ivor-spence
Copy link
Author

ivor-spence commented Sep 14, 2018 via email

@peterwvj
Copy link
Member

peterwvj commented Sep 14, 2018

Thanks! I'm happy to hear that you find the tools useful!

Please help me understand, if there's no human present at the time why may a warning not be appropriate? A warning still allows you to execute the model (unlike type-errors which prevent you from doing that). So just to clarify, all the warning is doing is telling you that you may be doing something you did not intend. If, however, an empty sequence application is executed then that would yield a runtime error.

@nickbattle
Copy link
Contributor

But if an empty sequence was passed to the example expression, the body of the forall expression would never be evaluated, so it would be fine. The problem is that we are aggressively raising a type error for a situation that will not occur.

I'll see what we can do with Tomo's inference idea. We already do do some of this "forward" inference with tests and preconditions that include is_nat and the like, so it may not be too much work.

@ivor-spence
Copy link
Author

ivor-spence commented Sep 14, 2018 via email

@nickbattle
Copy link
Contributor

There's a small bug that is causing the warning to be suppressed in VDMJ/Overture (the inds typecheck is not propagating the emptiness of its argument to the emptiness of its result). That's easy to fix. But the typecheck error for the body of the forall would still remain.

The existing mechanism for qualifying types, for example when an is_nat is used in a conditional, won't work for bindings without some changes. I'm trying to find a way to do it without too much change!

@peterwvj peterwvj modified the milestones: v2.6.4, v2.6.6 Oct 18, 2018
@peterwvj peterwvj modified the milestones: v2.7.0, v2.7.2 Jun 3, 2019
@peterwvj peterwvj modified the milestones: v2.7.2, v2.7.4 Sep 30, 2019
@nickbattle nickbattle self-assigned this Dec 17, 2019
@nickbattle nickbattle added the language Issues in parser, TC, interpreter, POG or CG label Dec 20, 2019
@nickbattle
Copy link
Contributor

Incidentally, the same kind of error occurs with empty maps ("Empty map cannot be applied" errors) that are inside some sort of conditional defence.

The search for an uncomplicated way to solve this internally continues... :-(

@idhugoid idhugoid modified the milestones: v2.7.4, v3.0.2 Mar 16, 2020
@idhugoid idhugoid modified the milestones: v3.0.0, v3.0.2 Aug 28, 2020
@idhugoid idhugoid modified the milestones: v3.0.2, v3.0.4 Nov 10, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Incorrect behaviour of the tool language Issues in parser, TC, interpreter, POG or CG
Projects
None yet
Development

No branches or pull requests

5 participants