Skip to content

Commit 80add8c

Browse files
committed
Support 'terminating return' opt in WithNode
1 parent 5381bca commit 80add8c

File tree

2 files changed

+26
-7
lines changed

2 files changed

+26
-7
lines changed

graalpython/com.oracle.graal.python/src/com/oracle/graal/python/nodes/generator/GeneratorWithNode.java

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,12 @@ public GeneratorWithNode(WriteNode targetNode, StatementNode body, ExpressionNod
6262
this.yieldSlot = generatorInfo.nextActiveFlagIndex();
6363
}
6464

65+
@Override
66+
public Object returnExecute(VirtualFrame frame) {
67+
// We do not use returnExecute inside generators
68+
throw new IllegalStateException();
69+
}
70+
6571
@Override
6672
protected Object getWithObject(VirtualFrame frame) {
6773
Object withObject = gen.getIterator(frame, withObjectSlot);
@@ -81,9 +87,11 @@ protected void doEnter(VirtualFrame frame, Object withObject, Object enterCallab
8187
}
8288

8389
@Override
84-
protected void doBody(VirtualFrame frame) {
90+
protected Object doBody(VirtualFrame frame, boolean isReturn) {
91+
assert !isReturn; // not supported in generators
8592
try {
86-
super.doBody(frame);
93+
super.doBody(frame, isReturn);
94+
return null;
8795
} catch (YieldException e) {
8896
gen.setActive(frame, yieldSlot, true);
8997
throw e;

graalpython/com.oracle.graal.python/src/com/oracle/graal/python/nodes/statement/WithNode.java

Lines changed: 16 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -104,6 +104,15 @@ private PRaiseNode getRaiseNode() {
104104

105105
@Override
106106
public void executeVoid(VirtualFrame frame) {
107+
executeImpl(frame, false);
108+
}
109+
110+
@Override
111+
public Object returnExecute(VirtualFrame frame) {
112+
return executeImpl(frame, true);
113+
}
114+
115+
private Object executeImpl(VirtualFrame frame, boolean isReturn) {
107116
Object withObject = getWithObject(frame);
108117
Object clazz = getClassNode.execute(withObject);
109118
Object enterCallable = enterSpecialGetter.execute(frame, clazz, withObject);
@@ -117,11 +126,12 @@ public void executeVoid(VirtualFrame frame) {
117126
throw getRaiseNode().raise(PythonBuiltinClassType.AttributeError, ErrorMessages.OBJ_P_HAS_NO_ATTR_S, withObject, __EXIT__);
118127
}
119128
doEnter(frame, withObject, enterCallable);
129+
Object result = null;
120130
try {
121-
doBody(frame);
131+
result = doBody(frame, isReturn);
122132
} catch (PException exception) {
123133
handleException(frame, withObject, exitCallable, exception);
124-
return;
134+
return PNone.NONE;
125135
} catch (ControlFlowException e) {
126136
doLeave(frame, withObject, exitCallable);
127137
throw e;
@@ -131,9 +141,10 @@ public void executeVoid(VirtualFrame frame) {
131141
throw e;
132142
}
133143
handleException(frame, withObject, exitCallable, pe);
134-
return;
144+
return PNone.NONE;
135145
}
136146
doLeave(frame, withObject, exitCallable);
147+
return result;
137148
}
138149

139150
/**
@@ -146,8 +157,8 @@ protected Object getWithObject(VirtualFrame frame) {
146157
/**
147158
* Execute the body
148159
*/
149-
protected void doBody(VirtualFrame frame) {
150-
body.executeVoid(frame);
160+
protected Object doBody(VirtualFrame frame, boolean isReturn) {
161+
return body.genericExecute(frame, isReturn);
151162
}
152163

153164
/**

0 commit comments

Comments
 (0)