Skip to content

Commit

Permalink
Try exposing IsCharacterHeadNode to Primitive.
Browse files Browse the repository at this point in the history
  • Loading branch information
itarato committed May 25, 2023
1 parent feb2ad1 commit 1c24ac5
Show file tree
Hide file tree
Showing 3 changed files with 61 additions and 54 deletions.
60 changes: 60 additions & 0 deletions src/main/java/org/truffleruby/core/encoding/CharacterNodes.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
/*
* Copyright (c) 2020, 2023 Oracle and/or its affiliates. All rights reserved. This
* code is released under a tri EPL/GPL/LGPL license. You can use it,
* redistribute it and/or modify it under the terms of the:
*
* Eclipse Public License version 2.0, or
* GNU General Public License version 2, or
* GNU Lesser General Public License version 2.1.
*/
package org.truffleruby.core.encoding;

import com.oracle.truffle.api.CompilerDirectives.TruffleBoundary;
import com.oracle.truffle.api.dsl.Cached;
import com.oracle.truffle.api.dsl.Specialization;
import com.oracle.truffle.api.strings.AbstractTruffleString;
import com.oracle.truffle.api.strings.TruffleString;
import org.truffleruby.annotations.CoreModule;
import org.truffleruby.annotations.Primitive;
import org.truffleruby.builtins.PrimitiveArrayArgumentsNode;

@CoreModule("Truffle::Encoding")
public abstract class CharacterNodes {

/** Whether the position at byteOffset is the start of a character and not in the middle of a character */
@Primitive(name = "is_character_head", lowerFixnum = 2)
public abstract static class IsCharacterHeadNode extends PrimitiveArrayArgumentsNode {

public abstract boolean execute(RubyEncoding enc, AbstractTruffleString string, int byteOffset);

@Specialization(guards = "enc.isSingleByte")
protected boolean singleByte(RubyEncoding enc, AbstractTruffleString string, int byteOffset) {
// return offset directly (org.jcodings.SingleByteEncoding#leftAdjustCharHead)
return true;
}

@Specialization(guards = { "!enc.isSingleByte", "enc.jcoding.isUTF8()" })
protected boolean utf8(RubyEncoding enc, AbstractTruffleString string, int byteOffset,
@Cached TruffleString.ReadByteNode readByteNode) {
// based on org.jcodings.specific.BaseUTF8Encoding#leftAdjustCharHead
return utf8IsLead(readByteNode.execute(string, byteOffset, enc.tencoding));

}

@TruffleBoundary
@Specialization(guards = { "!enc.isSingleByte", "!enc.jcoding.isUTF8()" })
protected boolean other(RubyEncoding enc, AbstractTruffleString string, int byteOffset,
@Cached TruffleString.GetInternalByteArrayNode getInternalByteArrayNode) {
var byteArray = getInternalByteArrayNode.execute(string, enc.tencoding);
int addedOffsets = byteArray.getOffset() + byteOffset;
return enc.jcoding.leftAdjustCharHead(byteArray.getArray(), byteArray.getOffset(), addedOffsets,
byteArray.getEnd()) == addedOffsets;
}

/** Copied from org.jcodings.specific.BaseUTF8Encoding */
private static boolean utf8IsLead(int c) {
return ((c & 0xc0) & 0xff) != 0x80;
}

}
}

This file was deleted.

2 changes: 1 addition & 1 deletion src/main/java/org/truffleruby/core/string/StringNodes.java
Original file line number Diff line number Diff line change
Expand Up @@ -115,7 +115,7 @@
import org.truffleruby.core.cast.ToStrNode;
import org.truffleruby.core.cast.ToStrNodeGen;
import org.truffleruby.core.encoding.EncodingNodes.NegotiateCompatibleStringEncodingNode;
import org.truffleruby.core.encoding.IsCharacterHeadNode;
import org.truffleruby.core.encoding.CharacterNodes.IsCharacterHeadNode;
import org.truffleruby.core.encoding.EncodingNodes.CheckEncodingNode;
import org.truffleruby.core.encoding.EncodingNodes.GetActualEncodingNode;
import org.truffleruby.core.encoding.Encodings;
Expand Down

0 comments on commit 1c24ac5

Please sign in to comment.