diff --git a/core/src/main/java/org/jruby/RubyHash.java b/core/src/main/java/org/jruby/RubyHash.java index c974ed8d6be..c5b39bce15b 100644 --- a/core/src/main/java/org/jruby/RubyHash.java +++ b/core/src/main/java/org/jruby/RubyHash.java @@ -1624,7 +1624,7 @@ public RubyHash each_pairCommon(final ThreadContext context, final Block block) public void visit(ThreadContext context, RubyHash self, IRubyObject key, IRubyObject value, int index, Block block) { if (block.type == Block.Type.LAMBDA) { block.call(context, context.runtime.newArray(key, value)); - } else if (block.getSignature().arityValue() > 1) { + } else if (block.getSignature().isSpreadable()) { block.yieldSpecific(context, key, value); } else { block.yield(context, context.runtime.newArray(key, value)); diff --git a/core/src/main/java/org/jruby/ir/runtime/IRRuntimeHelpers.java b/core/src/main/java/org/jruby/ir/runtime/IRRuntimeHelpers.java index 1b5c21d417c..2cce0936f2b 100644 --- a/core/src/main/java/org/jruby/ir/runtime/IRRuntimeHelpers.java +++ b/core/src/main/java/org/jruby/ir/runtime/IRRuntimeHelpers.java @@ -513,7 +513,9 @@ public static IRubyObject[] convertValueIntoArgArray(ThreadContext context, IRub new IRubyObject[] { value }; case 0: case 1: - return new IRubyObject[] { value }; + return signature.rest() == org.jruby.runtime.Signature.Rest.ANON ? + IRBlockBody.toAry(context, value) : + new IRubyObject[] { value }; } return IRBlockBody.toAry(context, value); diff --git a/core/src/main/java/org/jruby/runtime/IRBlockBody.java b/core/src/main/java/org/jruby/runtime/IRBlockBody.java index 6ba10157600..ae27eedf281 100644 --- a/core/src/main/java/org/jruby/runtime/IRBlockBody.java +++ b/core/src/main/java/org/jruby/runtime/IRBlockBody.java @@ -102,14 +102,13 @@ public IRubyObject yieldSpecific(ThreadContext context, Block block, IRubyObject } private IRubyObject yieldSpecificMultiArgsCommon(ThreadContext context, Block block, IRubyObject... args) { - int blockArity = signature.arityValue(); - if (blockArity == 1) { + if (signature.isOneArgument()) { args = new IRubyObject[] { RubyArray.newArrayMayCopy(context.runtime, args) }; } if (canCallDirect()) return yieldDirect(context, block, args, null); - if (blockArity == 0) { + if (signature.arityValue() == 0) { args = IRubyObject.NULL_ARRAY; // discard args } if (block.type == Block.Type.LAMBDA) signature.checkArity(context.runtime, args); diff --git a/core/src/main/java/org/jruby/runtime/Signature.java b/core/src/main/java/org/jruby/runtime/Signature.java index d4725735b85..1590067cd66 100644 --- a/core/src/main/java/org/jruby/runtime/Signature.java +++ b/core/src/main/java/org/jruby/runtime/Signature.java @@ -85,7 +85,7 @@ public boolean restKwargs() { * Are there an exact (fixed) number of parameters to this signature? */ public boolean isFixed() { - return arityValue() >= 0; + return arityValue() >= 0 && rest != Rest.ANON; } /** @@ -135,8 +135,9 @@ public int calculateArityValue() { int oneForKeywords = requiredKwargs > 0 ? 1 : 0; int fixedValue = pre() + post() + oneForKeywords; boolean hasOptionalKeywords = kwargs - requiredKwargs > 0; + boolean optionalFromRest = rest() != Rest.NONE && rest != Rest.ANON; - if (opt() > 0 || rest() != Rest.NONE || (hasOptionalKeywords || restKwargs()) && oneForKeywords == 0) { + if (opt() > 0 || optionalFromRest || (hasOptionalKeywords || restKwargs()) && oneForKeywords == 0) { return -1 * (fixedValue + 1); } @@ -153,7 +154,7 @@ public int arityValue() { * @return true if the signature expects multiple args */ public boolean isSpreadable() { - return arityValue < -1 || arityValue > 1 || (opt > 0 && !restKwargs()); + return arityValue < -1 || arityValue > 1 || (opt > 0 && !restKwargs()) || rest == Rest.ANON; } diff --git a/spec/tags/ruby/core/proc/arity_tags.txt b/spec/tags/ruby/core/proc/arity_tags.txt deleted file mode 100644 index e742e2ff5e3..00000000000 --- a/spec/tags/ruby/core/proc/arity_tags.txt +++ /dev/null @@ -1,2 +0,0 @@ -fails:Proc#arity for instances created with lambda { || } returns positive values for definition '@a = lambda { |a, | }' -fails:Proc#arity for instances created with proc { || } returns positive values for definition '@a = proc { |a, | }'