5936 – Regression(2.050): Segfault when forward-referencing pure auto-return member function with parameter.

D issues are now tracked on GitHub. This Bugzilla instance remains as a read-only archive.
Issue 5936 - Regression(2.050): Segfault when forward-referencing pure auto-return member function with parameter.
Summary: Regression(2.050): Segfault when forward-referencing pure auto-return member ...
Status: RESOLVED FIXED
Alias: None
Product: D
Classification: Unclassified
Component: dmd (show other issues)
Version: D2
Hardware: Other Mac OS X
: P2 regression
Assignee: No Owner
URL:
Keywords: ice-on-valid-code, patch, rejects-valid
: 5844 (view as issue list)
Depends on:
Blocks: 340
Show dependency tree / graph
Reported: 2011年05月06日 08:44 UTC by kennytm
Modified: 2011年08月24日 13:40 UTC (History)
2 users (show)

See Also:


Attachments
Add an attachment (proposed patch, testcase, etc.)

Note You need to log in before you can comment on or make changes to this issue.
Description kennytm 2011年05月06日 08:44:05 UTC
Test case:
---------------------------
import std.c.stdio;
int a() {
 return V.s(0);
}
struct V {
 static pure auto s(int x) {
 return 55;
 }
}
void main() {
 printf("%d\n", a());
}
---------------------------
Bus error
---------------------------
The bug appears only if all of the following conditions are met:
 1. The function 's' must be 'pure'. 
 2. The function 's' must have auto-return.
 3. The function 's' must have at least one named parameter. For example, if
 the parameter is changed to 'pure auto s(...)' the bug disappears.
 4. The function 's' must be placed after its first use. For example, moving
 'struct V' above 'int a()' the bug disappears.
The program works correctly in 2.048. Therefore I have marked this as a
regression.
============================
If instead of calling the function, we just compute the pointer of 's', we'll
get a forward reference error instead:
---------------------------
void a() {
 cast(void)(&V.s);
}
struct V {
 static pure auto s(int x) {
 return 0;
 }
}
---------------------------
x.d(2): Error: forward reference to s
---------------------------
But this error also happens on 2.048.
Comment 1 Don 2011年06月06日 06:18:17 UTC
The segfault is a simple null pointer dereference which can easily be patched.
mtype.c, TypeFunction::parameterEscapes, line 5369
 if (purity)
 { /* With pure functions, we need only be concerned if p escapes
 * via any return statement.
 */
- Type* tret = nextOf()->toBasetype();
- if (!isref && !tret->hasPointers())
+ Type* tret = nextOf() ? nextOf()->toBasetype() : NULL;
+ if (!isref && tret && !tret->hasPointers())
 { /* The result has no references, so p could not be escaping
 * that way.
 */
 return FALSE;
 }
Comment 2 Don 2011年06月06日 06:21:15 UTC
*** Issue 5844 has been marked as a duplicate of this issue. ***
Comment 3 kennytm 2011年06月30日 11:27:04 UTC
(In reply to comment #1)
> The segfault is a simple null pointer dereference which can easily be patched.
> 
> mtype.c, TypeFunction::parameterEscapes, line 5369
> 
> if (purity)
> { /* With pure functions, we need only be concerned if p escapes
> * via any return statement.
> */
> - Type* tret = nextOf()->toBasetype();
> - if (!isref && !tret->hasPointers())
> + Type* tret = nextOf() ? nextOf()->toBasetype() : NULL;
> + if (!isref && tret && !tret->hasPointers())
> { /* The result has no references, so p could not be escaping
> * that way.
> */
> return FALSE;
> }
This patch only fixes 5844. In git master this becomes
 Internal error: toir.c 190
with or without your patch.
Comment 4 kennytm 2011年07月27日 11:48:10 UTC
(In reply to comment #3)
> (In reply to comment #1)
> This patch only fixes 5844. In git master this becomes
> 
> Internal error: toir.c 190
> 
> with or without your patch.
As of the latest git master the ICE no longer happens and the test cases now behaves normally.
Also, one more test case which involves CTFE, based on std.complex.complex:
---------------------------
auto bug5936c(R)(R i) @safe pure nothrow {
 return true;
}
static assert( bug5936c(0) );
---------------------------


AltStyle によって変換されたページ (->オリジナル) /