Skip to content

Commit a4d241e

Browse files
committed
Implement rb_check_symbol_cstr()
1 parent 3bd4c3c commit a4d241e

File tree

4 files changed

+34
-12
lines changed

4 files changed

+34
-12
lines changed

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ Compatibility:
4040
* Implemented `keyword_init: true` for `Struct.new` (#1789, @XrXr).
4141
* Implemented `MatchData#dup` (#1792, @XrXr).
4242
* Implemented a native storage strategy for arrays to allow better C extension compatibility.
43+
* Implemented `rb_check_symbol_cstr` (#1814).
4344

4445
Performance:
4546

src/main/c/cext/ruby.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3283,7 +3283,8 @@ ID rb_check_id_cstr(const char *ptr, long len, rb_encoding *enc) {
32833283
}
32843284

32853285
VALUE rb_check_symbol_cstr(const char *ptr, long len, rb_encoding *enc) {
3286-
rb_tr_error("rb_check_symbol_cstr not implemented");
3286+
VALUE str = rb_enc_str_new(ptr, len, enc);
3287+
return RUBY_CEXT_INVOKE("rb_check_symbol_cstr", str);
32873288
}
32883289

32893290
int rb_econv_has_convpath_p(const char* from_encoding, const char* to_encoding) {

src/main/java/org/truffleruby/cext/CExtNodes.java

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1589,4 +1589,15 @@ protected Object unwrapFunction() {
15891589
return new ValueWrapperManager.WrapperFunction();
15901590
}
15911591
}
1592+
1593+
@CoreMethod(names = "rb_check_symbol_cstr", onSingleton = true, required = 1)
1594+
public abstract static class RbCheckSymbolCStrNode extends CoreMethodArrayArgumentsNode {
1595+
1596+
@Specialization
1597+
protected DynamicObject checkSymbolCStr(DynamicObject str) {
1598+
final DynamicObject sym = getContext().getSymbolTable().getSymbolIfExists(rope(str));
1599+
return sym == null ? nil() : sym;
1600+
}
1601+
1602+
}
15921603
}

src/main/java/org/truffleruby/core/symbol/SymbolTable.java

Lines changed: 20 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -105,29 +105,38 @@ public DynamicObject getSymbol(String string) {
105105

106106
@TruffleBoundary
107107
public DynamicObject getSymbol(Rope rope) {
108-
if (rope instanceof NativeRope) {
109-
rope = ((NativeRope) rope).toLeafRope();
110-
}
111-
112-
if (rope.isAsciiOnly() && rope.getEncoding() != USASCIIEncoding.INSTANCE) {
113-
rope = rope.withEncoding(USASCIIEncoding.INSTANCE, CodeRange.CR_7BIT);
114-
}
115-
116-
final RopeKey ropeKey = new RopeKey(rope, hashing);
117-
108+
final RopeKey ropeKey = createRopeKey(rope);
118109
final DynamicObject symbol = symbolMap.get(ropeKey);
119110
if (symbol != null) {
120111
return symbol;
121112
}
122113

123-
final Rope cachedRope = ropeCache.getRope(rope);
114+
final Rope cachedRope = ropeCache.getRope(ropeKey.getRope());
124115
final DynamicObject newSymbol = createSymbol(cachedRope);
125116
// Use a RopeKey with the cached Rope in symbolMap, since the Symbol refers to it and so we
126117
// do not keep rope alive unnecessarily.
127118
final RopeKey cachedRopeKey = new RopeKey(cachedRope, hashing);
128119
return symbolMap.addInCacheIfAbsent(cachedRopeKey, newSymbol);
129120
}
130121

122+
@TruffleBoundary
123+
public DynamicObject getSymbolIfExists(Rope rope) {
124+
final RopeKey ropeKey = createRopeKey(rope);
125+
return symbolMap.get(ropeKey);
126+
}
127+
128+
private RopeKey createRopeKey(Rope rope) {
129+
if (rope instanceof NativeRope) {
130+
rope = ((NativeRope) rope).toLeafRope();
131+
}
132+
133+
if (rope.isAsciiOnly() && rope.getEncoding() != USASCIIEncoding.INSTANCE) {
134+
rope = rope.withEncoding(USASCIIEncoding.INSTANCE, CodeRange.CR_7BIT);
135+
}
136+
137+
return new RopeKey(rope, hashing);
138+
}
139+
131140
private DynamicObject createSymbol(Rope cachedRope) {
132141
final String string = RopeOperations.decodeOrEscapeBinaryRope(cachedRope);
133142
return Layouts.SYMBOL.createSymbol(

0 commit comments

Comments
 (0)