Skip to content
Permalink

Comparing changes

Choose two branches to see what’s changed or to start a new pull request. If you need to, you can also or learn more about diff comparisons.

Open a pull request

Create a new pull request by comparing changes across two branches. If you need to, you can also . Learn more about diff comparisons here.
base repository: jruby/jruby
Failed to load repositories. Confirm that selected base ref is valid, then try again.
Loading
base: 09c2a3fb2d60
Choose a base ref
...
head repository: jruby/jruby
Failed to load repositories. Confirm that selected head ref is valid, then try again.
Loading
compare: bfe88168d668
Choose a head ref
  • 2 commits
  • 7 files changed
  • 1 contributor

Commits on May 2, 2015

  1. [Truffle] Fixed receiver & argument order for Regexp match.

    When looking at Regexp matches of the form 'BasicObject =~ Regexp', the AST has the receiver and value nodes backward and we trusted the values as named. As a consequence, we weren't calling the correct =~ method and getting incorrect results if the implementations for the two types weren't symmetric.
    nirvdrum committed May 2, 2015
    Copy the full SHA
    eb4d388 View commit details
  2. 2
    Copy the full SHA
    bfe8816 View commit details
1 change: 1 addition & 0 deletions spec/truffle/tags/core/exception/backtrace_tags.txt
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
fails:Exception#backtrace when redefined does not affect the behaviour of Exception#message
fails:Exception#backtrace contains lines of the same format for each prior position in the stack
2 changes: 2 additions & 0 deletions spec/truffle/tags/core/file/grpowned_tags.txt
Original file line number Diff line number Diff line change
@@ -1,2 +1,4 @@
fails:File.grpowned? takes non primary groups into account
fails(windows):File.grpowned? returns false if the file exist
fails:File.grpowned? returns true if the file exist
fails:File.grpowned? accepts an object that has a #to_path method
2 changes: 2 additions & 0 deletions spec/truffle/tags/core/file/stat/grpowned_tags.txt
Original file line number Diff line number Diff line change
@@ -1,2 +1,4 @@
fails:File::Stat#grpowned? takes non primary groups into account
fails(windows):File::Stat#grpowned? returns false if the file exist
fails:File::Stat#grpowned? returns true if the file exist
fails:File::Stat#grpowned? accepts an object that has a #to_path method
2 changes: 2 additions & 0 deletions spec/truffle/tags/core/filetest/grpowned_tags.txt
Original file line number Diff line number Diff line change
@@ -1 +1,3 @@
fails:FileTest.grpowned? takes non primary groups into account
fails:FileTest.grpowned? returns true if the file exist
fails:FileTest.grpowned? accepts an object that has a #to_path method
1 change: 1 addition & 0 deletions spec/truffle/tags/core/module/name_tags.txt
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
fails:Module#name is set with a conditional assignment to a nested constant
fails:Module#name preserves the encoding in which the class was defined
fails:Module#name is nil for a nested module created with the module keyword
Original file line number Diff line number Diff line change
@@ -15,6 +15,11 @@
import com.oracle.truffle.api.source.SourceSection;
import com.oracle.truffle.api.utilities.ConditionProfile;
import org.jruby.truffle.nodes.RubyNode;
import org.jruby.truffle.nodes.coerce.ToStrNode;
import org.jruby.truffle.nodes.coerce.ToStrNodeGen;
import org.jruby.truffle.nodes.dispatch.CallDispatchHeadNode;
import org.jruby.truffle.nodes.dispatch.DispatchHeadNode;
import org.jruby.truffle.nodes.dispatch.DispatchHeadNodeFactory;
import org.jruby.truffle.runtime.RubyContext;
import org.jruby.truffle.runtime.control.RaiseException;
import org.jruby.truffle.runtime.core.*;
@@ -93,6 +98,9 @@ protected RubyString escape(VirtualFrame frame, RubyString string) {
@CoreMethod(names = "=~", required = 1)
public abstract static class MatchOperatorNode extends CoreMethodArrayArgumentsNode {

@Child private CallDispatchHeadNode toSNode;
@Child private ToStrNode toStrNode;

public MatchOperatorNode(RubyContext context, SourceSection sourceSection) {
super(context, sourceSection);
}
@@ -103,14 +111,28 @@ public Object match(RubyRegexp regexp, RubyString string) {
}

@Specialization
public Object match(RubyRegexp regexp, RubyBasicObject other) {
notDesignedForCompilation();
public Object match(VirtualFrame frame, RubyRegexp regexp, RubySymbol symbol) {
if (toSNode == null) {
CompilerDirectives.transferToInterpreter();
toSNode = insert(DispatchHeadNodeFactory.createMethodCall(getContext()));
}

if (other instanceof RubyString) {
return match(regexp, (RubyString) other);
} else {
return nil();
return match(regexp, (RubyString) toSNode.call(frame, symbol, "to_s", null));
}

@Specialization
public Object match(RubyRegexp regexp, RubyNilClass nil) {
return nil();
}

@Specialization(guards = { "!isRubyString(other)", "!isRubySymbol(other)", "!isRubyNilClass(other)" })
public Object matchGeneric(VirtualFrame frame, RubyRegexp regexp, RubyBasicObject other) {
if (toStrNode == null) {
CompilerDirectives.transferToInterpreter();
toStrNode = insert(ToStrNodeGen.create(getContext(), getSourceSection(), null));
}

return match(regexp, toStrNode.executeRubyString(frame, other));
}

}
Original file line number Diff line number Diff line change
@@ -1769,13 +1769,17 @@ def destructure4r((*c,d))

@Override
public RubyNode visitMatchNode(org.jruby.ast.MatchNode node) {
// Triggered when a Regexp literal is used as a conditional's value.

final org.jruby.ast.Node argsNode = buildArrayNode(node.getPosition(), new org.jruby.ast.GlobalVarNode(node.getPosition(), "$_"));
final org.jruby.ast.Node callNode = new CallNode(node.getPosition(), node.getRegexpNode(), "=~", argsNode, null);
return callNode.accept(this);
}

@Override
public RubyNode visitMatch2Node(org.jruby.ast.Match2Node node) {
// Triggered when a Regexp literal is the LHS of an expression.

if (node.getReceiverNode() instanceof org.jruby.ast.RegexpNode) {
final org.jruby.ast.RegexpNode regexpNode = (org.jruby.ast.RegexpNode) node.getReceiverNode();
final Regex regex = new Regex(regexpNode.getValue().bytes(), 0, regexpNode.getValue().length(), regexpNode.getOptions().toOptions(), regexpNode.getEncoding(), Syntax.RUBY);
@@ -1807,8 +1811,12 @@ public RubyNode visitMatch2Node(org.jruby.ast.Match2Node node) {

@Override
public RubyNode visitMatch3Node(org.jruby.ast.Match3Node node) {
final org.jruby.ast.Node argsNode = buildArrayNode(node.getPosition(), node.getValueNode());
final org.jruby.ast.Node callNode = new CallNode(node.getPosition(), node.getReceiverNode(), "=~", argsNode, null);
// Triggered when a Regexp literal is the RHS of an expression.

// This looks weird, but the receiver and value nodes are reversed by the time they get to us, so we need to
// reverse them back in the CallNode.
final org.jruby.ast.Node argsNode = buildArrayNode(node.getPosition(), node.getReceiverNode());
final org.jruby.ast.Node callNode = new CallNode(node.getPosition(), node.getValueNode(), "=~", argsNode, null);
return callNode.accept(this);
}