facebook / facebook/hhvm

Failure to detect unsafe generic return

Open
#8,761 1 comment 0 reactions 0 assignees View on GitHub
hack
Dominant language
C++
Stars
18.7k
Forks
3.1k
Avg merge
1h 47m
Merged PRs (30d)
2

Description

**Describe the bug**

Here's a situation where a function is allowed to return a parent class of a passed parameter, leading to.a runtime failure.

This _would_ be valid if `CoolQuery` was declared `final` (and without the subclasses)

```hack
class Result {}
interface Query {}

class CoolResult extends Result {}
class EvenCoolerResult extends CoolResult {
public function doSomething() : void {}
}

class CoolQuery implements Query{}
class EvenCoolerQuery implements Query{}

function query(Query $q): Tr {
if ($q is CoolQuery) {
return new CoolResult(); // this is incorrect
}

throw new LogicException('Bad');
}

function foo() : void {
$r = query(new EvenCoolerQuery());
// $r correctly typed to EvenCoolerResult
$r->doSomething(); // runtime bug
}
```

**Expected behavior**

```
Typing[4110] Invalid return type [1]
-> Expected Tr [2]
-> But got CoolResult [3]

test.hack:14:16
10 | class EvenCoolerQuery implements Query{}
11 |
[2] 12 | function query(Query $q): Tr {
13 | if ($q is CoolQuery) {
[1,3] 14 | return new CoolResult(); // this is invalid
15 | }
16 |
```

**Actual behavior**

No errors!

**Environment**

- HHVM 4.81 installed on MacOS Catalina via homebrew
- hh_client: hackc-2e49583c00353eab08db093c6f14e2fb413d3954-4.79.0

Contributor guide

Open the contributing guide

Research direction

Start by reproducing the provided Hack example with the stated hh_client environment and confirm that the unsafe generic return is accepted. Trace the type-checking path for the `query` return and the `if ($q is CoolQuery)` branch. Done means the example reports the expected invalid return type diagnostic.

Written by the indexing model from the issue text.

Assessment

Domain
compilers
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Stale
Clarity
Clearly specified
Newbie friendliness
42/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.