Conversation
|
For error tests, look at the ones in |
scoder
left a comment
There was a problem hiding this comment.
Nice! Yes, error tests are missing. Those are the right way to test the actual nogil behaviour, because doing Python stuff in a nogil block should raise a compile error.
Cython/Compiler/Nodes.py
Outdated
| # | ||
| # state string 'gil' or 'nogil' | ||
|
|
||
| child_attrs = ["body", "condition", "finally_clause", "finally_except_clause"] |
There was a problem hiding this comment.
I'd spell this
child_attrs = ["condition"] + NogilTryFinallyStatNode.child_attrs
Just to avoid accidental inconsistencies in the future.
Cython/Compiler/Optimize.py
Outdated
| node.condition = None | ||
|
|
||
| # Condition is False - the body of the GILStatNode | ||
| # should run without changing changing the state of the gil |
| def visit_GILStatNode(self, node): | ||
| if node.condition is not None: | ||
| error(node.pos, "Non-constant condition in a " | ||
| "`with %s(<condition>)` statement" % node.state) |
There was a problem hiding this comment.
Nice. You could also use node.condition.pos instead of node.pos here, which then points directly to the non-constant condition.
| with nogil(True): | ||
| x = f_nogil(x) | ||
| with gil(True): | ||
| x = f_gil(x) |
There was a problem hiding this comment.
Note that this is not a function that needs the GIL. It's one that acquires the GIL itself, on entry. Just use a normal Python function instead.
There was a problem hiding this comment.
changed f_gil to normal Python function.
tests/run/nogil_conditional.pyx
Outdated
| return y | ||
|
|
||
|
|
||
| cdef int with_gil_func() except 0 with gil: |
There was a problem hiding this comment.
except 0 is a bit dangerous since 0 is also the default success value to return from a cdef int function when there is no explicit return x.
There was a problem hiding this comment.
changed to -1.
Note that in tests/run/nogil.pyx it is still 0.
There was a problem hiding this comment.
Ah, thanks. I fixed these tests and also added a compiler warning for this case.
tests/run/nogil_conditional.pyx
Outdated
| """ | ||
| cdef int res = 0 | ||
|
|
||
| if fused_with_object is object: |
There was a problem hiding this comment.
I think this condition makes the test a bit boring, because it discards all nogil tests in the int case without even looking at them, so the two alternative cases are not actually tested. Maybe you could add a third fused types test that tries to actually use the GIL differently based on the type?
There was a problem hiding this comment.
When adding a test for different behavior based on the actual fused type I see that in these cases, the condition (e.g. numeric is float) is not constant during GilCheck which fails the test.
Should I add logic to check for these special kind of expressions (reuse the logic from ReplaceFusedTypeChecks) or should I change some previous transform so that these expressions become constant?
There was a problem hiding this comment.
It looks like a simple .visit_GILStatNode() in that transform that works like .visit_IfStatNode() should suffice.
(Actually, I wonder if it wouldn't have been best to make RepFTCh inherit from ConstFold, but that's not something to fix up right now.)
There was a problem hiding this comment.
in that transform
You are referring to ReplaceFusedTypeChecks, right?
There was a problem hiding this comment.
Added it to ReplaceFusedTypeChecks, worked like a charm.
|
BTW, there is apparently a Py2 distutils problem in the test runner that I just fixed in master. If you merge that back (or rebase your branch), then the tests should be ok. |
6a45480 to
9afd1fd
Compare
|
@scoder rebased on latest master. |
|
@scoder I get the following exception: It seems that during the I am guessing that cython expects the condition of the GilStatNode to already be without a gil so that a functioned called in this scope should be a cdef / cpdef thus having a type. I defined foo as a normal python function without a return type. Does my analysis make sense? (note that we still want the compiler to raise an error in this case, but a different error - Non-constant condition for GilStatNode error) |
|
I believe the same thing happens with |
|
Ah, right. You have to call |
|
See? Good to have error tests. :) |
|
Where exactly should Because we probably want it to be evaluated before the GilStatNode changes the state of the GIL. Is this okay? |
|
Yes, exactly. It's the first child of the node that gets evaluated, before the nodes changes the GIL state. (That's also a reason for it to appear first in |
|
I've added some documentation about the AST to the HackerGuide in the wiki: |
9afd1fd to
412b232
Compare
|
Documentation looks good, very clear. What about documentation for Cython users regarding the conditional with gil/nogil statement? Should I do that as part of this PR or will it be done for all the features of Cython 3.0.0 before it is released? |
|
I'm yet to see a case where documentation magically appears out of thin air when we announce a release date. ;o) |
|
Should examples involving fused types be documented in the nogil docs or in the fused types docs? |
|
Excellent question, the fused types docs. Mentioning them elsewhere would just be confusing (pun half-intended). |
|
The error tests look good, BTW. I think this is ready to be merged when the docs are done. |
|
Thx. Do you think I should add a test in which the condition is a compile-time definition? |
|
Shouldn't make a difference, but well, it's a use case, so why not have it covered. Feel free to swap some of the True/False constants with a |
220687c to
9521466
Compare
9521466 to
5dc832d
Compare
|
@scoder how can I compile the docs into html (or something else) to check that my |
|
@scoder waiting for your input. I think everything should be covered now. |
If you have Sphinx installed, you can run |
|
Very nice feature, thanks! |
@scoder
Implementation for issue 2579.
Allowing statements such as:
which will either run inside a nogil block if condition is True, or will run without a nogil block if the condition is False.
Original form still works the same (
with nogil: ...).Still missing: errors tests.