Skip to content

Commit

Permalink
Showing 10 changed files with 53 additions and 65 deletions.
Original file line number Diff line number Diff line change
@@ -172,7 +172,7 @@ def post_match
end

def pre_match
@string.byteslice(0, match.full.at(0)) if @match
@string.byteslice(0, match.byte_begin(0)) if @match
end

def reset_state
@@ -296,7 +296,7 @@ def _scan(pattern, advance_pos, getstr, headonly)

return nil unless @match

fin = @match.full.at(1)
fin = @match.byte_end(0)

@prev_pos = @pos

Original file line number Diff line number Diff line change
@@ -30,10 +30,7 @@ DynamicObject createMatchData(DynamicObjectFactory factory,
DynamicObject pre,
DynamicObject post,
DynamicObject global,
int begin,
int end,
@Nullable Region charOffsets,
@Nullable Object fullTuple);
@Nullable Region charOffsets);

boolean isMatchData(DynamicObject object);
boolean isMatchData(Object object);
@@ -45,13 +42,8 @@ DynamicObject createMatchData(DynamicObjectFactory factory,
DynamicObject getPre(DynamicObject object);
DynamicObject getPost(DynamicObject object);
DynamicObject getGlobal(DynamicObject object);
int getBegin(DynamicObject object);
int getEnd(DynamicObject object);

Region getCharOffsets(DynamicObject object);
void setCharOffsets(DynamicObject object, Region value);

Object getFullTuple(DynamicObject object);
void setFullTuple(DynamicObject object, Object value);

}
Original file line number Diff line number Diff line change
@@ -18,6 +18,7 @@
import com.oracle.truffle.api.object.DynamicObject;
import com.oracle.truffle.api.profiles.BranchProfile;
import com.oracle.truffle.api.source.SourceSection;
import java.util.Arrays;
import org.jcodings.Encoding;
import org.joni.Region;
import org.joni.exception.ValueException;
@@ -39,13 +40,9 @@
import org.jruby.truffle.language.RubyGuards;
import org.jruby.truffle.language.RubyNode;
import org.jruby.truffle.language.control.RaiseException;
import org.jruby.truffle.language.dispatch.CallDispatchHeadNode;
import org.jruby.truffle.language.dispatch.DispatchHeadNodeFactory;
import org.jruby.util.ByteList;
import org.jruby.util.StringSupport;

import java.util.Arrays;

@CoreClass("MatchData")
public abstract class MatchDataNodes {

@@ -303,30 +300,40 @@ protected boolean inBounds(DynamicObject matchData, int index) {
}

@NonStandard
@CoreMethod(names = "full")
public abstract static class FullNode extends CoreMethodArrayArgumentsNode {
@CoreMethod(names = "byte_begin", required = 1, lowerFixnum = 1)
public abstract static class ByteBeginNode extends CoreMethodArrayArgumentsNode {

@Child private CallDispatchHeadNode newTupleNode;

@Specialization
public Object full(VirtualFrame frame, DynamicObject matchData) {
if (Layouts.MATCH_DATA.getFullTuple(matchData) != null) {
return Layouts.MATCH_DATA.getFullTuple(matchData);
@Specialization(guards = "inBounds(matchData, index)")
public Object byteBegin(DynamicObject matchData, int index) {
int b = Layouts.MATCH_DATA.getRegion(matchData).beg[index];
if (b < 0) {
return getContext().getCoreLibrary().getNilObject();
} else {
return b;
}
}

if (newTupleNode == null) {
CompilerDirectives.transferToInterpreterAndInvalidate();
newTupleNode = insert(DispatchHeadNodeFactory.createMethodCall(getContext()));
}
protected boolean inBounds(DynamicObject matchData, int index) {
return index >= 0 && index < Layouts.MATCH_DATA.getRegion(matchData).numRegs;
}
}

final Object fullTuple = newTupleNode.call(frame,
coreLibrary().getTupleClass(),
"create",
Layouts.MATCH_DATA.getBegin(matchData), Layouts.MATCH_DATA.getEnd(matchData));
@NonStandard
@CoreMethod(names = "byte_end", required = 1, lowerFixnum = 1)
public abstract static class ByteEndNode extends CoreMethodArrayArgumentsNode {

Layouts.MATCH_DATA.setFullTuple(matchData, fullTuple);
@Specialization(guards = "inBounds(matchData, index)")
public Object byteEnd(DynamicObject matchData, int index) {
int e = Layouts.MATCH_DATA.getRegion(matchData).end[index];
if (e < 0) {
return getContext().getCoreLibrary().getNilObject();
} else {
return e;
}
}

return fullTuple;
protected boolean inBounds(DynamicObject matchData, int index) {
return index >= 0 && index < Layouts.MATCH_DATA.getRegion(matchData).numRegs;
}
}

Original file line number Diff line number Diff line change
@@ -150,7 +150,7 @@ public static Object matchCommon(RubyContext context, RopeNodes.MakeSubstringNod
final DynamicObject global = createSubstring(makeSubstringNode, source, region.beg[0], region.end[0] - region.beg[0]);

final DynamicObject matchObject = Layouts.MATCH_DATA.createMatchData(Layouts.CLASS.getInstanceFactory(context.getCoreLibrary().getMatchDataClass()),
source, regexp, region, values, pre, post, global, matcher.getBegin(), matcher.getEnd(), null, null);
source, regexp, region, values, pre, post, global, null);

if (operator) {
if (values.length > 0) {
Original file line number Diff line number Diff line change
@@ -1854,10 +1854,6 @@ public RubyNode visitInstVarNode(org.jruby.ast.InstVarNode node) {
ret = MatchDataNodesFactory.RubiniusSourceNodeGen.create(self);
setSourceSection(ret, sourceSection);
return addNewlineIfNeeded(node, ret);
} else if (name.equals("@full")) {
// Delegate to MatchData#full.
ret = new RubyCallNode(context, sourceSection, "full", self, null, false);
return addNewlineIfNeeded(node, ret);
} else if (name.equals("@regexp")) {
ret = MatchDataNodesFactory.RegexpNodeFactory.create(new RubyNode[]{ self });
setSourceSection(ret, sourceSection);
3 changes: 2 additions & 1 deletion truffle/src/main/ruby/core/dir_glob.rb
Original file line number Diff line number Diff line change
@@ -249,7 +249,8 @@ def self.path_split(str)
last_match = nil

while match = %r!/+!.match_from(str, start)
cur_start, cur_end = match.full
cur_start = match.byte_begin(0)
cur_end = match.byte_end(0)
ret << str.byteslice(start, cur_start - start)
ret << str.byteslice(cur_start, cur_end - cur_start)

18 changes: 5 additions & 13 deletions truffle/src/main/ruby/core/regexp.rb
Original file line number Diff line number Diff line change
@@ -378,37 +378,29 @@ def names
end

def pre_match_from(idx)
return @source.byteslice(0, 0) if @full.at(0) == 0
nd = @full.at(0) - 1
return @source.byteslice(0, 0) if self.byte_begin(0) == 0
nd = self.byte_begin(0) - 1
@source.byteslice(idx, nd-idx+1)
end

def collapsing?
@full[0] == @full[1]
self.byte_begin(0) == self.byte_end(0)
end

def inspect
capts = captures
if capts.empty?
"#<MatchData \"#{matched_area}\">"
"#<MatchData \"#{self[0]}\">"
else
idx = 0
capts.map! { |capture| "#{idx += 1}:#{capture.inspect}" }
"#<MatchData \"#{matched_area}\" #{capts.join(" ")}>"
"#<MatchData \"#{self[0]}\" #{capts.join(" ")}>"
end
end

def values_at(*indexes)
indexes.map { |i| self[i] }.flatten(1)
end

def matched_area
x = @full.at(0)
y = @full.at(1)
@source.byteslice(x, y-x)
end

private :matched_area

end

6 changes: 3 additions & 3 deletions truffle/src/main/ruby/core/splitter.rb
Original file line number Diff line number Diff line change
@@ -123,7 +123,7 @@ def self.split(string, pattern, limit)

collapsed = match.collapsing?

unless collapsed && (match.full.at(0) == last_match_end)
unless collapsed && (match.byte_begin(0) == last_match_end)
ret << match.pre_match_from(last_match_end)

# length > 1 means there are captures
@@ -132,13 +132,13 @@ def self.split(string, pattern, limit)
end
end

start = match.full.at(1)
start = match.byte_end(0)
if collapsed
start += 1
end

last_match = match
last_match_end = last_match.full.at(1)
last_match_end = last_match.byte_end(0)
end

if last_match
18 changes: 9 additions & 9 deletions truffle/src/main/ruby/core/string.rb
Original file line number Diff line number Diff line change
@@ -251,7 +251,7 @@ def scan(pattern)
end

while match = pattern.match_from(self, index)
fin = match.full.at(1)
fin = match.byte_end(0)

if match.collapsing?
if char = find_character(fin)
@@ -1160,7 +1160,7 @@ def gsub(pattern, replacement=undefined)
last_match = nil

ret = byteslice(0, 0) # Empty string and string subclass
offset = match.full.at(0) if match
offset = match.byte_begin(0) if match

while match
if str = match.pre_match_from(last_end)
@@ -1191,7 +1191,7 @@ def gsub(pattern, replacement=undefined)

tainted ||= val.tainted?

last_end = match.full.at(1)
last_end = match.byte_end(0)

if match.collapsing?
if char = find_character(offset)
@@ -1200,15 +1200,15 @@ def gsub(pattern, replacement=undefined)
offset += 1
end
else
offset = match.full.at(1)
offset = match.byte_end(0)
end

last_match = match

match = pattern.match_from self, offset
break unless match

offset = match.full.at(0)
offset = match.byte_begin(0)
end

Regexp.last_match = last_match
@@ -1269,7 +1269,7 @@ def gsub!(pattern, replacement=undefined)
last_match = nil

ret = byteslice(0, 0) # Empty string and string subclass
offset = match.full.at(0)
offset = match.byte_begin(0)

while match
if str = match.pre_match_from(last_end)
@@ -1300,7 +1300,7 @@ def gsub!(pattern, replacement=undefined)

tainted ||= val.tainted?

last_end = match.full.at(1)
last_end = match.byte_end(0)

if match.collapsing?
if char = find_character(offset)
@@ -1309,15 +1309,15 @@ def gsub!(pattern, replacement=undefined)
offset += 1
end
else
offset = match.full.at(1)
offset = match.byte_end(0)
end

last_match = match

match = pattern.match_from self, offset
break unless match

offset = match.full.at(0)
offset = match.byte_begin(0)
end

Regexp.last_match = last_match
2 changes: 1 addition & 1 deletion truffle/src/main/ruby/core/symbol.rb
Original file line number Diff line number Diff line change
@@ -84,7 +84,7 @@ def match(pattern)
when Regexp
match_data = pattern.search_region(str, 0, str.bytesize, true)
Regexp.last_match = match_data
return match_data.full[0] if match_data
return match_data.byte_begin(0) if match_data
when String
raise TypeError, "type mismatch: String given"
else

0 comments on commit 24dd66d

Please sign in to comment.