Add Expression-Based Contract Syntax#8155
Conversation
|
Thanks for your pull request and interest in making D better, @tgehr! We are looking forward to reviewing it, and you should be hearing from a maintainer soon.
Please see CONTRIBUTING.md for more information. If you have addressed all reviews or aren't sure how to proceed, don't hesitate to ping us with a simple comment. Bugzilla referencesYour PR doesn't reference any Bugzilla issue. If your PR contains non-trivial changes, please reference a Bugzilla issue or create a manual changelog. Testing this PR locallyIf you don't have a local development environment setup, you can use Digger to test this PR: dub fetch digger
dub run digger -- build "master + dmd#8155" |
c306ff4 to
357bfe8
Compare
c70941f to
34e6850
Compare
src/dmd/arraytypes.h
Outdated
|
|
||
| typedef Array<class TemplateInstance *> TemplateInstances; | ||
|
|
||
| typedef Array<class Ensure> Ensures; |
There was a problem hiding this comment.
Should this not be struct Ensure?
There was a problem hiding this comment.
It does not make a difference in code semantics, but I guess using struct is better style.
ibuclaw
left a comment
There was a problem hiding this comment.
The most notable thing missing here is documentation, both for new code blocks added and ddoc entries for functions and types introduced.
Other than that, just a couple notes on implementation detail that are trivial or could be explained away by adding documentation for why it's needed.
src/dmd/func.d
Outdated
| o.push(new TypeIdentifier(rloc,Id.result)); | ||
| import dmd.cond: StaticIfCondition; | ||
| auto c = new StaticIfCondition(rloc, new TraitsExp(loc, Id.compiles, o)); | ||
| auto result = new ConditionalStatement(rloc, c, new ExpStatement(rloc, a), null); |
There was a problem hiding this comment.
Why do we need an artificial static if here?
There was a problem hiding this comment.
This was a hack to improve diagnostics. (__result should not appear in the output.)
The static if condition always passes in well-formed D programs, but will fail if out contracts of void functions specify a result identifier. I'd prefer to remove this. I can just not semantically analyze the out contracts if one of them specifies an output but the result is void, I guess.
| /*********************************************************** | ||
| */ | ||
|
|
||
| extern (C++) struct Ensure |
There was a problem hiding this comment.
Wouldn't this be better as class EnsureStatement : Statement? Then it can go in the statement module.
There was a problem hiding this comment.
It is not really a statement, it's just a way to create a tuple of result identifier and out contract.
I can of course declare it as a statement if that is better. (But I don't think it is.)
src/dmd/func.d
Outdated
| const(char)* mangleString; /// mangled symbol created from mangleExact() | ||
|
|
||
| Identifier outId; /// identifier for out statement | ||
| @property Identifier outId(){ /// identifier for result |
There was a problem hiding this comment.
This would be dead code now, so remove?
There was a problem hiding this comment.
It is not dead code, but I can turn it into a more appropriately-named bool function.
| } | ||
|
|
||
| case TOK.in_: | ||
| auto loc = token.loc; |
There was a problem hiding this comment.
Add a couple comments presenting the supported in syntaxes as per invariant above.
|
|
||
| case TOK.out_: | ||
| // parse: out (identifier) { statement } | ||
| auto loc = token.loc; |
There was a problem hiding this comment.
Likewise here, add comments for syntaxes that are now handled.
src/dmd/statement.d
Outdated
| assert(0); | ||
| } | ||
|
|
||
| static Statements* arraySyntaxCopy(Statements* a){ |
|
I think this could be ironed out within a week ready for inclusion. |
57c8c90 to
0491d4c
Compare
src/dmd/statement.d
Outdated
| /************************************* | ||
| * Do syntax copy of an array of Statement's. | ||
| */ | ||
| static Statements* arraySyntaxCopy(Statements* a){ |
There was a problem hiding this comment.
Curly braces on next line, check for this style everywhere.
src/dmd/func.d
Outdated
| if (a) | ||
| { | ||
| b = a.copy(); | ||
| foreach(i,e;*a) |
There was a problem hiding this comment.
Add spaces in foreach (i, e; *a) - check for this style everywhere as I've seen it more than once.
src/dmd/func.d
Outdated
| * `true` if the function has a return type that | ||
| * is different from `void`. | ||
| */ | ||
| final bool canBuildResultVar(){ |
There was a problem hiding this comment.
I see that this is only used by the module its declared in. So make it private, and extern(D).
852982c to
db54028
Compare
|
@JinShil Probably not, but I can delete code. (I think most of what is not covered in hdrgen it is currently dead code.) |
|
I'm referring to coverage within this PR itself. The hdrgen code that isn't covered is new code in this PR. See https://codecov.io/gh/dlang/dmd/compare/b4d5005db0fd3581789d8a0942583f7c13efbc82...772309cbccb1c0d3e3cd9892f1ebc36024e5f7b7/diff Ideally, we should have 100% coverage for all code in this PR. |
|
So am I. I know. |
|
If its dead code, why was it added? |
|
There is an obvious way to handle the case other than an assertion failure. But if coverage is more important than robustness to changes to invariants in other parts of the code, I can remove that. |
|
Sorry, I don't understand what you're implying. I think all that is required is a test to generate a .di file and verify that the result is correct. That should exercise the new code in hdrgen.d |
|
Currently, a contract is always either a ScopeStatement or an AssertStatement. The header generation code also handles the case when it is a different statement. But yes, you are right, the AssertStatement case can still be covered. I'll add a test and delete the dead code. |
7c09f5b to
312d16f
Compare
1c556ea to
34b6986
Compare
|
@JinShil @ibuclaw @klickverbot @RazvanN7 @WalterBright Gentle reminder. (The remaining few lines of uncovered code cannot be covered in an end-to-end test as far as I can tell, but they should be there for completeness.) |
andralex
left a comment
There was a problem hiding this comment.
Cool, thanks! Please follow with a spec PR.
|
cc @ibuclaw |
|
@andralex FYI: there's already a PR to dlang.org: dlang/dlang.org#2339 |
| @@ -0,0 +1,22 @@ | |||
| Implement DIP 1009 - $(LINK2 https://github.com/dlang/DIPs/blob/master/DIPs/accepted/DIP1009.md, Add Expression-Based Contract Syntax) | |||
There was a problem hiding this comment.
The title is already a link. Thus it can't contain links.
Implementation of DIP 1009.