Skip to content

Commit

Permalink
Showing 104 changed files with 1,128 additions and 2,427 deletions.
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -105,3 +105,6 @@ build.eclipse
truffle-findbugs-report.html
findbugs-noUpdateChecks-3.0.0.tar.gz
findbugs-3.0.0

# Vagrant
/.vagrant
1 change: 0 additions & 1 deletion antlib/extra.xml
Original file line number Diff line number Diff line change
@@ -112,7 +112,6 @@ build jruby-complete.jar
<arg value='test/test_irubyobject_java_passing.rb'/>
<arg value='test/test_jruby_object_input_stream.rb'/>
<arg value='test/test_jar_on_load_path.rb'/>
<arg value='test/test_jruby_ext.rb'/>
<arg value='test/test_jruby_core_ext.rb'/>
<arg value='test/test_thread_context_frame_dereferences_unreachable_variables.rb'/>
<arg value='test/test_context_classloader.rb'/>
12 changes: 1 addition & 11 deletions core/src/main/java/org/jruby/AbstractRubyMethod.java
Original file line number Diff line number Diff line change
@@ -31,23 +31,13 @@
***** END LICENSE BLOCK *****/
package org.jruby;

import org.jruby.anno.JRubyClass;
import org.jruby.anno.JRubyMethod;
import org.jruby.ext.jruby.JRubyLibrary;
import org.jruby.internal.runtime.methods.DynamicMethod;
import org.jruby.internal.runtime.methods.IRMethodArgs;
import org.jruby.internal.runtime.methods.ProcMethod;
import org.jruby.internal.runtime.methods.UndefinedMethod;
import org.jruby.runtime.Block;
import org.jruby.runtime.BlockBody;
import org.jruby.runtime.ClassIndex;
import org.jruby.runtime.CompiledBlockCallback19;
import org.jruby.runtime.CompiledBlockLight19;
import org.jruby.runtime.Helpers;
import org.jruby.runtime.ObjectAllocator;
import org.jruby.runtime.PositionAware;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.Visibility;
import org.jruby.runtime.builtin.IRubyObject;
import org.jruby.runtime.marshal.DataType;

@@ -145,7 +135,7 @@ public int getLine() {

@JRubyMethod(name = "parameters")
public IRubyObject parameters(ThreadContext context) {
return JRubyLibrary.MethodExtensions.methodArgs(this);
return Helpers.methodToParameters(context.runtime, this);
}

protected IRubyObject super_method(ThreadContext context, IRubyObject receiver, RubyModule superClass) {
10 changes: 0 additions & 10 deletions core/src/main/java/org/jruby/Ruby.java
Original file line number Diff line number Diff line change
@@ -112,7 +112,6 @@
import org.jruby.runtime.Binding;
import org.jruby.runtime.Block;
import org.jruby.runtime.CallSite;
import org.jruby.runtime.CallbackFactory;
import org.jruby.runtime.ClassIndex;
import org.jruby.runtime.DynamicScope;
import org.jruby.runtime.EventHook;
@@ -4804,15 +4803,6 @@ private void addEvalParseToStats() {
if (parserStats != null) parserStats.addEvalParse();
}

private void addJRubyModuleParseToStats() {
if (parserStats != null) parserStats.addJRubyModuleParse();
}

@Deprecated
public CallbackFactory callbackFactory(Class<?> type) {
throw new RuntimeException("callback-style handles are no longer supported in JRuby");
}

@Deprecated
public boolean is1_8() {
return false;
2 changes: 1 addition & 1 deletion core/src/main/java/org/jruby/RubyArray.java
Original file line number Diff line number Diff line change
@@ -559,7 +559,7 @@ private IRubyObject initializeCommon(ThreadContext context, IRubyObject arg0, IR
runtime.getWarnings().warn(ID.BLOCK_BEATS_DEFAULT_VALUE, "block supersedes default value argument");
}

if (block.getBody().getArgumentType() == BlockBody.ZERO_ARGS) {
if (block.getSignature() == Signature.NO_ARGUMENTS) {
IRubyObject nil = runtime.getNil();
for (int i = 0; i < ilen; i++) {
store(i, block.yield(context, nil));
3 changes: 1 addition & 2 deletions core/src/main/java/org/jruby/RubyFixnum.java
Original file line number Diff line number Diff line change
@@ -286,8 +286,7 @@ public IRubyObject times(ThreadContext context, Block block) {
long lvalue = this.value;
boolean checkArity = block.type.checkArity;

if (block.getBody().getArgumentType() == BlockBody.ZERO_ARGS ||
block.getSignature() == Signature.NO_ARGUMENTS) {
if (block.getSignature() == Signature.NO_ARGUMENTS) {
if (checkArity) {
// must pass arg
IRubyObject nil = runtime.getNil();
5 changes: 3 additions & 2 deletions core/src/main/java/org/jruby/RubyInteger.java
Original file line number Diff line number Diff line change
@@ -44,6 +44,7 @@
import org.jruby.runtime.BlockBody;
import org.jruby.runtime.ClassIndex;
import org.jruby.runtime.ObjectAllocator;
import org.jruby.runtime.Signature;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.builtin.IRubyObject;
import org.jruby.util.ByteList;
@@ -141,7 +142,7 @@ public IRubyObject upto(ThreadContext context, IRubyObject to, Block block) {
private static void fixnumUpto(ThreadContext context, long from, long to, Block block) {
// We must avoid "i++" integer overflow when (to == Long.MAX_VALUE).
Ruby runtime = context.runtime;
if (block.getBody().getArgumentType() == BlockBody.ZERO_ARGS) {
if (block.getSignature() == Signature.NO_ARGUMENTS) {
IRubyObject nil = runtime.getNil();
long i;
for (i = from; i < to; i++) {
@@ -204,7 +205,7 @@ public IRubyObject downto(ThreadContext context, IRubyObject to, Block block) {
private static void fixnumDownto(ThreadContext context, long from, long to, Block block) {
// We must avoid "i--" integer overflow when (to == Long.MIN_VALUE).
Ruby runtime = context.runtime;
if (block.getBody().getArgumentType() == BlockBody.ZERO_ARGS) {
if (block.getSignature() == Signature.NO_ARGUMENTS) {
IRubyObject nil = runtime.getNil();
long i;
for (i = from; i > to; i--) {
58 changes: 16 additions & 42 deletions core/src/main/java/org/jruby/RubyMethod.java
Original file line number Diff line number Diff line change
@@ -31,26 +31,21 @@
***** END LICENSE BLOCK *****/
package org.jruby;

import org.jruby.ext.jruby.JRubyLibrary;
import org.jruby.anno.JRubyMethod;
import org.jruby.anno.JRubyClass;
import org.jruby.internal.runtime.methods.AliasMethod;
import org.jruby.internal.runtime.methods.DynamicMethod;
import org.jruby.internal.runtime.methods.IRMethodArgs;
import org.jruby.internal.runtime.methods.ProcMethod;
import org.jruby.runtime.Arity;
import org.jruby.runtime.ArgumentDescriptor;
import org.jruby.runtime.Block;
import org.jruby.runtime.BlockBody;
import org.jruby.runtime.ClassIndex;
import org.jruby.runtime.CompiledBlockCallback19;
import org.jruby.runtime.CompiledBlockLight;
import org.jruby.runtime.CompiledBlockLight19;
import org.jruby.runtime.Helpers;
import org.jruby.runtime.MethodBlockBody;
import org.jruby.runtime.ObjectAllocator;
import org.jruby.runtime.PositionAware;
import org.jruby.runtime.Signature;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.Visibility;
import org.jruby.runtime.builtin.IRubyObject;

/**
@@ -188,48 +183,26 @@ public RubyMethod rbClone() {
*
*/
@JRubyMethod
public IRubyObject to_proc(ThreadContext context, Block unusedBlock) {
public IRubyObject to_proc(ThreadContext context) {
Ruby runtime = context.runtime;
CompiledBlockCallback19 callback = new CompiledBlockCallback19() {
@Override
public IRubyObject call(ThreadContext context, IRubyObject self, IRubyObject[] args, Block block) {
return method.call(context, receiver, originModule, originName, args, block);
}

@Override
public String getFile() {
return getFilename();
}

@Override
public int getLine() {
return RubyMethod.this.getLine();
}
};

BlockBody body;
MethodBlockBody body;
Signature signature;
ArgumentDescriptor[] argsDesc;
if (method instanceof IRMethodArgs) {
Signature signature = ((IRMethodArgs) method).getSignature();
int argumentType = resolveArgumentType(signature.isFixed(), signature.required());
body = CompiledBlockLight19.newCompiledBlockLight(((IRMethodArgs) method).getSignature(),
runtime.getStaticScopeFactory().getDummyScope(), callback, false, argumentType, JRubyLibrary.MethodExtensions.methodParameters(runtime, method));
signature = ((IRMethodArgs) method).getSignature();
argsDesc = ((IRMethodArgs) method).getArgumentDescriptors();
} else {
Arity arity = method.getArity();
int argumentType = resolveArgumentType(arity.isFixed(), arity.required());
body = CompiledBlockLight19.newCompiledBlockLight(method.getArity(),
runtime.getStaticScopeFactory().getDummyScope(), callback, false, argumentType, JRubyLibrary.MethodExtensions.methodParameters(runtime, method));
signature = Signature.from(method.getArity());
argsDesc = Helpers.methodToArgumentDescriptors(method);
}
Block b = new Block(body, context.currentBinding(receiver, Visibility.PUBLIC));

body = new MethodBlockBody(runtime.getStaticScopeFactory().getDummyScope(), signature, method, argsDesc, receiver, originModule, originName, getFilename(), getLine());
Block b = MethodBlockBody.createMethodBlock(body);

return RubyProc.newProc(runtime, b, Block.Type.LAMBDA);
}

private int resolveArgumentType(boolean isFixed, int required) {
if (!isFixed) return BlockBody.MULTIPLE_ASSIGNMENT;
if (required > 0) return BlockBody.MULTIPLE_ASSIGNMENT;
return BlockBody.ZERO_ARGS;
}

@JRubyMethod
public RubyUnboundMethod unbind() {
RubyUnboundMethod unboundMethod =
@@ -316,12 +289,12 @@ public int getLine() {

@JRubyMethod
public IRubyObject parameters(ThreadContext context) {
return JRubyLibrary.MethodExtensions.methodArgs(this);
return Helpers.methodToParameters(context.runtime, this);
}

@JRubyMethod(optional = 1)
public IRubyObject curry(ThreadContext context, IRubyObject[] args) {
return to_proc(context, Block.NULL_BLOCK).callMethod(context, "curry", args);
return to_proc(context).callMethod(context, "curry", args);
}

@JRubyMethod
@@ -337,5 +310,6 @@ public IRubyObject original_name(ThreadContext context) {
}
return name(context);
}

}

10 changes: 2 additions & 8 deletions core/src/main/java/org/jruby/RubyProc.java
Original file line number Diff line number Diff line change
@@ -45,7 +45,6 @@
import org.jruby.runtime.ClassIndex;
import org.jruby.runtime.Helpers;
import org.jruby.runtime.IRBlockBody;
import org.jruby.runtime.MethodBlock;
import org.jruby.runtime.ObjectAllocator;
import org.jruby.runtime.Signature;
import org.jruby.runtime.ThreadContext;
@@ -241,9 +240,6 @@ public IRubyObject call(ThreadContext context, IRubyObject[] args) {
public static IRubyObject[] prepareArgs(ThreadContext context, Block.Type type, BlockBody blockBody, IRubyObject[] args) {
Signature signature = blockBody.getSignature();

// FIXME: which blocks have no signature (and no arity before that?)
if (signature == null) return args;

if (args == null) return IRubyObject.NULL_ARRAY;

if (type == Block.Type.LAMBDA) {
@@ -349,10 +345,8 @@ public IRubyObject source_location(ThreadContext context) {
public IRubyObject parameters(ThreadContext context) {
BlockBody body = this.getBlock().getBody();

if (body instanceof MethodBlock) return ((MethodBlock) body).getMethod().parameters(context);

return Helpers.parameterListToParameters(context.runtime,
body.getParameterList(), isLambda());
return Helpers.argumentDescriptorsToParameters(context.runtime,
body.getArgumentDescriptors(), isLambda());
}

@JRubyMethod(name = "lambda?")
2 changes: 1 addition & 1 deletion core/src/main/java/org/jruby/RubyRange.java
Original file line number Diff line number Diff line change
@@ -421,7 +421,7 @@ private void fixnumEach(ThreadContext context, Ruby runtime, Block block) {
to--;
}
long from = ((RubyFixnum) begin).getLongValue();
if (block.getBody().getArgumentType() == BlockBody.ZERO_ARGS) {
if (block.getSignature() == Signature.NO_ARGUMENTS) {
IRubyObject nil = runtime.getNil();
long i;
for (i = from; i < to; i++) {
10 changes: 8 additions & 2 deletions core/src/main/java/org/jruby/RubySymbol.java
Original file line number Diff line number Diff line change
@@ -282,7 +282,13 @@ public IRubyObject id2name(ThreadContext context) {
@JRubyMethod(name = "===", required = 1)
@Override
public IRubyObject op_eqq(ThreadContext context, IRubyObject other) {
return super.op_equal(context, other);
return context.runtime.newBoolean(this == other);
}

@JRubyMethod(name = "==", required = 1)
@Override
public IRubyObject op_equal(ThreadContext context, IRubyObject other) {
return context.runtime.newBoolean(this == other);
}

@Deprecated
@@ -419,7 +425,7 @@ public IRubyObject encoding(ThreadContext context) {
public IRubyObject to_proc(ThreadContext context) {
StaticScope scope = context.runtime.getStaticScopeFactory().getDummyScope();
final CallSite site = new FunctionalCachingCallSite(symbol);
BlockBody body = new ContextAwareBlockBody(scope, Signature.OPTIONAL, BlockBody.SINGLE_RESTARG) {
BlockBody body = new ContextAwareBlockBody(scope, Signature.OPTIONAL) {
private IRubyObject yieldInner(ThreadContext context, RubyArray array, Block block) {
if (array.isEmpty()) {
throw context.runtime.newArgumentError("no receiver given");
46 changes: 2 additions & 44 deletions core/src/main/java/org/jruby/ast/executable/AbstractScript.java
Original file line number Diff line number Diff line change
@@ -5,10 +5,8 @@

package org.jruby.ast.executable;

import java.math.BigInteger;
import org.jcodings.Encoding;
import org.jcodings.EncodingDB;
import org.jruby.Ruby;
import org.jruby.RubyFixnum;
import org.jruby.RubyFloat;
import org.jruby.RubyModule;
@@ -18,14 +16,14 @@
import org.jruby.internal.runtime.methods.DynamicMethod;
import org.jruby.parser.StaticScope;
import org.jruby.runtime.Block;
import org.jruby.runtime.BlockBody;
import org.jruby.runtime.CompiledBlockCallback;
import org.jruby.runtime.CallSite;
import org.jruby.runtime.MethodIndex;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.builtin.IRubyObject;
import org.jruby.util.ByteList;

import java.math.BigInteger;

/**
*
* @author headius
@@ -105,46 +103,6 @@ public IRubyObject run(ThreadContext context, IRubyObject self, IRubyObject[] ar
public final CallSite getCallSite8() {return runtimeCache.callSites[8];}
public final CallSite getCallSite9() {return runtimeCache.callSites[9];}

public static final int NUMBERED_BLOCKBODY_COUNT = 10;

public final BlockBody getBlockBody(ThreadContext context, StaticScope scope, int i, String descriptor) {return runtimeCache.getBlockBody(this, context, scope, i, descriptor);}
public final BlockBody getBlockBody0(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody(this, context, scope, 0, descriptor);}
public final BlockBody getBlockBody1(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody(this, context, scope, 1, descriptor);}
public final BlockBody getBlockBody2(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody(this, context, scope, 2, descriptor);}
public final BlockBody getBlockBody3(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody(this, context, scope, 3, descriptor);}
public final BlockBody getBlockBody4(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody(this, context, scope, 4, descriptor);}
public final BlockBody getBlockBody5(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody(this, context, scope, 5, descriptor);}
public final BlockBody getBlockBody6(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody(this, context, scope, 6, descriptor);}
public final BlockBody getBlockBody7(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody(this, context, scope, 7, descriptor);}
public final BlockBody getBlockBody8(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody(this, context, scope, 8, descriptor);}
public final BlockBody getBlockBody9(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody(this, context, scope, 9, descriptor);}

public final BlockBody getBlockBody19(ThreadContext context, StaticScope scope, int i, String descriptor) {return runtimeCache.getBlockBody19(this, context, scope, i, descriptor);}
public final BlockBody getBlockBody190(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody19(this, context, scope, 0, descriptor);}
public final BlockBody getBlockBody191(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody19(this, context, scope, 1, descriptor);}
public final BlockBody getBlockBody192(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody19(this, context, scope, 2, descriptor);}
public final BlockBody getBlockBody193(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody19(this, context, scope, 3, descriptor);}
public final BlockBody getBlockBody194(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody19(this, context, scope, 4, descriptor);}
public final BlockBody getBlockBody195(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody19(this, context, scope, 5, descriptor);}
public final BlockBody getBlockBody196(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody19(this, context, scope, 6, descriptor);}
public final BlockBody getBlockBody197(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody19(this, context, scope, 7, descriptor);}
public final BlockBody getBlockBody198(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody19(this, context, scope, 8, descriptor);}
public final BlockBody getBlockBody199(ThreadContext context, StaticScope scope, String descriptor) {return runtimeCache.getBlockBody19(this, context, scope, 9, descriptor);}

public static final int NUMBERED_BLOCKCALLBACK_COUNT = 10;

public final CompiledBlockCallback getBlockCallback(int i, String method) {return runtimeCache.getBlockCallback(this, i, method);}
public final CompiledBlockCallback getBlockCallback0(String method) {return runtimeCache.getBlockCallback(this, 0, method);}
public final CompiledBlockCallback getBlockCallback1(String method) {return runtimeCache.getBlockCallback(this, 1, method);}
public final CompiledBlockCallback getBlockCallback2(String method) {return runtimeCache.getBlockCallback(this, 2, method);}
public final CompiledBlockCallback getBlockCallback3(String method) {return runtimeCache.getBlockCallback(this, 3, method);}
public final CompiledBlockCallback getBlockCallback4(String method) {return runtimeCache.getBlockCallback(this, 4, method);}
public final CompiledBlockCallback getBlockCallback5(String method) {return runtimeCache.getBlockCallback(this, 5, method);}
public final CompiledBlockCallback getBlockCallback6(String method) {return runtimeCache.getBlockCallback(this, 6, method);}
public final CompiledBlockCallback getBlockCallback7(String method) {return runtimeCache.getBlockCallback(this, 7, method);}
public final CompiledBlockCallback getBlockCallback8(String method) {return runtimeCache.getBlockCallback(this, 8, method);}
public final CompiledBlockCallback getBlockCallback9(String method) {return runtimeCache.getBlockCallback(this, 9, method);}

public static final int NUMBERED_SYMBOL_COUNT = 10;

public final RubySymbol getSymbol(ThreadContext context, int i, String name, String encoding) {return runtimeCache.getSymbol(context, i, name, encoding);}
81 changes: 1 addition & 80 deletions core/src/main/java/org/jruby/ast/executable/RuntimeCache.java
Original file line number Diff line number Diff line change
@@ -19,10 +19,8 @@
import org.jruby.internal.runtime.methods.UndefinedMethod;
import org.jruby.runtime.Helpers;
import org.jruby.parser.StaticScope;
import org.jruby.runtime.BlockBody;
import org.jruby.runtime.CallSite;
import org.jruby.runtime.CallType;
import org.jruby.runtime.CompiledBlockCallback;
import org.jruby.runtime.MethodIndex;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.builtin.IRubyObject;
@@ -53,50 +51,6 @@ public final CallSite getCallSite(int index) {
return callSites[index];
}

/**
* descriptor format is
*
* closure_method_name,arity,varname1;varname2;varname3,has_multi_args_head,arg_type,light
*
* @param context
* @param index
* @param descriptor
* @return
*/
public final BlockBody getBlockBody(Object scriptObject, ThreadContext context, StaticScope scope, int index, String descriptor) {
BlockBody body = blockBodies[index];
if (body == null) {
return createBlockBody(scriptObject, context, scope, index, descriptor);
}
return body;
}

/**
* descriptor format is
*
* closure_method_name,arity,varname1;varname2;varname3,has_multi_args_head,arg_type,light
*
* @param context
* @param index
* @param descriptor
* @return
*/
public final BlockBody getBlockBody19(Object scriptObject, ThreadContext context, StaticScope scope, int index, String descriptor) {
BlockBody body = blockBodies[index];
if (body == null) {
return createBlockBody19(scriptObject, context, scope, index, descriptor);
}
return body;
}

public final CompiledBlockCallback getBlockCallback(Object scriptObject, int index, String method) {
CompiledBlockCallback callback = blockCallbacks[index];
if (callback == null) {
return createCompiledBlockCallback(scriptObject, index, method);
}
return callback;
}

public final RubySymbol getSymbol(ThreadContext context, int index, String name, String encodingName) {
RubySymbol symbol = symbols[index];
if (symbol == null) {
@@ -288,9 +242,7 @@ public final void initFromDescriptor(String descriptor) {
private static final int BIGINTEGER = REGEXP + 1;
private static final int VARIABLEREADER = BIGINTEGER + 1;
private static final int VARIABLEWRITER = VARIABLEREADER + 1;
private static final int BLOCKBODY = VARIABLEWRITER + 1;
private static final int BLOCKCALLBACK = BLOCKBODY + 1;
private static final int METHOD = BLOCKCALLBACK + 1;
private static final int METHOD = VARIABLEWRITER + 1;
private static final int STRING = METHOD + 1;
private static final int ENCODING = STRING + 1;
private static final int FROZEN_STRING = ENCODING + 1;
@@ -335,10 +287,6 @@ public final void initFromDescriptor(String descriptor) {
if (variableReaderCount > 0) initVariableReaders(variableReaderCount);
int variableWriterCount = getDescriptorValue(descriptor, VARIABLEWRITER);
if (variableWriterCount > 0) initVariableWriters(variableWriterCount);
int blockBodyCount = getDescriptorValue(descriptor, BLOCKBODY);
if (blockBodyCount > 0) initBlockBodies(blockBodyCount);
int blockCallbackCount = getDescriptorValue(descriptor, BLOCKCALLBACK);
if (blockCallbackCount > 0) initBlockCallbacks(blockCallbackCount);
int methodCount = getDescriptorValue(descriptor, METHOD);
if (methodCount > 0) initMethodCache(methodCount);
int stringCount = getDescriptorValue(descriptor, STRING);
@@ -353,14 +301,6 @@ private static int getDescriptorValue(String descriptor, int type) {
return descriptor.charAt(type);
}

public final void initBlockBodies(int size) {
blockBodies = new BlockBody[size];
}

public final void initBlockCallbacks(int size) {
blockCallbacks = new CompiledBlockCallback[size];
}

public final void initSymbols(int size) {
symbols = new RubySymbol[size];
}
@@ -463,21 +403,6 @@ public IRubyObject reCacheFrom(RubyModule target, ThreadContext context, String
return value;
}

private BlockBody createBlockBody(Object scriptObject, ThreadContext context, StaticScope scope, int index, String descriptor) throws NumberFormatException {
BlockBody body = Helpers.createCompiledBlockBody(context, scriptObject, scope, descriptor);
return blockBodies[index] = body;
}

private BlockBody createBlockBody19(Object scriptObject, ThreadContext context, StaticScope scope, int index, String descriptor) throws NumberFormatException {
BlockBody body = Helpers.createCompiledBlockBody19(context, scriptObject, scope, descriptor);
return blockBodies[index] = body;
}

private CompiledBlockCallback createCompiledBlockCallback(Object scriptObject, int index, String method) {
CompiledBlockCallback callback = Helpers.createBlockCallback(scriptObject, method, "(internal)", -1);
return blockCallbacks[index] = callback;
}

public DynamicMethod getMethod(ThreadContext context, RubyClass selfType, int index, String methodName) {
CacheEntry myCache = getCacheEntry(index);
if (CacheEntry.typeOk(myCache, selfType)) {
@@ -660,10 +585,6 @@ private CacheEntry getCacheEntry(int index) {
public CallSite[] callSites = EMPTY_CALLSITES;
private static final CacheEntry[] EMPTY_CACHEENTRIES = {};
public CacheEntry[] methodCache = EMPTY_CACHEENTRIES;
private static final BlockBody[] EMPTY_BLOCKBODIES = {};
public BlockBody[] blockBodies = EMPTY_BLOCKBODIES;
private static final CompiledBlockCallback[] EMPTY_COMPILEDBLOCKCALLBACKS = {};
public CompiledBlockCallback[] blockCallbacks = EMPTY_COMPILEDBLOCKCALLBACKS;
private static final RubySymbol[] EMPTY_RUBYSYMBOLS = {};
public RubySymbol[] symbols = EMPTY_RUBYSYMBOLS;
private static final ByteList[] EMPTY_BYTELISTS = {};
Original file line number Diff line number Diff line change
@@ -122,7 +122,7 @@ public Object get(String key) {

public ScriptEngine getEngineByName(String shortName) {
if (shortName == null) {
throw new NullPointerException("Null shortName");
throw new NullPointerException("Null symbolicName");
}
ScriptEngineFactory factory = nameMap.get(shortName);
if (factory == null) {
66 changes: 1 addition & 65 deletions core/src/main/java/org/jruby/ext/jruby/JRubyLibrary.java
Original file line number Diff line number Diff line change
@@ -30,23 +30,17 @@
***** END LICENSE BLOCK *****/
package org.jruby.ext.jruby;

import java.util.ArrayList;
import org.jruby.AbstractRubyMethod;
import org.jruby.Ruby;
import org.jruby.RubyArray;
import org.jruby.RubyClass;
import org.jruby.RubyModule;
import org.jruby.RubySymbol;
import org.jruby.anno.JRubyMethod;
import org.jruby.anno.JRubyModule;
import org.jruby.internal.runtime.methods.DynamicMethod;
import org.jruby.internal.runtime.methods.IRMethodArgs;
import org.jruby.internal.runtime.methods.MethodArgs2;
import org.jruby.java.proxies.JavaProxy;
import org.jruby.javasupport.Java;
import org.jruby.javasupport.JavaObject;
import org.jruby.javasupport.JavaUtil;
import org.jruby.runtime.Arity;
import org.jruby.runtime.Helpers;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.builtin.IRubyObject;
@@ -150,64 +144,6 @@ public static IRubyObject identity_hash(ThreadContext context, IRubyObject recv,
}

public static class MethodExtensions {
@JRubyMethod(name = "args")
public static IRubyObject methodArgs(IRubyObject recv) {
Ruby runtime = recv.getRuntime();
AbstractRubyMethod rubyMethod = (AbstractRubyMethod)recv;
RubyArray argsArray = RubyArray.newArray(runtime);
DynamicMethod method = rubyMethod.getMethod().getRealMethod();
RubySymbol rest = runtime.newSymbol("rest");

if (method instanceof MethodArgs2) {
return Helpers.parameterListToParameters(runtime, ((MethodArgs2) method).getParameterList(), true);
} else if (method instanceof IRMethodArgs) {
String[] argsDesc = ((IRMethodArgs) method).getParameterList();

for (int i = 0; i < argsDesc.length; i++) {
RubySymbol argType = runtime.newSymbol(argsDesc[i]);
i++;
String argName = argsDesc[i];
if (argName.isEmpty()) {
argsArray.append(RubyArray.newArray(runtime, argType));
} else {
argsArray.append(RubyArray.newArray(runtime, argType, runtime.newSymbol(argName)));
}
}
} else {
if (method.getArity() == Arity.OPTIONAL) {
argsArray.append(RubyArray.newArray(runtime, rest));
}
}

return argsArray;
}

public static String[] methodParameters(Ruby runtime, DynamicMethod method) {
ArrayList<String> argsArray = new ArrayList<String>();
method = method.getRealMethod();

if (method instanceof MethodArgs2) {
return ((MethodArgs2) method).getParameterList();
} else if (method instanceof IRMethodArgs) {
String[] argsDesc = ((IRMethodArgs) method).getParameterList();

for (int i = 0; i < argsDesc.length; i++) {
String argType = argsDesc[i];
i++;
String argName = argsDesc[i];
if (argName.isEmpty()) {
argsArray.add(argType);
} else {
argsArray.add(argType + argName);
}
}
} else {
if (method.getArity() == Arity.OPTIONAL) {
argsArray.add("r");
}
}

return argsArray.toArray(new String[argsArray.size()]);
}

}
}
2 changes: 1 addition & 1 deletion core/src/main/java/org/jruby/ext/socket/RubySocket.java
Original file line number Diff line number Diff line change
@@ -313,7 +313,7 @@ public static IRubyObject gethostbyname(ThreadContext context, IRubyObject recv,
return SocketUtils.gethostbyname(context, hostname);
}

@JRubyMethod(required = 2, optional = 4, meta = true)
@JRubyMethod(required = 2, optional = 5, meta = true)
public static IRubyObject getaddrinfo(ThreadContext context, IRubyObject recv, IRubyObject[] args) {
return SocketUtils.getaddrinfo(context, args);
}
49 changes: 41 additions & 8 deletions core/src/main/java/org/jruby/ext/socket/SocketUtils.java
Original file line number Diff line number Diff line change
@@ -32,6 +32,7 @@
import jnr.netdb.Service;
import org.jruby.Ruby;
import org.jruby.RubyArray;
import org.jruby.RubyBoolean;
import org.jruby.RubyClass;
import org.jruby.RubyFixnum;
import org.jruby.RubyInteger;
@@ -182,15 +183,15 @@ public static IRubyObject gethostbyname(ThreadContext context, IRubyObject hostn
/**
* Ruby definition would look like:
*
* def self.getaddrinfo(host, port, family = nil, socktype = nil, protocol = nil, flags = nil)
* def self.getaddrinfo(host, port, family = nil, socktype = nil, protocol = nil, flags = nil, reverse_lookup = nil)
*/
public static IRubyObject getaddrinfo(final ThreadContext context, IRubyObject[] args) {
final Ruby runtime = context.runtime;
final List<IRubyObject> l = new ArrayList<IRubyObject>();

buildAddrinfoList(context, args, new AddrinfoCallback() {
@Override
public void addrinfo(InetAddress address, int port, Sock sock) {
public void addrinfo(InetAddress address, int port, Sock sock, Boolean reverse) {
boolean is_ipv6 = address instanceof Inet6Address;
boolean sock_stream = true;
boolean sock_dgram = true;
@@ -211,7 +212,7 @@ public void addrinfo(InetAddress address, int port, Sock sock) {
c = new IRubyObject[7];
c[0] = runtime.newString(is_ipv6 ? "AF_INET6" : "AF_INET");
c[1] = runtime.newFixnum(port);
c[2] = runtime.newString(getHostAddress(context, address));
c[2] = runtime.newString(getHostAddress(context, address, reverse));
c[3] = runtime.newString(address.getHostAddress());
c[4] = runtime.newFixnum(is_ipv6 ? PF_INET6 : PF_INET);
c[5] = runtime.newFixnum(SOCK_DGRAM);
@@ -223,7 +224,7 @@ public void addrinfo(InetAddress address, int port, Sock sock) {
c = new IRubyObject[7];
c[0] = runtime.newString(is_ipv6 ? "AF_INET6" : "AF_INET");
c[1] = runtime.newFixnum(port);
c[2] = runtime.newString(getHostAddress(context, address));
c[2] = runtime.newString(getHostAddress(context, address, reverse));
c[3] = runtime.newString(address.getHostAddress());
c[4] = runtime.newFixnum(is_ipv6 ? PF_INET6 : PF_INET);
c[5] = runtime.newFixnum(SOCK_STREAM);
@@ -242,7 +243,7 @@ public static List<Addrinfo> getaddrinfoList(ThreadContext context, IRubyObject[

buildAddrinfoList(context, args, new AddrinfoCallback() {
@Override
public void addrinfo(InetAddress address, int port, Sock sock) {
public void addrinfo(InetAddress address, int port, Sock sock, Boolean reverse) {
boolean sock_stream = true;
boolean sock_dgram = true;

@@ -279,7 +280,8 @@ interface AddrinfoCallback {
void addrinfo(
InetAddress address,
int port,
Sock sock);
Sock sock,
Boolean reverse);
}

public static void buildAddrinfoList(ThreadContext context, IRubyObject[] args, AddrinfoCallback callback) {
@@ -297,6 +299,24 @@ public static void buildAddrinfoList(ThreadContext context, IRubyObject[] args,
IRubyObject socktype = args.length > 3 ? args[3] : context.nil;
//IRubyObject protocol = args[4];
IRubyObject flags = args.length > 5 ? args[5] : context.nil;
IRubyObject reverseArg = args.length > 6 ? args[6] : context.nil;

// The Ruby Socket.getaddrinfo function supports boolean/nil/Symbol values for the
// reverse_lookup parameter. We need to massage all valid inputs to true/false/null.
Boolean reverseLookup = null;
if (reverseArg instanceof RubyBoolean) {
reverseLookup = reverseArg.isTrue();
} else if (reverseArg instanceof RubySymbol) {
String reverseString = reverseArg.toString();
if ("hostname".equals(reverseString)) {
reverseLookup = true;
} else if ("numeric".equals(reverseString)) {
reverseLookup = false;
} else {
throw runtime.newArgumentError("invalid reverse_lookup flag: :" +
reverseString);
}
}

AddressFamily addressFamily = AF_INET;
if (!family.isNil()) {
@@ -339,7 +359,7 @@ public static void buildAddrinfoList(ThreadContext context, IRubyObject[] args,

for(int i = 0; i < addrs.length; i++) {
int p = port.isNil() ? 0 : (int)port.convertToInteger().getLongValue();
callback.addrinfo(addrs[i], p, sock);
callback.addrinfo(addrs[i], p, sock, reverseLookup);
}

} catch(UnknownHostException e) {
@@ -527,8 +547,21 @@ public static int getPortFrom(ThreadContext context, IRubyObject _port) {
return port;
}

private static String getHostAddress(ThreadContext context, InetAddress addr, Boolean reverse) {
String ret;
if (reverse == null) {
ret = context.runtime.isDoNotReverseLookupEnabled() ?
addr.getHostAddress() : addr.getCanonicalHostName();
} else if (reverse) {
ret = addr.getCanonicalHostName();
} else {
ret = addr.getHostAddress();
}
return ret;
}

private static String getHostAddress(ThreadContext context, InetAddress addr) {
return context.runtime.isDoNotReverseLookupEnabled() ? addr.getHostAddress() : addr.getCanonicalHostName();
return getHostAddress(context, addr, null);
}

private static final Pattern STRING_IPV4_ADDRESS_PATTERN =
Original file line number Diff line number Diff line change
@@ -4,6 +4,7 @@
import org.jruby.ir.IRFlags;
import org.jruby.ir.IRScope;
import org.jruby.parser.StaticScope;
import org.jruby.runtime.ArgumentDescriptor;
import org.jruby.runtime.Block;
import org.jruby.runtime.DynamicScope;
import org.jruby.runtime.ThreadContext;
@@ -24,8 +25,8 @@ public CompiledIRMetaClassBody(MethodHandle handle, IRScope scope, RubyModule im
this.popDynScope = this.pushNewDynScope || reuseParentDynScope;
}

public String[] getParameterList() {
return new String[0];
public ArgumentDescriptor[] getArgumentDescriptors() {
return new ArgumentDescriptor[0];
}

@Override
Original file line number Diff line number Diff line change
@@ -5,6 +5,7 @@
import org.jruby.ir.IRScope;
import org.jruby.ir.runtime.IRRuntimeHelpers;
import org.jruby.parser.StaticScope;
import org.jruby.runtime.ArgumentDescriptor;
import org.jruby.runtime.Arity;
import org.jruby.runtime.Block;
import org.jruby.runtime.PositionAware;
@@ -17,14 +18,13 @@

import org.jruby.runtime.Helpers;

public class CompiledIRMethod extends JavaMethod implements IRMethodArgs, MethodArgs2, PositionAware {
public class CompiledIRMethod extends DynamicMethod implements IRMethodArgs, PositionAware {
protected final MethodHandle variable;

protected final MethodHandle specific;
protected final int specificArity;

protected final IRScope method;
private String[] parameterList;
private final StaticScope staticScope;
private final boolean hasExplicitCallProtocol;
private final boolean hasKwargs;
@@ -72,10 +72,8 @@ public Signature getSignature() {
return staticScope.getSignature();
}

public String[] getParameterList() {
if (parameterList != null) return parameterList;

return parameterList = Helpers.irMethodArgsToParameters(((IRMethod)method).getArgDesc());
public ArgumentDescriptor[] getArgumentDescriptors() {
return ((IRMethod)method).getArgumentDescriptors();
}

@Override
Original file line number Diff line number Diff line change
@@ -1,13 +1,22 @@
package org.jruby.internal.runtime.methods;

import org.jruby.runtime.ArgumentDescriptor;
import org.jruby.runtime.Signature;

/**
* Represents a method object that can return a Signature and an array of ArgumentDescriptors.
*/
public interface IRMethodArgs {
// FIXME: Should get pushed to DynamicMethod

/**
* Get the Signature for this method.
*/
public Signature getSignature();
public String[] getParameterList();

public enum ArgType {
key, keyreq, keyrest, block, opt, rest, req
}
/**
* Get the array of ArgumentDescriptors that represent the arguments to this method.
*/
public ArgumentDescriptor[] getArgumentDescriptors();

}
Original file line number Diff line number Diff line change
@@ -4,6 +4,7 @@
import org.jruby.ir.IRScope;
import org.jruby.ir.interpreter.InterpreterContext;
import org.jruby.ir.runtime.IRRuntimeHelpers;
import org.jruby.runtime.ArgumentDescriptor;
import org.jruby.runtime.Block;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.Visibility;
@@ -20,8 +21,8 @@ public InterpretedIRBodyMethod(IRScope method, RubyModule implementationClass) {
}

@Override
public String[] getParameterList() {
return new String[0];
public ArgumentDescriptor[] getArgumentDescriptors() {
return ArgumentDescriptor.EMPTY_ARRAY;
}

@Override
Original file line number Diff line number Diff line change
@@ -8,6 +8,7 @@
import org.jruby.ir.interpreter.InterpreterContext;
import org.jruby.ir.runtime.IRRuntimeHelpers;
import org.jruby.parser.StaticScope;
import org.jruby.runtime.ArgumentDescriptor;
import org.jruby.runtime.Arity;
import org.jruby.runtime.Block;
import org.jruby.runtime.DynamicScope;
@@ -55,9 +56,9 @@ public StaticScope getStaticScope() {
return method.getStaticScope();
}

public String[] getParameterList() {
public ArgumentDescriptor[] getArgumentDescriptors() {
ensureInstrsReady(); // Make sure method is minimally built before returning this info
return ((IRMethod) method).getArgDesc();
return ((IRMethod) method).getArgumentDescriptors();
}

public Signature getSignature() {
Original file line number Diff line number Diff line change
@@ -28,20 +28,9 @@
***** END LICENSE BLOCK *****/
package org.jruby.internal.runtime.methods;

import java.io.PrintWriter;
import java.lang.reflect.Modifier;
import java.util.Arrays;
import java.util.List;

import org.jruby.Ruby;
import org.jruby.RubyInstanceConfig;
import org.jruby.RubyKernel;
import org.jruby.parser.StaticScope;
import org.jruby.runtime.Helpers;
import org.jruby.runtime.Signature;
import org.jruby.util.ClassDefiningClassLoader;
import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.Opcodes;
import org.jruby.RubyModule;
import org.jruby.RubyString;
import org.jruby.anno.JRubyMethod;
@@ -51,23 +40,35 @@
import org.jruby.exceptions.JumpException;
import org.jruby.exceptions.RaiseException;
import org.jruby.lexer.yacc.ISourcePosition;
import org.jruby.parser.StaticScope;
import org.jruby.runtime.Arity;
import org.jruby.runtime.Block;
import org.jruby.runtime.CompiledBlockCallback;
import org.jruby.runtime.CompiledBlockCallback19;
import org.jruby.runtime.Helpers;
import org.jruby.runtime.MethodFactory;
import org.jruby.runtime.Signature;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.Visibility;
import org.jruby.runtime.builtin.IRubyObject;
import org.jruby.util.CodegenUtils;
import static org.jruby.util.CodegenUtils.*;
import static java.lang.System.*;
import org.jruby.util.ClassDefiningJRubyClassLoader;
import org.jruby.util.CodegenUtils;
import org.jruby.util.log.Logger;
import org.jruby.util.log.LoggerFactory;
import org.objectweb.asm.ClassReader;
import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.Label;
import org.objectweb.asm.Opcodes;
import org.objectweb.asm.util.CheckClassAdapter;
import org.jruby.util.log.Logger;
import org.jruby.util.log.LoggerFactory;

import java.io.PrintWriter;
import java.lang.reflect.Modifier;
import java.util.Arrays;
import java.util.List;

import static java.lang.System.out;
import static org.jruby.util.CodegenUtils.ci;
import static org.jruby.util.CodegenUtils.p;
import static org.jruby.util.CodegenUtils.params;
import static org.jruby.util.CodegenUtils.sig;

/**
* In order to avoid the overhead with reflection-based method handles, this
@@ -93,18 +94,6 @@ public class InvocationMethodFactory extends MethodFactory implements Opcodes {

/** The pathname of the super class for compiled Ruby method handles. */
private final static String COMPILED_SUPER_CLASS_NAME = p(COMPILED_SUPER_CLASS);

/** The class used for the super class of compiled Ruby block handles. */
private static final Class<CompiledBlockCallback> COMPILED_BLOCK_SUPER_CLASS = CompiledBlockCallback.class;

/** The pathname of the super class for compiled Ruby block handles. */
private static final String COMPILED_BLOCK_SUPER_CLASS_NAME = p(COMPILED_BLOCK_SUPER_CLASS);

/** The interface used for compiled Ruby 1.9+ block handles. */
public static final Class<CompiledBlockCallback19> COMPILED_BLOCK_19_INTERFACE = CompiledBlockCallback19.class;

/** The pathname of the interface for compiled Ruby block handles. */
public static final String COMPILED_BLOCK_19_INTERFACE_NAME = p(COMPILED_BLOCK_19_INTERFACE);

/** The outward call signature for compiled Ruby method handles. */
private final static String COMPILED_CALL_SIG = sig(IRubyObject.class,
@@ -935,180 +924,6 @@ public static String getBlockCallbackName(String typePathString, String method)
return (typePathString + "$" + method).replaceAll("/", "\\$");
}

public CompiledBlockCallback getBlockCallback(String method, String file, int line, Object scriptObject) {
Class typeClass = scriptObject.getClass();
String typePathString = p(typeClass);
String mname = getBlockCallbackName(typePathString, method);
try {
Class c = tryBlockCallbackClass(mname, COMPILED_BLOCK_SUPER_CLASS);
if (c == null) {
synchronized (syncObject) {
c = tryBlockCallbackClass(mname, COMPILED_BLOCK_SUPER_CLASS);
if (c == null) {
if (RubyInstanceConfig.JIT_LOADING_DEBUG) {
LOG.debug("no generated handle in classloader for: {}", mname);
}
byte[] bytes = getBlockCallbackOffline(method, file, line, typePathString);
c = endClassWithBytes(bytes, mname);
} else {
if (RubyInstanceConfig.JIT_LOADING_DEBUG) {
LOG.debug("found generated handle in classloader for: {}", mname);
}
}
}
}

CompiledBlockCallback ic = (CompiledBlockCallback) c.getConstructor(Object.class).newInstance(scriptObject);
return ic;
} catch (IllegalArgumentException e) {
throw e;
} catch (Exception e) {
throw new IllegalArgumentException(e.getMessage());
}
}

@Override
public byte[] getBlockCallbackOffline(String method, String file, int line, String classname) {
String mname = getBlockCallbackName(classname, method);
ClassWriter cw = createBlockCtor(mname, classname);
SkinnyMethodAdapter mv = startBlockCall(cw);
mv.aload(0);
mv.getfield(mname, "$scriptObject", "L" + classname + ";");
mv.aloadMany(1, 2, 3, 4);
mv.invokestatic(classname, method, sig(
IRubyObject.class, "L" + classname + ";", ThreadContext.class,
IRubyObject.class, IRubyObject.class, Block.class));
mv.areturn();
mv.end();

mv = new SkinnyMethodAdapter(cw, ACC_PUBLIC, "getFile", sig(String.class), null, null);
mv.start();
mv.ldc(file);
mv.areturn();
mv.end();

mv = new SkinnyMethodAdapter(cw, ACC_PUBLIC, "getLine", sig(int.class), null, null);
mv.start();
mv.ldc(line);
mv.ireturn();
mv.end();

return endCallOffline(cw);
}

public CompiledBlockCallback19 getBlockCallback19(String method, String file, int line, Object scriptObject) {
Class typeClass = scriptObject.getClass();
String typePathString = p(typeClass);
String mname = getBlockCallbackName(typePathString, method);
try {
Class c = tryBlockCallback19Class(mname, COMPILED_BLOCK_19_INTERFACE);
if (c == null) {
synchronized (syncObject) {
c = tryBlockCallback19Class(mname, COMPILED_BLOCK_19_INTERFACE);
if (c == null) {
if (RubyInstanceConfig.JIT_LOADING_DEBUG) {
LOG.debug("no generated handle in classloader for: {}", mname);
}
byte[] bytes = getBlockCallback19Offline(method, file, line, typePathString);
c = endClassWithBytes(bytes, mname);
} else {
if (RubyInstanceConfig.JIT_LOADING_DEBUG) {
LOG.debug("found generated handle in classloader for: {}", mname);
}
}
}
}

CompiledBlockCallback19 ic = (CompiledBlockCallback19) c.getConstructor(Object.class).newInstance(scriptObject);
return ic;
} catch (IllegalArgumentException e) {
throw e;
} catch (Exception e) {
throw new IllegalArgumentException(e.getMessage());
}
}

@Override
public byte[] getBlockCallback19Offline(String method, String file, int line, String classname) {
String mnamePath = getBlockCallbackName(classname, method);
ClassWriter cw = createBlockCtor19(mnamePath, classname);
SkinnyMethodAdapter mv = startBlockCall19(cw);
mv.aload(0);
mv.getfield(mnamePath, "$scriptObject", "L" + classname + ";");
mv.aloadMany(1, 2, 3, 4);
mv.invokestatic(classname, method, sig(
IRubyObject.class, "L" + classname + ";", ThreadContext.class,
IRubyObject.class, IRubyObject[].class, Block.class));
mv.areturn();
mv.end();

mv = new SkinnyMethodAdapter(cw, ACC_PUBLIC, "getFile", sig(String.class), null, null);
mv.start();
mv.ldc(file);
mv.areturn();
mv.end();

mv = new SkinnyMethodAdapter(cw, ACC_PUBLIC, "getLine", sig(int.class), null, null);
mv.start();
mv.ldc(line);
mv.ireturn();
mv.end();

return endCallOffline(cw);
}

private SkinnyMethodAdapter startBlockCall(ClassWriter cw) {
SkinnyMethodAdapter mv = new SkinnyMethodAdapter(cw, ACC_PUBLIC | ACC_SYNTHETIC | ACC_FINAL, "call", BLOCK_CALL_SIG, null, null);

mv.visitCode();
return mv;
}

private SkinnyMethodAdapter startBlockCall19(ClassWriter cw) {
SkinnyMethodAdapter mv = new SkinnyMethodAdapter(cw, ACC_PUBLIC | ACC_SYNTHETIC | ACC_FINAL, "call", BLOCK_CALL_SIG19, null, null);

mv.visitCode();
return mv;
}

private ClassWriter createBlockCtor(String namePath, String classname) {
String ciClassname = "L" + classname + ";";
ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS | ClassWriter.COMPUTE_FRAMES);
cw.visit(RubyInstanceConfig.JAVA_VERSION, ACC_PUBLIC + ACC_SUPER, namePath, null, COMPILED_BLOCK_SUPER_CLASS_NAME, null);
cw.visitSource(namePath, null);
cw.visitField(ACC_PRIVATE | ACC_FINAL, "$scriptObject", ciClassname, null, null);
SkinnyMethodAdapter mv = new SkinnyMethodAdapter(cw, ACC_PUBLIC, "<init>", sig(Void.TYPE, params(Object.class)), null, null);
mv.start();
mv.aload(0);
mv.invokespecial(p(CompiledBlockCallback.class), "<init>", sig(void.class));
mv.aloadMany(0, 1);
mv.checkcast(classname);
mv.putfield(namePath, "$scriptObject", ciClassname);
mv.voidreturn();
mv.end();

return cw;
}

private ClassWriter createBlockCtor19(String namePath, String classname) {
String ciClassname = "L" + classname + ";";
ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS | ClassWriter.COMPUTE_FRAMES);
cw.visit(RubyInstanceConfig.JAVA_VERSION, ACC_PUBLIC + ACC_SUPER, namePath, null, p(Object.class), new String[] {COMPILED_BLOCK_19_INTERFACE_NAME});
cw.visitSource(namePath, null);
cw.visitField(ACC_PRIVATE | ACC_FINAL, "$scriptObject", ciClassname, null, null);
SkinnyMethodAdapter mv = new SkinnyMethodAdapter(cw, ACC_PUBLIC, "<init>", sig(Void.TYPE, params(Object.class)), null, null);
mv.start();
mv.aload(0);
mv.invokespecial(p(Object.class), "<init>", sig(void.class));
mv.aloadMany(0, 1);
mv.checkcast(classname);
mv.putfield(namePath, "$scriptObject", ciClassname);
mv.voidreturn();
mv.end();

return cw;
}

/**
* Use code generation to provide a method handle based on an annotated Java
* method.
Original file line number Diff line number Diff line change
@@ -1,6 +1,13 @@
package org.jruby.internal.runtime.methods;

/**
* Get a list of argument descriptors in prefixed form.
*
* The prefixed form has a single leading character to indicate the type of argument
* followed immediately by the name of the argument.
*
* @see IRMethodArgs
* @see org.jruby.runtime.ArgumentType
*/
public interface MethodArgs2 {
public String[] getParameterList();
Original file line number Diff line number Diff line change
@@ -8,6 +8,7 @@
import org.jruby.ir.interpreter.InterpreterContext;
import org.jruby.ir.runtime.IRRuntimeHelpers;
import org.jruby.parser.StaticScope;
import org.jruby.runtime.ArgumentDescriptor;
import org.jruby.runtime.Arity;
import org.jruby.runtime.Block;
import org.jruby.runtime.DynamicScope;
@@ -64,9 +65,9 @@ public StaticScope getStaticScope() {
return method.getStaticScope();
}

public String[] getParameterList() {
public ArgumentDescriptor[] getArgumentDescriptors() {
ensureInstrsReady(); // Make sure method is minimally built before returning this info
return ((IRMethod) method).getArgDesc();
return ((IRMethod) method).getArgumentDescriptors();
}

public Signature getSignature() {
Original file line number Diff line number Diff line change
@@ -32,10 +32,12 @@

import org.jruby.RubyModule;
import org.jruby.RubyProc;
import org.jruby.ast.ArgsNode;
import org.jruby.runtime.ArgumentDescriptor;
import org.jruby.runtime.Arity;
import org.jruby.runtime.Block;
import org.jruby.runtime.Helpers;
import org.jruby.runtime.PositionAware;
import org.jruby.runtime.Signature;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.Visibility;
import org.jruby.runtime.builtin.IRubyObject;
@@ -44,7 +46,7 @@
*
* @author jpetersen
*/
public class ProcMethod extends DynamicMethod implements PositionAware, MethodArgs2 {
public class ProcMethod extends DynamicMethod implements PositionAware, IRMethodArgs {
private RubyProc proc;

/**
@@ -57,9 +59,6 @@ public ProcMethod(RubyModule implementationClass, RubyProc proc, Visibility visi
this.proc = proc;
}

/**
* @see org.jruby.runtime.ICallable#call(Ruby, IRubyObject, String, IRubyObject[], boolean)
*/
public IRubyObject call(ThreadContext context, IRubyObject self, RubyModule klazz, String name, IRubyObject[] args, Block block) {
return proc.call(context, args, self, block);
}
@@ -88,7 +87,13 @@ public int getLine() {
return proc.getBlock().getBody().getLine();
}

public String[] getParameterList() {
return proc.getBlock().getBody().getParameterList();
@Override
public Signature getSignature() {
return proc.getBlock().getBody().getSignature();
}

@Override
public ArgumentDescriptor[] getArgumentDescriptors() {
return proc.getBlock().getBody().getArgumentDescriptors();
}
}
Original file line number Diff line number Diff line change
@@ -29,29 +29,25 @@
***** END LICENSE BLOCK *****/
package org.jruby.internal.runtime.methods;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;

import java.util.ArrayList;
import java.util.List;
import org.jruby.RubyModule;
import org.jruby.anno.JRubyMethod;
import org.jruby.anno.JavaMethodDescriptor;
import org.jruby.anno.TypePopulator;
import org.jruby.lexer.yacc.ISourcePosition;
import org.jruby.parser.StaticScope;
import org.jruby.runtime.Arity;
import org.jruby.runtime.Block;
import org.jruby.runtime.CompiledBlockCallback;
import org.jruby.runtime.CompiledBlockCallback19;
import org.jruby.runtime.MethodFactory;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.Visibility;
import org.jruby.runtime.builtin.IRubyObject;
import org.jruby.util.log.Logger;
import org.jruby.util.log.LoggerFactory;

import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import java.util.ArrayList;
import java.util.List;

/**
* This MethodFactory uses reflection to provide method handles. Reflection is
* typically slower than code-generated handles, but it does provide a simple
@@ -178,78 +174,4 @@ public DynamicMethod getAnnotatedMethod(RubyModule implementationClass, List<Jav
throw new RuntimeException(e);
}
}

public CompiledBlockCallback getBlockCallback(String method, final String file, final int line, final Object scriptObject) {
try {
Class scriptClass = scriptObject.getClass();
final Method blockMethod = scriptClass.getMethod(method, scriptClass, ThreadContext.class, IRubyObject.class, IRubyObject.class, Block.class);
return new CompiledBlockCallback() {
public IRubyObject call(ThreadContext context, IRubyObject self, IRubyObject args, Block block) {
try {
return (IRubyObject)blockMethod.invoke(null, scriptObject, context, self, args, block);
} catch (IllegalAccessException ex) {
throw new RuntimeException(ex);
} catch (IllegalArgumentException ex) {
throw new RuntimeException(ex);
} catch (InvocationTargetException ex) {
Throwable cause = ex.getCause();
if (cause instanceof RuntimeException) {
throw (RuntimeException) cause;
} else if (cause instanceof Error) {
throw (Error) cause;
} else {
throw new RuntimeException(ex);
}
}
}

public String getFile() {
return file;
}

public int getLine() {
return line;
}
};
} catch (NoSuchMethodException nsme) {
throw new RuntimeException(nsme);
}
}

public CompiledBlockCallback19 getBlockCallback19(String method, final String file, final int line, final Object scriptObject) {
try {
Class scriptClass = scriptObject.getClass();
final Method blockMethod = scriptClass.getMethod(method, scriptClass, ThreadContext.class, IRubyObject.class, IRubyObject[].class, Block.class);
return new CompiledBlockCallback19() {
public IRubyObject call(ThreadContext context, IRubyObject self, IRubyObject[] args, Block block) {
try {
return (IRubyObject)blockMethod.invoke(null, scriptObject, context, self, args, block);
} catch (IllegalAccessException ex) {
throw new RuntimeException(ex);
} catch (IllegalArgumentException ex) {
throw new RuntimeException(ex);
} catch (InvocationTargetException ex) {
Throwable cause = ex.getCause();
if (cause instanceof RuntimeException) {
throw (RuntimeException) cause;
} else if (cause instanceof Error) {
throw (Error) cause;
} else {
throw new RuntimeException(ex);
}
}
}

public String getFile() {
return file;
}

public int getLine() {
return line;
}
};
} catch (NoSuchMethodException nsme) {
throw new RuntimeException(nsme);
}
}
}
128 changes: 63 additions & 65 deletions core/src/main/java/org/jruby/ir/IRBuilder.java

Large diffs are not rendered by default.

21 changes: 0 additions & 21 deletions core/src/main/java/org/jruby/ir/IRClosure.java
Original file line number Diff line number Diff line change
@@ -6,11 +6,9 @@
import org.jruby.ir.interpreter.ClosureInterpreterContext;
import org.jruby.ir.interpreter.InterpreterContext;
import org.jruby.ir.operands.*;
import org.jruby.ir.representations.CFG;
import org.jruby.ir.transformations.inlining.CloneInfo;
import org.jruby.ir.transformations.inlining.SimpleCloneInfo;
import org.jruby.parser.StaticScope;
import org.jruby.runtime.Arity;
import org.jruby.runtime.BlockBody;
import org.jruby.runtime.IRBlockBody;
import org.jruby.runtime.InterpretedIRBlockBody;
@@ -28,9 +26,6 @@ public class IRClosure extends IRScope {

private boolean isBeginEndBlock;

/** The parameter names, for Proc#parameters */
private String[] parameterList;

private Signature signature;

/** Added for interp/JIT purposes */
@@ -48,7 +43,6 @@ protected IRClosure(IRManager manager, IRScope lexicalParent, String fileName, i
this.closureId = lexicalParent.getNextClosureId();
setName(prefix + closureId);
this.body = null;
this.parameterList = new String[] {};
}

/** Used by cloning code */
@@ -107,16 +101,6 @@ public boolean isBeginEndBlock() {
return isBeginEndBlock;
}

public void setParameterList(String[] parameterList) {
this.parameterList = parameterList;

if (!getManager().isDryRun()) this.body.setParameterList(parameterList);
}

public String[] getParameterList() {
return this.parameterList;
}

@Override
public int getNextClosureId() {
return getLexicalParent().getNextClosureId();
@@ -250,7 +234,6 @@ public LocalVariable getLocalVariable(String name, int depth) {
protected IRClosure cloneForInlining(CloneInfo ii, IRClosure clone) {
// SSS FIXME: This is fragile. Untangle this state.
// Why is this being copied over to InterpretedIRBlockBody?
clone.setParameterList(this.parameterList);
clone.isBeginEndBlock = this.isBeginEndBlock;

SimpleCloneInfo clonedII = ii.cloneForCloningClosure(clone);
@@ -296,10 +279,6 @@ public void setName(String name) {
super.setName(getLexicalParent().getName() + name);
}

public Arity getArity() {
return signature.arity();
}

public Signature getSignature() {
return signature;
}
16 changes: 1 addition & 15 deletions core/src/main/java/org/jruby/ir/IRMethod.java
Original file line number Diff line number Diff line change
@@ -5,6 +5,7 @@
import java.util.HashMap;
import java.util.Map;
import org.jruby.ast.MethodDefNode;
import org.jruby.runtime.ArgumentDescriptor;
import org.jruby.ir.interpreter.InterpreterContext;
import org.jruby.ir.operands.LocalVariable;
import org.jruby.ir.representations.BasicBlock;
@@ -13,9 +14,6 @@
public class IRMethod extends IRScope {
public final boolean isInstanceMethod;

// Argument description of the form [:req, "a"], [:opt, "b"] ..
private String[] argDesc;

// Signatures to the jitted versions of this method
private Map<Integer, MethodType> signatures;

@@ -30,7 +28,6 @@ public IRMethod(IRManager manager, IRScope lexicalParent, MethodDefNode defn, St

this.defn = defn;
this.isInstanceMethod = isInstanceMethod;
this.argDesc = null;
this.signatures = null;

if (!getManager().isDryRun() && staticScope != null) {
@@ -64,17 +61,6 @@ public IRScopeType getScopeType() {
return isInstanceMethod ? IRScopeType.INSTANCE_METHOD : IRScopeType.CLASS_METHOD;
}

public String[] getArgDesc() {
return argDesc;
}

/**
* Set upon completion of IRBuild of this IRMethod.
*/
public void setArgDesc(String[] argDesc) {
this.argDesc = argDesc;
}

@Override
protected LocalVariable findExistingLocalVariable(String name, int scopeDepth) {
assert scopeDepth == 0: "Local variable depth in IRMethod should always be zero (" + name + " had depth of " + scopeDepth + ")";
16 changes: 16 additions & 0 deletions core/src/main/java/org/jruby/ir/IRScope.java
Original file line number Diff line number Diff line change
@@ -21,6 +21,8 @@

import java.util.*;
import java.util.concurrent.atomic.AtomicInteger;

import org.jruby.runtime.ArgumentDescriptor;
import org.jruby.util.log.Logger;
import org.jruby.util.log.LoggerFactory;

@@ -61,6 +63,8 @@ public abstract class IRScope implements ParseResult {
private static final Collection<IRClosure> NO_CLOSURES = Collections.unmodifiableCollection(new ArrayList<IRClosure>(0));

private static AtomicInteger globalScopeCount = new AtomicInteger();
// Argument description
protected ArgumentDescriptor[] argDesc = ArgumentDescriptor.EMPTY_ARRAY;

/** Unique global scope id */
private int scopeId;
@@ -191,6 +195,7 @@ public IRScope(IRManager manager, IRScope lexicalParent, String name,
this.scopeId = globalScopeCount.getAndIncrement();

setupLexicalContainment();
this.argDesc = null;
}

private void setupLexicalContainment() {
@@ -777,6 +782,17 @@ public LocalVariable lookupExistingLVar(String name) {
return localVars.get(name);
}

public ArgumentDescriptor[] getArgumentDescriptors() {
return argDesc;
}

/**
* Set upon completion of IRBuild of this IRMethod.
*/
public void setArgumentDescriptors(ArgumentDescriptor[] argDesc) {
this.argDesc = argDesc;
}

protected LocalVariable findExistingLocalVariable(String name, int depth) {
return localVars.get(name);
}
Original file line number Diff line number Diff line change
@@ -56,14 +56,14 @@ public IRubyObject interpret(ThreadContext context, IRubyObject self, Interprete
while (ipc < n) {
Instr instr = instrs[ipc];

ipc++;

Operation operation = instr.getOperation();
if (debug) {
Interpreter.LOG.info("I: {}", instr);
Interpreter.LOG.info("I: {" + ipc + "} ", instr);
Interpreter.interpInstrsCount++;
}

ipc++;

try {
switch (operation) {
case RETURN:
Original file line number Diff line number Diff line change
@@ -129,16 +129,18 @@ public IRubyObject interpret(ThreadContext context, IRubyObject self,
// Enter the looooop!
while (ipc < n) {
Instr instr = instrs[ipc];
ipc++;

Operation operation = instr.getOperation();
if (debug) {
Interpreter.LOG.info("I: {}", instr);
Interpreter.LOG.info("I: {" + ipc + "} ", instr);
Interpreter.interpInstrsCount++;
} else if (profile) {
Profiler.instrTick(operation);
Interpreter.interpInstrsCount++;
}

ipc++;

try {
switch (operation.opClass) {
case INT_OP:
Original file line number Diff line number Diff line change
@@ -56,16 +56,18 @@ public IRubyObject interpret(ThreadContext context, IRubyObject self,
// Enter the looooop!
while (ipc < n) {
Instr instr = instrs[ipc];
ipc++;

Operation operation = instr.getOperation();
if (debug) {
Interpreter.LOG.info("I: {}", instr);
Interpreter.LOG.info("I: {" + ipc + "} ", instr);
Interpreter.interpInstrsCount++;
} else if (profile) {
Profiler.instrTick(operation);
Interpreter.interpInstrsCount++;
}

ipc++;

try {
switch (operation.opClass) {
case ARG_OP:
5 changes: 2 additions & 3 deletions core/src/main/java/org/jruby/ir/runtime/IRRuntimeHelpers.java
Original file line number Diff line number Diff line change
@@ -456,11 +456,10 @@ public static IRubyObject yieldSpecific(ThreadContext context, Object blk) {
return b.yieldSpecific(context);
}

public static IRubyObject[] convertValueIntoArgArray(ThreadContext context, IRubyObject value, Arity arity, boolean argIsArray) {
public static IRubyObject[] convertValueIntoArgArray(ThreadContext context, IRubyObject value, int blockArity, boolean argIsArray) {
// SSS FIXME: This should not really happen -- so, some places in the runtime library are breaking this contract.
if (argIsArray && !(value instanceof RubyArray)) argIsArray = false;

int blockArity = arity.getValue();
switch (blockArity) {
case -1 : return argIsArray ? ((RubyArray)value).toJavaArray() : new IRubyObject[] { value };
case 0 : return new IRubyObject[] { value };
@@ -497,7 +496,7 @@ public static Block getBlockFromObject(ThreadContext context, Object value) {
} else if (value instanceof RubyProc) {
block = ((RubyProc) value).getBlock();
} else if (value instanceof RubyMethod) {
block = ((RubyProc)((RubyMethod)value).to_proc(context, null)).getBlock();
block = ((RubyProc)((RubyMethod)value).to_proc(context)).getBlock();
} else if ((value instanceof IRubyObject) && ((IRubyObject)value).isNil()) {
block = Block.NULL_BLOCK;
} else if (value instanceof IRubyObject) {
7 changes: 6 additions & 1 deletion core/src/main/java/org/jruby/ir/targets/JVMVisitor.java
Original file line number Diff line number Diff line change
@@ -174,7 +174,12 @@ public void emitScope(IRScope scope, String name, Signature signature, boolean s
}

// ensure there's at least one instr per block
if (bb.getInstrs().size() == 0) m.adapter.nop();
/* FIXME: (CON 20150507) This used to filter blocks that had no instructions and only emit nop for them,
but this led to BBs with no *bytecode-emitting* instructions failing to have a nop and triggering
verification errors when we attached an exception-handling range to them (because the leading
label failed to anchor anywhere, or anchored the same place as the trailing label). Until we can
detect that a BB will not emit any code, we return to always emitting the nop. */
m.adapter.nop();

// visit remaining instrs
for (Instr instr : bb.getInstrs()) {
43 changes: 43 additions & 0 deletions core/src/main/java/org/jruby/runtime/ArgumentDescriptor.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
package org.jruby.runtime;

import org.jruby.Ruby;
import org.jruby.RubyArray;

/**
* A description of a single argument in a Ruby argument list.
*/
public class ArgumentDescriptor {
/** The type of the argument */
public final ArgumentType type;

/** The name of the argument */
public final String name;

public static final ArgumentDescriptor[] EMPTY_ARRAY = new ArgumentDescriptor[0];

public ArgumentDescriptor(ArgumentType type, String name) {
this.type = type;
this.name = name;
}

public ArgumentDescriptor(ArgumentType type) {
this(type, null);
}

/**
* Generate the prefixed version of this descriptor.
*
* @see org.jruby.internal.runtime.methods.MethodArgs2
*/
public String toPrefixForm() {
return type.renderPrefixForm(name);
}

public RubyArray toArrayForm(Ruby runtime, boolean isLambda) {
if (type == ArgumentType.req && !isLambda) {
return ArgumentType.opt.toArrayForm(runtime, name);
} else {
return type.toArrayForm(runtime, name);
}
}
}
55 changes: 55 additions & 0 deletions core/src/main/java/org/jruby/runtime/ArgumentType.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
package org.jruby.runtime;

import org.jruby.Ruby;
import org.jruby.RubyArray;

/**
* Created by headius on 5/8/15.
*/
public enum ArgumentType {
key("key", "k", false),
keyreq("keyreq", "K", false),
keyrest("keyrest", "e", false),
block("block", "b", false),
opt("opt", "o", false),
rest("rest", "r", false),
req("req", "q", false),
anonreq("req", "n", true),
anonopt("opt", "O", true),
anonrest("rest", "R", true),
anonkeyrest("keyrest", "N", true);

ArgumentType(String symbolicName, String prefix, boolean anonymous) {
this.symbolicName = symbolicName;
this.prefix = prefix;
this.anonymous = anonymous;
}

public static ArgumentType valueOf(char prefix) {
switch (prefix) {
case 'k': return key;
case 'K': return keyreq;
case 'e': return keyrest;
case 'b': return block;
case 'o': return opt;
case 'r': return rest;
case 'q': return req;
case 'R': return anonrest;
case 'n': return anonreq;
case 'O': return anonopt;
default: return null;
}
}

public String renderPrefixForm(String name) {
return anonymous ? String.valueOf(prefix) : prefix + name;
}

public RubyArray toArrayForm(Ruby runtime, String name) {
return anonymous ? runtime.newArray(runtime.newSymbol(symbolicName)) : runtime.newArray(runtime.newSymbol(symbolicName), runtime.newSymbol(name));
}

public final String symbolicName;
public final String prefix;
public final boolean anonymous;
}
60 changes: 15 additions & 45 deletions core/src/main/java/org/jruby/runtime/BlockBody.java
Original file line number Diff line number Diff line change
@@ -36,27 +36,19 @@
import org.jruby.EvalType;
import org.jruby.RubyArray;
import org.jruby.RubyProc;
import org.jruby.common.IRubyWarnings.ID;
import org.jruby.ir.runtime.IRRuntimeHelpers;
import org.jruby.parser.StaticScope;
import org.jruby.runtime.builtin.IRubyObject;

/**
* The executable body portion of a closure.
*/
public abstract class BlockBody {
// FIXME: Maybe not best place, but move it to a good home
public static final int ZERO_ARGS = 0;
public static final int MULTIPLE_ASSIGNMENT = 1;
public static final int ARRAY = 2;
public static final int SINGLE_RESTARG = 3;

public static final String[] EMPTY_PARAMETER_LIST = new String[0];

protected final int argumentType;
protected final Signature signature;

public BlockBody(int argumentType, Signature signature) {
this.argumentType = argumentType;
public BlockBody(Signature signature) {
this.signature = signature;
}

@@ -122,10 +114,6 @@ public IRubyObject yield(ThreadContext context, IRubyObject value,
return yield(context, value, binding, type);
}

public int getArgumentType() {
return argumentType;
}

public IRubyObject call(ThreadContext context, Binding binding, Block.Type type) {
IRubyObject[] args = IRubyObject.NULL_ARRAY;
args = prepareArgumentsForCall(context, args, type);
@@ -217,43 +205,25 @@ public boolean isGiven() {
public abstract int getLine();

public IRubyObject[] prepareArgumentsForCall(ThreadContext context, IRubyObject[] args, Block.Type type) {
switch (type) {
case NORMAL: {
// assert false : "can this happen?";
if (args.length == 1 && args[0] instanceof RubyArray) {
if (argumentType == MULTIPLE_ASSIGNMENT || argumentType == SINGLE_RESTARG) {
args = ((RubyArray) args[0]).toJavaArray();
}
break;
}
}
case PROC: {
if (args.length == 1 && args[0] instanceof RubyArray) {
if (argumentType == MULTIPLE_ASSIGNMENT && argumentType != SINGLE_RESTARG) {
args = ((RubyArray) args[0]).toJavaArray();
}
}
break;
}
case LAMBDA:
if (argumentType == ARRAY && args.length != 1) {
context.runtime.getWarnings().warn(ID.MULTIPLE_VALUES_FOR_BLOCK, "multiple values for a block parameter (" + args.length + " for " + getSignature().arityValue() + ")");
if (args.length == 0) {
args = context.runtime.getSingleNilArray();
} else {
args = new IRubyObject[] {context.runtime.newArrayNoCopy(args)};
}
} else {
getSignature().checkArity(context.runtime, args);
if (type == Block.Type.LAMBDA) {
signature.checkArity(context.runtime, args);
} else {
// SSS FIXME: How is it even possible to "call" a NORMAL block?
// I thought only procs & lambdas can be called, and blocks are yielded to.
if (args.length == 1) {
// Convert value to arg-array, unwrapping where necessary
args = IRRuntimeHelpers.convertValueIntoArgArray(context, args[0], signature.arityValue(), type == Block.Type.NORMAL && args[0] instanceof RubyArray);
} else if (getSignature().arityValue() == 1 && !getSignature().restKwargs()) {
// discard excess arguments
args = args.length == 0 ? context.runtime.getSingleNilArray() : new IRubyObject[] { args[0] };
}
break;
}

return args;
}

public String[] getParameterList() {
return EMPTY_PARAMETER_LIST;
public ArgumentDescriptor[] getArgumentDescriptors() {
return ArgumentDescriptor.EMPTY_ARRAY;
}

public static final BlockBody NULL_BODY = new NullBlockBody();
2 changes: 1 addition & 1 deletion core/src/main/java/org/jruby/runtime/CallBlock.java
Original file line number Diff line number Diff line change
@@ -55,7 +55,7 @@ public static Block newCallClosure(IRubyObject self, RubyModule imClass, Arity a
}

private CallBlock(Signature signature, BlockCallback callback, ThreadContext context) {
super(BlockBody.SINGLE_RESTARG, signature);
super(signature);
this.callback = callback;
this.dummyScope = context.runtime.getStaticScopeFactory().getDummyScope();
}
2 changes: 1 addition & 1 deletion core/src/main/java/org/jruby/runtime/CallBlock19.java
Original file line number Diff line number Diff line change
@@ -57,7 +57,7 @@ public static Block newCallClosure(IRubyObject self, RubyModule imClass, Arity a
}

public CallBlock19(Signature signature, BlockCallback callback, ThreadContext context) {
super(BlockBody.SINGLE_RESTARG, signature);
super(signature);
this.callback = callback;
this.dummy = context.runtime.getStaticScopeFactory().getDummyScope();
}
241 changes: 0 additions & 241 deletions core/src/main/java/org/jruby/runtime/CallbackFactory.java

This file was deleted.

222 changes: 0 additions & 222 deletions core/src/main/java/org/jruby/runtime/CompiledBlock.java

This file was deleted.

198 changes: 0 additions & 198 deletions core/src/main/java/org/jruby/runtime/CompiledBlock19.java

This file was deleted.

22 changes: 0 additions & 22 deletions core/src/main/java/org/jruby/runtime/CompiledBlockCallback.java

This file was deleted.

This file was deleted.

66 changes: 0 additions & 66 deletions core/src/main/java/org/jruby/runtime/CompiledBlockLight.java

This file was deleted.

80 changes: 0 additions & 80 deletions core/src/main/java/org/jruby/runtime/CompiledBlockLight19.java

This file was deleted.

Original file line number Diff line number Diff line change
@@ -3,6 +3,7 @@
import org.jruby.EvalType;
import org.jruby.ir.IRClosure;
import org.jruby.ir.IRFlags;
import org.jruby.ir.IRMethod;
import org.jruby.ir.IRScope;
import org.jruby.ir.runtime.IRRuntimeHelpers;
import org.jruby.runtime.Block.Type;
@@ -18,7 +19,7 @@ public class CompiledIRBlockBody extends IRBlockBody {
protected boolean usesKwargs;

public CompiledIRBlockBody(MethodHandle handle, IRScope closure, long encodedSignature) {
super(closure.getStaticScope(), ((IRClosure)closure).getParameterList(), closure.getFileName(), closure.getLineNumber(), Signature.decode(encodedSignature));
super(closure.getStaticScope(), closure.getFileName(), closure.getLineNumber(), Signature.decode(encodedSignature));
this.handle = handle;
this.closure = (IRClosure)closure;
// FIXME: duplicated from InterpreterContext
@@ -30,6 +31,11 @@ public CompiledIRBlockBody(MethodHandle handle, IRScope closure, long encodedSig
closure.getStaticScope().determineModule();
}

@Override
public ArgumentDescriptor[] getArgumentDescriptors() {
return closure.getArgumentDescriptors();
}

protected IRubyObject commonYieldPath(ThreadContext context, IRubyObject[] args, IRubyObject self, Binding binding, Type type, Block block) {

// SSS: Important! Use getStaticScope() to use a copy of the static-scope stored in the block-body.
54 changes: 0 additions & 54 deletions core/src/main/java/org/jruby/runtime/CompiledSharedScopeBlock.java

This file was deleted.

Original file line number Diff line number Diff line change
@@ -9,14 +9,15 @@ public abstract class ContextAwareBlockBody extends BlockBody {
/** The static scope for the block body */
protected StaticScope scope;

public ContextAwareBlockBody(StaticScope scope, Signature signature, int argumentType) {
super(argumentType, signature);
public ContextAwareBlockBody(StaticScope scope, Signature signature) {
super(signature);

this.scope = scope;
}

@Deprecated
public ContextAwareBlockBody(StaticScope scope, Arity arity, int argumentType) {
this(scope, Signature.from(arity), argumentType);
this(scope, Signature.from(arity));
}

protected Frame pre(ThreadContext context, Binding binding) {
Loading

0 comments on commit 08193c6

Please sign in to comment.