Skip to content

Commit 7d26b4b

Browse files
committed
Merge branch 'master' into truffle-head
2 parents 231b213 + 0d1d636 commit 7d26b4b

File tree

349 files changed

+2538
-1569
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

349 files changed

+2538
-1569
lines changed

core/src/main/java/org/jruby/internal/runtime/methods/IRMethodArgs.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,6 @@ public interface IRMethodArgs {
66
public List<String[]> getParameterList();
77

88
public enum ArgType {
9-
key, keyrest, block, opt, rest, req
9+
key, keyreq, keyrest, block, opt, rest, req
1010
}
1111
}

core/src/main/java/org/jruby/ir/IRBuilder.java

Lines changed: 18 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1879,12 +1879,12 @@ public void receiveArgs(final ArgsNode argsNode) {
18791879
String argName = ((INameNode) kasgn).getName();
18801880
Variable av = getNewLocalVariable(argName, 0);
18811881
Label l = getNewLabel();
1882-
if (scope instanceof IRMethod) ((IRMethod) scope).addArgDesc(IRMethodArgs.ArgType.key, argName);
1882+
if (scope instanceof IRMethod) addKeyArgDesc(kasgn, argName);
18831883
addInstr(new ReceiveKeywordArgInstr(av, argName, required));
18841884
addInstr(BNEInstr.create(av, UndefinedValue.UNDEFINED, l)); // if 'av' is not undefined, we are done
18851885

18861886
// Required kwargs have no value and check_arity will throw if they are not provided.
1887-
if (kasgn.getValueNode().getNodeType() != NodeType.REQUIRED_KEYWORD_ARGUMENT_VALUE) {
1887+
if (!isRequiredKeywordArgumentValue(kasgn)) {
18881888
build(kasgn);
18891889
} else {
18901890
addInstr(new RaiseRequiredKeywordArgumentError(argName));
@@ -1906,6 +1906,18 @@ public void receiveArgs(final ArgsNode argsNode) {
19061906
receiveBlockArg(argsNode);
19071907
}
19081908

1909+
private void addKeyArgDesc(AssignableNode kasgn, String argName) {
1910+
if (isRequiredKeywordArgumentValue(kasgn)) {
1911+
((IRMethod) scope).addArgDesc(IRMethodArgs.ArgType.keyreq, argName);
1912+
} else {
1913+
((IRMethod) scope).addArgDesc(IRMethodArgs.ArgType.key, argName);
1914+
}
1915+
}
1916+
1917+
private boolean isRequiredKeywordArgumentValue(AssignableNode kasgn) {
1918+
return (kasgn.getValueNode().getNodeType()) == NodeType.REQUIRED_KEYWORD_ARGUMENT_VALUE;
1919+
}
1920+
19091921
// This method is called to build arguments
19101922
public void buildArgsMasgn(Node node, Operand argsArray, boolean isMasgnRoot, int preArgsCount, int postArgsCount, int index, boolean isSplat) {
19111923
Variable v;
@@ -3387,7 +3399,6 @@ public Operand buildZArray() {
33873399
}
33883400

33893401
private Operand buildZSuperIfNest(final Operand block) {
3390-
final IRScope s = scope;
33913402
// If we are in a block, we cannot make any assumptions about what args
33923403
// the super instr is going to get -- if there were no 'define_method'
33933404
// for defining methods, we could guarantee that the super is going to
@@ -3407,9 +3418,9 @@ public Operand run() {
34073418

34083419
Label allDoneLabel = getNewLabel();
34093420

3410-
IRScope superScope = s;
34113421
int depthFromSuper = 0;
34123422
Label next = null;
3423+
IRScope superScope = scope;
34133424

34143425
// Loop and generate a block for each possible value of depthFromSuper
34153426
Variable zsuperResult = createTemporaryVariable();
@@ -3418,7 +3429,7 @@ public Operand run() {
34183429
if (next != null) addInstr(new LabelInstr(next));
34193430
next = getNewLabel();
34203431
addInstr(BNEInstr.create(new Fixnum(depthFromSuper), scopeDepth, next));
3421-
Operand[] args = adjustVariableDepth(((IRClosure)superScope).getBlockArgs(), depthFromSuper);
3432+
Operand[] args = adjustVariableDepth(superScope.getCallArgs(), depthFromSuper);
34223433
addInstr(new ZSuperInstr(zsuperResult, buildSelf(), args, block));
34233434
addInstr(new JumpInstr(allDoneLabel));
34243435

@@ -3431,7 +3442,7 @@ public Operand run() {
34313442

34323443
// If we hit a method, this is known to always succeed
34333444
if (superScope instanceof IRMethod) {
3434-
Operand[] args = adjustVariableDepth(((IRMethod)superScope).getCallArgs(), depthFromSuper);
3445+
Operand[] args = adjustVariableDepth(superScope.getCallArgs(), depthFromSuper);
34353446
addInstr(new ZSuperInstr(zsuperResult, buildSelf(), args, block));
34363447
} //else {
34373448
// FIXME: Do or don't ... there is no try
@@ -3455,7 +3466,7 @@ public Operand buildZSuper(ZSuperNode zsuperNode) {
34553466

34563467
// Enebo:ZSuper in for (or nested for) can be statically resolved like method but it needs to fixup depth.
34573468
if (scope instanceof IRMethod) {
3458-
return buildSuperInstr(block, ((IRMethod) scope).getCallArgs());
3469+
return buildSuperInstr(block, scope.getCallArgs());
34593470
} else {
34603471
return buildZSuperIfNest(block);
34613472
}

core/src/main/java/org/jruby/ir/IRClosure.java

Lines changed: 3 additions & 49 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
package org.jruby.ir;
22

3-
import org.jcodings.specific.USASCIIEncoding;
43
import org.jruby.ir.instructions.*;
54
import org.jruby.ir.interpreter.ClosureInterpreterContext;
65
import org.jruby.ir.interpreter.InterpreterContext;
@@ -14,12 +13,8 @@
1413
import org.jruby.runtime.IRBlockBody;
1514
import org.jruby.runtime.InterpretedIRBlockBody;
1615
import org.jruby.runtime.Signature;
17-
import org.jruby.util.KeyValuePair;
1816
import org.objectweb.asm.Handle;
1917

20-
import java.util.ArrayList;
21-
import java.util.List;
22-
2318
// Closures are contexts/scopes for the purpose of IR building. They are self-contained and accumulate instructions
2419
// that don't merge into the flow of the containing scope. They are manipulated as an unit.
2520
// Their parents are always execution scopes.
@@ -33,10 +28,6 @@ public class IRClosure extends IRScope {
3328

3429
private boolean isBeginEndBlock;
3530

36-
// Block parameters
37-
private List<Operand> blockArgs;
38-
private List<KeyValuePair<Operand, Operand>> keywordArgs;
39-
4031
/** The parameter names, for Proc#parameters */
4132
private String[] parameterList;
4233

@@ -83,8 +74,7 @@ protected IRClosure(IRClosure c, IRScope lexicalParent, int closureId, String fu
8374
} else {
8475
this.body = new InterpretedIRBlockBody(this, c.body.getSignature());
8576
}
86-
this.blockArgs = new ArrayList<>();
87-
this.keywordArgs = new ArrayList<>();
77+
8878
this.signature = c.signature;
8979
}
9080

@@ -98,8 +88,6 @@ public IRClosure(IRManager manager, IRScope lexicalParent, int lineNumber, Stati
9888

9989
public IRClosure(IRManager manager, IRScope lexicalParent, int lineNumber, StaticScope staticScope, Signature signature, int argumentType, String prefix, boolean isBeginEndBlock) {
10090
this(manager, lexicalParent, lexicalParent.getFileName(), lineNumber, staticScope, prefix);
101-
this.blockArgs = new ArrayList<>();
102-
this.keywordArgs = new ArrayList<>();
10391
this.argumentType = argumentType;
10492
this.signature = signature;
10593
lexicalParent.addClosure(this);
@@ -132,9 +120,8 @@ public boolean isBeginEndBlock() {
132120

133121
public void setParameterList(String[] parameterList) {
134122
this.parameterList = parameterList;
135-
if (!getManager().isDryRun()) {
136-
((InterpretedIRBlockBody)this.body).setParameterList(parameterList);
137-
}
123+
124+
if (!getManager().isDryRun()) this.body.setParameterList(parameterList);
138125
}
139126

140127
public String[] getParameterList() {
@@ -186,39 +173,6 @@ public boolean isFlipScope() {
186173
return false;
187174
}
188175

189-
@Override
190-
public void addInstr(Instr i) {
191-
// Accumulate block arguments
192-
if (i instanceof ReceiveKeywordRestArgInstr) {
193-
// Always add the keyword rest arg to the beginning
194-
keywordArgs.add(0, new KeyValuePair<Operand, Operand>(Symbol.KW_REST_ARG_DUMMY, ((ReceiveArgBase) i).getResult()));
195-
} else if (i instanceof ReceiveKeywordArgInstr) {
196-
ReceiveKeywordArgInstr rkai = (ReceiveKeywordArgInstr)i;
197-
// FIXME: This lost encoding information when name was converted to string earlier in IRBuilder
198-
keywordArgs.add(new KeyValuePair<Operand, Operand>(new Symbol(rkai.argName, USASCIIEncoding.INSTANCE), rkai.getResult()));
199-
} else if (i instanceof ReceiveRestArgInstr) {
200-
blockArgs.add(new Splat(((ReceiveRestArgInstr)i).getResult()));
201-
} else if (i instanceof ReceiveArgBase) {
202-
blockArgs.add(((ReceiveArgBase) i).getResult());
203-
}
204-
205-
super.addInstr(i);
206-
}
207-
208-
public Operand[] getBlockArgs() {
209-
if (receivesKeywordArgs()) {
210-
int i = 0;
211-
Operand[] args = new Operand[blockArgs.size() + 1];
212-
for (Operand arg: blockArgs) {
213-
args[i++] = arg;
214-
}
215-
args[i] = new Hash(keywordArgs, true);
216-
return args;
217-
} else {
218-
return blockArgs.toArray(new Operand[blockArgs.size()]);
219-
}
220-
}
221-
222176
public String toStringBody() {
223177
StringBuilder buf = new StringBuilder();
224178
buf.append(getName()).append(" = { \n");

core/src/main/java/org/jruby/ir/IREvalScript.java

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@
88
import org.jruby.ir.interpreter.InterpreterContext;
99
import org.jruby.ir.operands.Label;
1010
import org.jruby.ir.operands.LocalVariable;
11-
import org.jruby.ir.operands.Operand;
1211
import org.jruby.parser.StaticScope;
1312

1413
public class IREvalScript extends IRClosure {
@@ -50,11 +49,6 @@ public IRScopeType getScopeType() {
5049
return IRScopeType.EVAL_SCRIPT;
5150
}
5251

53-
@Override
54-
public Operand[] getBlockArgs() {
55-
return new Operand[0];
56-
}
57-
5852
public boolean isModuleOrInstanceEval() {
5953
return evalType == EvalType.MODULE_EVAL || evalType == EvalType.INSTANCE_EVAL;
6054
}

core/src/main/java/org/jruby/ir/IRMethod.java

Lines changed: 0 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,10 @@
11
package org.jruby.ir;
22

3-
import org.jcodings.specific.USASCIIEncoding;
43
import org.jruby.ast.MethodDefNode;
54
import org.jruby.internal.runtime.methods.IRMethodArgs;
6-
import org.jruby.ir.instructions.Instr;
7-
import org.jruby.ir.instructions.ReceiveArgBase;
8-
import org.jruby.ir.instructions.ReceiveKeywordArgInstr;
9-
import org.jruby.ir.instructions.ReceiveKeywordRestArgInstr;
10-
import org.jruby.ir.instructions.ReceiveRestArgInstr;
115
import org.jruby.ir.interpreter.InterpreterContext;
126
import org.jruby.ir.operands.LocalVariable;
13-
import org.jruby.ir.operands.Operand;
14-
import org.jruby.ir.operands.Symbol;
15-
import org.jruby.ir.operands.Hash;
16-
import org.jruby.ir.operands.Splat;
177
import org.jruby.ir.representations.BasicBlock;
18-
import org.jruby.util.KeyValuePair;
198
import org.jruby.parser.StaticScope;
209

2110
import java.lang.invoke.MethodType;
@@ -28,13 +17,6 @@
2817
public class IRMethod extends IRScope {
2918
public final boolean isInstanceMethod;
3019

31-
// Note that if operands from the method are modified,
32-
// callArgs would have to be updated as well
33-
//
34-
// Call parameters
35-
private List<Operand> callArgs;
36-
private List<KeyValuePair<Operand, Operand>> keywordArgs;
37-
3820
// Argument description of the form [:req, "a"], [:opt, "b"] ..
3921
private List<String[]> argDesc;
4022

@@ -52,8 +34,6 @@ public IRMethod(IRManager manager, IRScope lexicalParent, MethodDefNode defn, St
5234

5335
this.defn = defn;
5436
this.isInstanceMethod = isInstanceMethod;
55-
this.callArgs = new ArrayList<>();
56-
this.keywordArgs = new ArrayList<>();
5737
this.argDesc = new ArrayList<>();
5838
this.signatures = new HashMap<>();
5939

@@ -85,25 +65,6 @@ public IRScopeType getScopeType() {
8565
return isInstanceMethod ? IRScopeType.INSTANCE_METHOD : IRScopeType.CLASS_METHOD;
8666
}
8767

88-
@Override
89-
public void addInstr(Instr i) {
90-
// Accumulate call arguments
91-
if (i instanceof ReceiveKeywordRestArgInstr) {
92-
// Always add the keyword rest arg to the beginning
93-
keywordArgs.add(0, new KeyValuePair<Operand, Operand>(Symbol.KW_REST_ARG_DUMMY, ((ReceiveArgBase) i).getResult()));
94-
} else if (i instanceof ReceiveKeywordArgInstr) {
95-
ReceiveKeywordArgInstr rkai = (ReceiveKeywordArgInstr)i;
96-
// FIXME: This lost encoding information when name was converted to string earlier in IRBuilder
97-
keywordArgs.add(new KeyValuePair<Operand, Operand>(new Symbol(rkai.argName, USASCIIEncoding.INSTANCE), rkai.getResult()));
98-
} else if (i instanceof ReceiveRestArgInstr) {
99-
callArgs.add(new Splat(((ReceiveRestArgInstr)i).getResult()));
100-
} else if (i instanceof ReceiveArgBase) {
101-
callArgs.add(((ReceiveArgBase) i).getResult());
102-
}
103-
104-
super.addInstr(i);
105-
}
106-
10768
public void addArgDesc(IRMethodArgs.ArgType type, String argName) {
10869
argDesc.add(new String[]{type.name(), argName});
10970
}
@@ -112,20 +73,6 @@ public List<String[]> getArgDesc() {
11273
return argDesc;
11374
}
11475

115-
public Operand[] getCallArgs() {
116-
if (receivesKeywordArgs()) {
117-
int i = 0;
118-
Operand[] args = new Operand[callArgs.size() + 1];
119-
for (Operand arg: callArgs) {
120-
args[i++] = arg;
121-
}
122-
args[i] = new Hash(keywordArgs, true);
123-
return args;
124-
} else {
125-
return callArgs.toArray(new Operand[callArgs.size()]);
126-
}
127-
}
128-
12976
@Override
13077
protected LocalVariable findExistingLocalVariable(String name, int scopeDepth) {
13178
assert scopeDepth == 0: "Local variable depth in IRMethod should always be zero (" + name + " had depth of " + scopeDepth + ")";

core/src/main/java/org/jruby/ir/IRScope.java

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
package org.jruby.ir;
22

3+
import org.jcodings.specific.USASCIIEncoding;
34
import org.jruby.ParseResult;
45
import org.jruby.RubyInstanceConfig;
56
import org.jruby.RubyModule;
@@ -17,6 +18,7 @@
1718
import org.jruby.ir.transformations.inlining.CFGInliner;
1819
import org.jruby.ir.transformations.inlining.SimpleCloneInfo;
1920
import org.jruby.parser.StaticScope;
21+
import org.jruby.util.KeyValuePair;
2022
import org.jruby.util.log.Logger;
2123
import org.jruby.util.log.LoggerFactory;
2224

@@ -1011,6 +1013,63 @@ public boolean definesLocalVariable(Variable v) {
10111013
return false;
10121014
}
10131015

1016+
/**
1017+
* Extract all call arguments from the specified scope (only useful for Closures and Methods) so that
1018+
* we can convert zsupers to supers with explicit arguments.
1019+
*
1020+
* Note: This is fairly expensive because we walk entire scope when we could potentially stop earlier
1021+
* if we knew when recv_* were done.
1022+
*/
1023+
public Operand[] getCallArgs() {
1024+
List<Operand> callArgs = new ArrayList<>(5);
1025+
List<KeyValuePair<Operand, Operand>> keywordArgs = new ArrayList<>(3);
1026+
1027+
// We have two paths. eval and non-eval.
1028+
if (instrList == null) { // CFG already made. eval has zsuper and we walk back to some executing method/script
1029+
for (BasicBlock bb: getCFG().getBasicBlocks()) {
1030+
for (Instr instr: bb.getInstrs()) {
1031+
extractCallOperands(callArgs, keywordArgs, instr);
1032+
}
1033+
}
1034+
} else { // common zsuper case. non-eval and at build time entirely.
1035+
for (Instr instr : getInstrs()) {
1036+
extractCallOperands(callArgs, keywordArgs, instr);
1037+
}
1038+
}
1039+
1040+
return getCallOperands(callArgs, keywordArgs);
1041+
}
1042+
1043+
1044+
private void extractCallOperands(List<Operand> callArgs, List<KeyValuePair<Operand, Operand>> keywordArgs, Instr instr) {
1045+
if (instr instanceof ReceiveKeywordRestArgInstr) {
1046+
// Always add the keyword rest arg to the beginning
1047+
keywordArgs.add(0, new KeyValuePair<Operand, Operand>(Symbol.KW_REST_ARG_DUMMY, ((ReceiveArgBase) instr).getResult()));
1048+
} else if (instr instanceof ReceiveKeywordArgInstr) {
1049+
ReceiveKeywordArgInstr rkai = (ReceiveKeywordArgInstr) instr;
1050+
// FIXME: This lost encoding information when name was converted to string earlier in IRBuilder
1051+
keywordArgs.add(new KeyValuePair<Operand, Operand>(new Symbol(rkai.argName, USASCIIEncoding.INSTANCE), rkai.getResult()));
1052+
} else if (instr instanceof ReceiveRestArgInstr) {
1053+
callArgs.add(new Splat(((ReceiveRestArgInstr) instr).getResult()));
1054+
} else if (instr instanceof ReceiveArgBase) {
1055+
callArgs.add(((ReceiveArgBase) instr).getResult());
1056+
}
1057+
}
1058+
1059+
private Operand[] getCallOperands(List<Operand> callArgs, List<KeyValuePair<Operand, Operand>> keywordArgs) {
1060+
if (receivesKeywordArgs()) {
1061+
int i = 0;
1062+
Operand[] args = new Operand[callArgs.size() + 1];
1063+
for (Operand arg: callArgs) {
1064+
args[i++] = arg;
1065+
}
1066+
args[i] = new Hash(keywordArgs, true);
1067+
return args;
1068+
}
1069+
1070+
return callArgs.toArray(new Operand[callArgs.size()]);
1071+
}
1072+
10141073
public void setDataFlowSolution(String name, DataFlowProblem p) {
10151074
dfProbs.put(name, p);
10161075
}

0 commit comments

Comments
 (0)