Skip to content

Commit

Permalink
Showing 196 changed files with 6,378 additions and 5,127 deletions.
2 changes: 0 additions & 2 deletions .travis.yml
Original file line number Diff line number Diff line change
@@ -43,8 +43,6 @@ matrix:
jdk: oraclejdk8
- env: JT='test integration'
jdk: oraclejdk8
- env: JT='test gems' JAVA_OPTS="$JAVA_OPTS -Xmx512m" HAS_REDIS=true
jdk: oraclejdk8
- env: JT='test tck'
jdk: oraclejdk8
- env: JT=check_ambiguous_arguments SKIP_BUILD=true
2 changes: 1 addition & 1 deletion VERSION
Original file line number Diff line number Diff line change
@@ -1 +1 @@
9.1.1.0-SNAPSHOT
9.1.2.0-SNAPSHOT
4 changes: 2 additions & 2 deletions bin/jruby-cext-c
Original file line number Diff line number Diff line change
@@ -39,12 +39,12 @@ end
CONFIG = YAML.load_file(CONFIG_FILE)

SRC = Dir[File.join(CEXT_DIR, CONFIG['src'])]
OUT = File.join(CEXT_DIR, CONFIG['out'])
OUT = File.expand_path(CONFIG['out'], CEXT_DIR)

LL = []

SRC.each do |src|
ll = File.join(File.dirname(src), File.basename(src, '.*') + '.ll')
ll = File.join(File.dirname(OUT), File.basename(src, '.*') + '.ll')
mx 'su-clang', "-I#{SULONG_DIR}/include", '-Ilib/ruby/truffle/cext', '-S', '-emit-llvm', src, '-o', ll
mx 'su-opt', '-S', '-mem2reg', ll, '-o', ll
LL.push ll
3 changes: 2 additions & 1 deletion bin/jruby.bash
Original file line number Diff line number Diff line change
@@ -246,6 +246,7 @@ do
-X+T)
JRUBY_CP="$JRUBY_CP$CP_DELIMITER$JRUBY_HOME/lib/jruby-truffle.jar"
ruby_args=("${ruby_args[@]}" "-X+T")
USING_TRUFFLE="true"
;;
# Match -Xa.b.c=d to translate to -Da.b.c=d as a java option
-X*)
@@ -356,7 +357,7 @@ if [ "$nailgun_client" != "" ]; then
exit 1
fi
else
if [ "$VERIFY_JRUBY" != "" ]; then
if [[ "$VERIFY_JRUBY" != "" && -z "$USING_TRUFFLE" ]]; then
if [ "$PROFILE_ARGS" != "" ]; then
echo "Running with instrumented profiler"
fi
2 changes: 1 addition & 1 deletion core/pom.xml
Original file line number Diff line number Diff line change
@@ -12,7 +12,7 @@ DO NOT MODIFIY - GENERATED CODE
<parent>
<groupId>org.jruby</groupId>
<artifactId>jruby-parent</artifactId>
<version>9.1.1.0-SNAPSHOT</version>
<version>9.1.2.0-SNAPSHOT</version>
</parent>
<artifactId>jruby-core</artifactId>
<name>JRuby Core</name>
65 changes: 64 additions & 1 deletion core/src/main/java/org/jruby/Ruby.java
Original file line number Diff line number Diff line change
@@ -4437,6 +4437,69 @@ private IRubyObject execRecursiveInternal(RecursiveFunction func, IRubyObject ob
}
}

ThreadLocal<Map<String, Map<IRubyObject, IRubyObject>>> symMap = new ThreadLocal<>();

public IRubyObject safeRecurse(RecursiveFunction func, IRubyObject obj, String name, boolean outer) {
Map<IRubyObject, IRubyObject> guards = safeRecurseGetGuards(name);

boolean outermost = outer && !guards.containsKey(recursiveKey);

// check guards
if (guards.containsKey(obj)) {
if (outer && !outermost) {
throw new RecursiveError(guards);
}
return func.call(obj, true);
} else {
if (outermost) {
return safeRecurseOutermost(func, obj, guards);
} else {
return safeRecurseInner(func, obj, guards);
}
}
}

private IRubyObject safeRecurseOutermost(RecursiveFunction func, IRubyObject obj, Map<IRubyObject, IRubyObject> guards) {
boolean recursed = false;
guards.put(recursiveKey, recursiveKey);

try {
return safeRecurseInner(func, obj, guards);
} catch (RecursiveError re) {
if (re.tag != guards) {
throw re;
}
recursed = true;
guards.remove(recursiveKey);
return func.call(obj, true);
} finally {
if (!recursed) guards.remove(recursiveKey);
}
}

private Map<IRubyObject, IRubyObject> safeRecurseGetGuards(String name) {
Map<String, Map<IRubyObject, IRubyObject>> symToGuards = symMap.get();
if (symToGuards == null) {
symToGuards = new HashMap<>();
symMap.set(symToGuards);
}

Map<IRubyObject, IRubyObject> guards = symToGuards.get(name);
if (guards == null) {
guards = new IdentityHashMap<>();
symToGuards.put(name, guards);
} return guards;
}

private IRubyObject safeRecurseInner(RecursiveFunction func, IRubyObject obj, Map<IRubyObject, IRubyObject> guards) {
try {
guards.put(obj, obj);
return func.call(obj, false);
} finally {
guards.remove(obj);
}
}

/**
* Perform a recursive walk on the given object using the given function.
*
@@ -4846,7 +4909,7 @@ public void setFFI(FFI ffi) {
}

public RubyString getDefinedMessage(DefinedMessage definedMessage) {
return definedMessages.get(definedMessage);
return freezeAndDedupString(definedMessages.get(definedMessage));
}

public RubyString getThreadStatus(RubyThread.Status status) {
55 changes: 25 additions & 30 deletions core/src/main/java/org/jruby/RubyArray.java
Original file line number Diff line number Diff line change
@@ -76,9 +76,10 @@

import static org.jruby.RubyEnumerator.enumeratorize;
import static org.jruby.RubyEnumerator.enumeratorizeWithSize;
import static org.jruby.runtime.Helpers.hashEnd;
import static org.jruby.runtime.Helpers.invokedynamic;
import static org.jruby.runtime.Helpers.murmurCombine;
import static org.jruby.runtime.Visibility.PRIVATE;
import static org.jruby.runtime.invokedynamic.MethodNames.HASH;
import static org.jruby.runtime.invokedynamic.MethodNames.OP_CMP;
import static org.jruby.RubyEnumerator.SizeFn;

@@ -676,25 +677,23 @@ public RubyFixnum hash19(ThreadContext context) {
*
*/
@JRubyMethod(name = "hash")
public RubyFixnum hash(final ThreadContext context) {
return (RubyFixnum) context.runtime.execRecursiveOuter(new Ruby.RecursiveFunction() {
public IRubyObject call(IRubyObject obj, boolean recur) {
final Ruby runtime = context.runtime;
int begin = RubyArray.this.begin;
long h = realLength;
h ^= System.identityHashCode(RubyArray.class);
if (recur) {
h ^= h * 31 + RubyNumeric.num2long(invokedynamic(context, runtime.getArray(), HASH));
} else {
for (int i = begin; i < begin + realLength; i++) {
h = (h << 1) | (h < 0 ? 1 : 0);
final IRubyObject value = safeArrayRef(runtime, values, i);
h ^= h * 31 + RubyNumeric.num2long(invokedynamic(context, value, HASH));
}
}
return runtime.newFixnum(h);
}
}, RubyArray.this);
public RubyFixnum hash(ThreadContext context) {
Ruby runtime = context.runtime;

int begin = RubyArray.this.begin;
long h = Helpers.hashStart(runtime, realLength);

h = Helpers.murmurCombine(h, System.identityHashCode(RubyArray.class));

for (int i = begin; i < begin + realLength; i++) {
IRubyObject value = safeArrayRef(runtime, values, i);
RubyFixnum n = Helpers.safeHash(context, value);
h = murmurCombine(h, n.getLongValue());
}

h = hashEnd(h);

return runtime.newFixnum(h);
}

/** rb_ary_store
@@ -1765,15 +1764,15 @@ private void recursiveJoin(final ThreadContext context, final IRubyObject outVal

if (ary == this) throw runtime.newArgumentError("recursive array join");

runtime.execRecursive(new Ruby.RecursiveFunction() {
runtime.safeRecurse(new Ruby.RecursiveFunction() {
public IRubyObject call(IRubyObject obj, boolean recur) {
if (recur) throw runtime.newArgumentError("recursive array join");

RubyArray recAry = ((RubyArray) ary);
recAry.joinAny(context, outValue, sep, recAry.begin, result);

return runtime.getNil();
}}, outValue);
}}, outValue, "join", true);
}

/** rb_ary_join
@@ -1799,15 +1798,11 @@ public IRubyObject join19(final ThreadContext context, IRubyObject sep) {
IRubyObject tmp = val.checkStringType19();
if (tmp.isNil() || tmp != val) {
len += ((begin + realLength) - i) * 10;
final RubyString result = (RubyString) RubyString.newStringLight(runtime, len, USASCIIEncoding.INSTANCE).infectBy(this);
final RubyString sepStringFinal = sepString;
final int iFinal = i;
RubyString result = (RubyString) RubyString.newStringLight(runtime, len, USASCIIEncoding.INSTANCE).infectBy(this);
RubyString sepStringFinal = sepString;
int iFinal = i;

return runtime.recursiveListOperation(new Callable<IRubyObject>() {
public IRubyObject call() {
return joinAny(context, RubyArray.this, sepStringFinal, iFinal, joinStrings(sepStringFinal, iFinal, result));
}
});
return joinAny(context, RubyArray.this, sepStringFinal, iFinal, joinStrings(sepStringFinal, iFinal, result));
}

len += ((RubyString) tmp).getByteList().length();
26 changes: 10 additions & 16 deletions core/src/main/java/org/jruby/RubyHash.java
Original file line number Diff line number Diff line change
@@ -1241,24 +1241,18 @@ public IRubyObject op_ge(ThreadContext context, IRubyObject other) {
@JRubyMethod(name = "hash")
public RubyFixnum hash() {
final Ruby runtime = getRuntime();
if (size == 0) return RubyFixnum.zero(runtime);
final ThreadContext context = runtime.getCurrentContext();
return (RubyFixnum) runtime.execRecursiveOuter(new Ruby.RecursiveFunction() {
@Override
public IRubyObject call(IRubyObject obj, boolean recur) {
if (recur) {
return invokedynamic(context, runtime.getHash(), HASH).convertToInteger();
final long[] hval = {Helpers.hashStart(runtime, size())};
if (size > 0) {
iteratorVisitAll(new Visitor() {
@Override
public void visit(IRubyObject key, IRubyObject value) {
hval[0] += Helpers.safeHash(context, key).convertToInteger().getLongValue()
^ Helpers.safeHash(context, value).convertToInteger().getLongValue();
}
final long[] h = new long[]{1};
visitAll(new Visitor() {
@Override
public void visit(IRubyObject key, IRubyObject value) {
h[0] += invokedynamic(context, key, HASH).convertToInteger().getLongValue() ^ invokedynamic(context, value, HASH).convertToInteger().getLongValue();
}
});
return runtime.newFixnum(h[0]);
}
}, this);
});
}
return runtime.newFixnum(hval[0]);
}

@Deprecated
4 changes: 4 additions & 0 deletions core/src/main/java/org/jruby/RubyModule.java
Original file line number Diff line number Diff line change
@@ -3663,6 +3663,10 @@ public IRubyObject getConstantNoConstMissing(String name, boolean inherit) {
return getConstantNoConstMissing(name, inherit, true);
}

public IRubyObject getConstantNoConstMissingSKipAutoload(String name) {
return getConstantSkipAutoload(name, true, true);
}

public IRubyObject getConstantNoConstMissing(String name, boolean inherit, boolean includeObject) {
IRubyObject constant = iterateConstantNoConstMissing(name, this, inherit, true);

12 changes: 4 additions & 8 deletions core/src/main/java/org/jruby/RubyStruct.java
Original file line number Diff line number Diff line change
@@ -586,15 +586,11 @@ public RubyString inspect(final ThreadContext context) {
final Ruby runtime = context.runtime;
final RubyStruct struct = this;
// recursion guard
return runtime.recursiveListOperation(new Callable<RubyString>() {
public RubyString call() {
return (RubyString) runtime.execRecursive(new Ruby.RecursiveFunction() {
public IRubyObject call(IRubyObject obj, boolean recur) {
return inspectStruct(context, recur);
}
}, struct);
return (RubyString) runtime.safeRecurse(new Ruby.RecursiveFunction() {
public IRubyObject call(IRubyObject obj, boolean recur) {
return inspectStruct(context, recur);
}
});
}, struct, "inspect", false);
}

@JRubyMethod(name = {"to_a", "values"})
Original file line number Diff line number Diff line change
@@ -76,7 +76,7 @@ public InterpreterContext ensureInstrsReady() {
if (Options.IR_PRINT.load()) {
ByteArrayOutputStream baos = IRDumper.printIR(method, false, true);

LOG.info("Printing simple IR for " + method.getName(), "\n" + new String(baos.toByteArray()));
LOG.info("Printing simple IR for " + method.getName() + ":\n" + new String(baos.toByteArray()));
}
}

Original file line number Diff line number Diff line change
@@ -75,7 +75,7 @@ public InterpreterContext ensureInstrsReady() {
if (Options.IR_PRINT.load()) {
ByteArrayOutputStream baos = IRDumper.printIR(method, false);

LOG.info("Printing simple IR for " + method.getName(), "\n" + new String(baos.toByteArray()));
LOG.info("Printing simple IR for " + method.getName() + ":\n" + new String(baos.toByteArray()));
}

return ic;
6 changes: 3 additions & 3 deletions core/src/main/java/org/jruby/ir/IRBuilder.java
Original file line number Diff line number Diff line change
@@ -1403,7 +1403,7 @@ private Operand protectCodeWithRescue(CodeBlock protectedCode, CodeBlock rescueB
// Receive 'exc' and verify that 'exc' is of ruby-type 'Exception'
addInstr(new LabelInstr(rescueLabel));
addInstr(new ReceiveRubyExceptionInstr(exc));
addInstr(new InheritanceSearchConstInstr(excType, new ObjectClass(), "Exception", false));
addInstr(new InheritanceSearchConstInstr(excType, new ObjectClass(), "Exception"));
outputExceptionCheck(excType, exc, caughtLabel);

// Fall-through when the exc !== Exception; rethrow 'exc'
@@ -1525,7 +1525,7 @@ public Operand run() {
String constName = ((ConstNode) node).getName();
addInstr(new LexicalSearchConstInstr(tmpVar, startingSearchScope(), constName));
addInstr(BNEInstr.create(defLabel, tmpVar, UndefinedValue.UNDEFINED));
addInstr(new InheritanceSearchConstInstr(tmpVar, findContainerModule(), constName, false)); // SSS FIXME: should this be the current-module var or something else?
addInstr(new InheritanceSearchConstInstr(tmpVar, findContainerModule(), constName)); // SSS FIXME: should this be the current-module var or something else?
addInstr(BNEInstr.create(defLabel, tmpVar, UndefinedValue.UNDEFINED));
addInstr(new CopyInstr(tmpVar, manager.getNil()));
addInstr(new JumpInstr(doneLabel));
@@ -2471,7 +2471,7 @@ public Operand buildFlip(FlipNode flipNode) {
// for JIT/AOT. Also it means needing to grow the size of any heap scope for variables.
if (nearestNonClosureBuilder == null) {
Variable excType = createTemporaryVariable();
addInstr(new InheritanceSearchConstInstr(excType, new ObjectClass(), "NotImplementedError", false));
addInstr(new InheritanceSearchConstInstr(excType, new ObjectClass(), "NotImplementedError"));
Variable exc = addResultInstr(CallInstr.create(scope, createTemporaryVariable(), "new", excType, new Operand[] {new FrozenString("Flip support currently broken")}, null));
addInstr(new ThrowExceptionInstr(exc));
return buildNil();
19 changes: 12 additions & 7 deletions core/src/main/java/org/jruby/ir/IRScope.java
Original file line number Diff line number Diff line change
@@ -662,14 +662,19 @@ private void calculateClosureScopeFlags() {
}
}

private static final EnumSet<IRFlags> NEEDS_DYNAMIC_SCOPE_FLAGS =
EnumSet.of(
CAN_RECEIVE_BREAKS,
HAS_NONLOCAL_RETURNS,CAN_RECEIVE_NONLOCAL_RETURNS,
BINDING_HAS_ESCAPED,
USES_ZSUPER);

private void computeNeedsDynamicScopeFlag() {
// SSS FIXME: checkArity for keyword args looks up a keyword arg in the static scope which
// currently requires a dynamic scope to be recovered. If there is another way to do this,
// we can get rid of this.
if (flags.contains(CAN_RECEIVE_BREAKS) || flags.contains(HAS_NONLOCAL_RETURNS) ||
flags.contains(CAN_RECEIVE_NONLOCAL_RETURNS) || flags.contains(BINDING_HAS_ESCAPED) ||
flags.contains(USES_ZSUPER) || flags.contains(RECEIVES_KEYWORD_ARGS)) {
flags.add(REQUIRES_DYNSCOPE);
for (IRFlags f : NEEDS_DYNAMIC_SCOPE_FLAGS) {
if (flags.contains(f)) {
flags.add(REQUIRES_DYNSCOPE);
return;
}
}
}

Original file line number Diff line number Diff line change
@@ -66,7 +66,7 @@ public static CheckArityInstr decode(IRReaderDecoder d) {
}

public void checkArity(ThreadContext context, Object[] args, Block.Type blockType) {
IRRuntimeHelpers.checkArity(context, args, required, opt, rest, receivesKeywords, restKey, blockType);
IRRuntimeHelpers.checkArity(context.runtime, context.getCurrentStaticScope(), args, required, opt, rest, receivesKeywords, restKey, blockType);
}

@Override
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
package org.jruby.ir.instructions;

import org.jruby.ir.IRFlags;
import org.jruby.ir.IRScope;
import org.jruby.ir.IRVisitor;
import org.jruby.ir.Operation;
import org.jruby.ir.persistence.IRReaderDecoder;
@@ -50,4 +52,11 @@ public String[] toStringNonOperandArgs() {
public void check(ThreadContext context, DynamicScope dynamicScope, Block.Type blockType) {
IRRuntimeHelpers.checkForLJE(context, dynamicScope, maybeLambda, blockType);
}

@Override
public boolean computeScopeFlags(IRScope scope) {
super.computeScopeFlags(scope);
scope.getFlags().add(IRFlags.REQUIRES_DYNSCOPE);
return true;
}
}
20 changes: 19 additions & 1 deletion core/src/main/java/org/jruby/ir/instructions/GetFieldInstr.java
Original file line number Diff line number Diff line change
@@ -1,17 +1,21 @@
package org.jruby.ir.instructions;

import org.jruby.RubyClass;
import org.jruby.common.IRubyWarnings;
import org.jruby.ir.IRVisitor;
import org.jruby.ir.Operation;
import org.jruby.ir.operands.Operand;
import org.jruby.ir.operands.Variable;
import org.jruby.ir.persistence.IRReaderDecoder;
import org.jruby.ir.transformations.inlining.CloneInfo;
import org.jruby.parser.StaticScope;
import org.jruby.runtime.DynamicScope;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.builtin.IRubyObject;
import org.jruby.runtime.ivars.VariableAccessor;

public class GetFieldInstr extends GetInstr implements FixedArityInstr {
private VariableAccessor accessor = VariableAccessor.DUMMY_ACCESSOR;
private transient VariableAccessor accessor = VariableAccessor.DUMMY_ACCESSOR;

public GetFieldInstr(Variable dest, Operand obj, String fieldName) {
super(Operation.GET_FIELD, dest, obj, fieldName);
@@ -38,6 +42,20 @@ public VariableAccessor getAccessor(IRubyObject o) {
return localAccessor;
}

@Override
public Object interpret(ThreadContext context, StaticScope currScope, DynamicScope currDynScope, IRubyObject self, Object[] temp) {
IRubyObject object = (IRubyObject) getSource().retrieve(context, self, currScope, currDynScope, temp);
VariableAccessor a = getAccessor(object);
Object result = a == null ? null : (IRubyObject)a.get(object);
if (result == null) {
if (context.runtime.isVerbose()) {
context.runtime.getWarnings().warning(IRubyWarnings.ID.IVAR_NOT_INITIALIZED, "instance variable " + getRef() + " not initialized");
}
result = context.nil;
}
return result;
}

@Override
public void visit(IRVisitor visitor) {
visitor.GetFieldInstr(this);
Original file line number Diff line number Diff line change
@@ -22,18 +22,21 @@

public class InheritanceSearchConstInstr extends OneOperandResultBaseInstr implements FixedArityInstr {
String constName;
private final boolean noPrivateConsts;

// Constant caching
private volatile transient ConstantCache cache;

public InheritanceSearchConstInstr(Variable result, Operand currentModule, String constName, boolean noPrivateConsts) {
public InheritanceSearchConstInstr(Variable result, Operand currentModule, String constName) {
super(Operation.INHERITANCE_SEARCH_CONST, result, currentModule);

assert result != null: "InheritanceSearchConstInstr result is null";

this.constName = constName;
this.noPrivateConsts = noPrivateConsts;
}

@Deprecated
public InheritanceSearchConstInstr(Variable result, Operand currentModule, String constName, boolean unused) {
this(result, currentModule, constName);
}

public Operand getCurrentModule() {
@@ -44,23 +47,23 @@ public String getConstName() {
return constName;
}

@Deprecated
public boolean isNoPrivateConsts() {
return noPrivateConsts;
return false;
}

@Override
public Instr clone(CloneInfo ii) {
return new InheritanceSearchConstInstr(ii.getRenamedVariable(result),
getCurrentModule().cloneForInlining(ii), constName, noPrivateConsts);
return new InheritanceSearchConstInstr(ii.getRenamedVariable(result), getCurrentModule().cloneForInlining(ii), constName);
}

@Override
public String[] toStringNonOperandArgs() {
return new String[] { "name: " + constName, "no_priv: " + noPrivateConsts};
return new String[] { "name: " + constName };
}

private Object cache(Ruby runtime, RubyModule module) {
Object constant = noPrivateConsts ? module.getConstantFromNoConstMissing(constName, false) : module.getConstantNoConstMissing(constName);
Object constant = module.getConstantNoConstMissingSKipAutoload(constName);
if (constant == null) {
constant = UndefinedValue.UNDEFINED;
} else {
@@ -76,11 +79,10 @@ public void encode(IRWriterEncoder e) {
super.encode(e);
e.encode(getCurrentModule());
e.encode(getConstName());
e.encode(isNoPrivateConsts());
}

public static InheritanceSearchConstInstr decode(IRReaderDecoder d) {
return new InheritanceSearchConstInstr(d.decodeVariable(), d.decodeOperand(), d.decodeString(), d.decodeBoolean());
return new InheritanceSearchConstInstr(d.decodeVariable(), d.decodeOperand(), d.decodeString());
}

@Override
Original file line number Diff line number Diff line change
@@ -66,7 +66,7 @@ public static LexicalSearchConstInstr decode(IRReaderDecoder d) {
private Object cache(ThreadContext context, StaticScope currScope, DynamicScope currDynScope, IRubyObject self, Object[] temp) {
StaticScope staticScope = (StaticScope) getDefiningScope().retrieve(context, self, currScope, currDynScope, temp);

IRubyObject constant = staticScope.getConstantInner(constName);
IRubyObject constant = staticScope.getConstantDefined(constName);

if (constant == null) {
constant = UndefinedValue.UNDEFINED;
23 changes: 17 additions & 6 deletions core/src/main/java/org/jruby/ir/instructions/PutFieldInstr.java
Original file line number Diff line number Diff line change
@@ -10,8 +10,11 @@
import org.jruby.runtime.DynamicScope;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.builtin.IRubyObject;
import org.jruby.runtime.ivars.VariableAccessor;

public class PutFieldInstr extends PutInstr implements FixedArityInstr {
private transient VariableAccessor accessor = VariableAccessor.DUMMY_ACCESSOR;

public PutFieldInstr(Operand obj, String fieldName, Operand value) {
super(Operation.PUT_FIELD, obj, fieldName, value);
}
@@ -21,17 +24,25 @@ public Instr clone(CloneInfo ii) {
return new PutFieldInstr(getTarget().cloneForInlining(ii), ref, getValue().cloneForInlining(ii));
}

public VariableAccessor getAccessor(IRubyObject o) {
RubyClass cls = o.getMetaClass().getRealClass();
VariableAccessor localAccessor = accessor;

if (localAccessor.getClassId() != cls.hashCode()) {
localAccessor = cls.getVariableAccessorForWrite(getRef());
accessor = localAccessor;
}
return localAccessor;
}

@Override
public Object interpret(ThreadContext context, StaticScope currScope, DynamicScope currDynScope, IRubyObject self, Object[] temp) {
IRubyObject object = (IRubyObject) getTarget().retrieve(context, self, currScope, currDynScope, temp);

// We store instance variable offsets on the real class, since instance var tables are associated with the
// natural type of an object.
RubyClass clazz = object.getMetaClass().getRealClass();
VariableAccessor a = getAccessor(object);
Object value = getValue().retrieve(context, self, currScope, currDynScope, temp);
a.set(object, value);

// FIXME: Should add this as a field for instruction
clazz.getVariableAccessorForWrite(getRef()).set(object,
getValue().retrieve(context, self, currScope, currDynScope, temp));
return null;
}

Original file line number Diff line number Diff line change
@@ -65,7 +65,7 @@ protected IRubyObject execute(Ruby runtime, IRScriptBody irScope, IRubyObject se
if (Options.IR_PRINT.load()) {
ByteArrayOutputStream baos = IRDumper.printIR(irScope, false);

LOG.info("Printing simple IR for " + irScope.getName(), "\n" + new String(baos.toByteArray()));
LOG.info("Printing simple IR for " + irScope.getName() + ":\n" + new String(baos.toByteArray()));
}

ThreadContext context = runtime.getCurrentContext();
18 changes: 0 additions & 18 deletions core/src/main/java/org/jruby/ir/interpreter/InterpreterEngine.java
Original file line number Diff line number Diff line change
@@ -4,14 +4,12 @@
import org.jruby.RubyFixnum;
import org.jruby.RubyFloat;
import org.jruby.RubyModule;
import org.jruby.common.IRubyWarnings;
import org.jruby.exceptions.Unrescuable;
import org.jruby.ir.Operation;
import org.jruby.ir.instructions.BreakInstr;
import org.jruby.ir.instructions.CheckArityInstr;
import org.jruby.ir.instructions.CheckForLJEInstr;
import org.jruby.ir.instructions.CopyInstr;
import org.jruby.ir.instructions.GetFieldInstr;
import org.jruby.ir.instructions.Instr;
import org.jruby.ir.instructions.JumpInstr;
import org.jruby.ir.instructions.LineNumberInstr;
@@ -65,7 +63,6 @@
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.Visibility;
import org.jruby.runtime.builtin.IRubyObject;
import org.jruby.runtime.ivars.VariableAccessor;
import org.jruby.runtime.opto.ConstantCache;

/**
@@ -463,21 +460,6 @@ protected static void processOtherOp(ThreadContext context, Block block, Instr i
break;
}

case GET_FIELD: {
GetFieldInstr gfi = (GetFieldInstr)instr;
IRubyObject object = (IRubyObject)gfi.getSource().retrieve(context, self, currScope, currDynScope, temp);
VariableAccessor a = gfi.getAccessor(object);
result = a == null ? null : (IRubyObject)a.get(object);
if (result == null) {
if (context.runtime.isVerbose()) {
context.runtime.getWarnings().warning(IRubyWarnings.ID.IVAR_NOT_INITIALIZED, "instance variable " + gfi.getRef() + " not initialized");
}
result = context.nil;
}
setResult(temp, currDynScope, gfi.getResult(), result);
break;
}

case SEARCH_CONST: {
SearchConstInstr sci = (SearchConstInstr)instr;
ConstantCache cache = sci.getConstantCache();
Original file line number Diff line number Diff line change
@@ -2,17 +2,13 @@

import java.util.HashMap;
import java.util.Map;
import org.jruby.RubyClass;
import org.jruby.RubyModule;
import org.jruby.common.IRubyWarnings;
import org.jruby.ir.OpClass;
import org.jruby.ir.Operation;
import org.jruby.ir.instructions.CopyInstr;
import org.jruby.ir.instructions.GetFieldInstr;
import org.jruby.ir.instructions.Instr;
import org.jruby.ir.instructions.JumpInstr;
import org.jruby.ir.instructions.LineNumberInstr;
import org.jruby.ir.instructions.PutFieldInstr;
import org.jruby.ir.instructions.ReceivePreReqdArgInstr;
import org.jruby.ir.instructions.ResultInstr;
import org.jruby.ir.instructions.ReturnBase;
@@ -29,7 +25,6 @@
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.Visibility;
import org.jruby.runtime.builtin.IRubyObject;
import org.jruby.runtime.ivars.VariableAccessor;
import org.jruby.runtime.opto.ConstantCache;

/**
@@ -211,33 +206,6 @@ public IRubyObject interpret(ThreadContext context, Block block, IRubyObject sel
rhc.callHelper(context, currScope, currDynScope, self, temp, blockType));
break;
}
case GET_FIELD: { // NO INTERP
GetFieldInstr gfi = (GetFieldInstr)instr;
IRubyObject object = (IRubyObject)gfi.getSource().retrieve(context, self, currScope, currDynScope, temp);
VariableAccessor a = gfi.getAccessor(object);
Object result = a == null ? null : (IRubyObject)a.get(object);
if (result == null) {
if (context.runtime.isVerbose()) {
context.runtime.getWarnings().warning(IRubyWarnings.ID.IVAR_NOT_INITIALIZED, "instance variable " + gfi.getRef() + " not initialized");
}
result = context.nil;
}
setResult(temp, currDynScope, gfi.getResult(), result);
break;
}
case PUT_FIELD: {
PutFieldInstr putField = (PutFieldInstr) instr;
IRubyObject object = (IRubyObject) putField.getTarget().retrieve(context, self, currScope, currDynScope, temp);

// We store instance variable offsets on the real class, since instance var tables are associated with the
// natural type of an object.
RubyClass clazz = object.getMetaClass().getRealClass();

// FIXME: Should add this as a field for instruction
clazz.getVariableAccessorForWrite(putField.getRef()).set(object,
putField.getValue().retrieve(context, self, currScope, currDynScope, temp));
break;
}

case BUILD_COMPOUND_STRING: case CONST_MISSING:
default:
@@ -413,33 +381,6 @@ public IRubyObject interpret(ThreadContext context, Block block, IRubyObject sel
rhc.callHelper(context, currScope, currDynScope, self, temp, blockType));
break;
}
case GET_FIELD: { // NO INTERP
GetFieldInstr gfi = (GetFieldInstr)instr;
IRubyObject object = (IRubyObject)gfi.getSource().retrieve(context, self, currScope, currDynScope, temp);
VariableAccessor a = gfi.getAccessor(object);
Object result = a == null ? null : (IRubyObject)a.get(object);
if (result == null) {
if (context.runtime.isVerbose()) {
context.runtime.getWarnings().warning(IRubyWarnings.ID.IVAR_NOT_INITIALIZED, "instance variable " + gfi.getRef() + " not initialized");
}
result = context.nil;
}
setResult(temp, currDynScope, gfi.getResult(), result);
break;
}
case PUT_FIELD: {
PutFieldInstr putField = (PutFieldInstr) instr;
IRubyObject object = (IRubyObject) putField.getTarget().retrieve(context, self, currScope, currDynScope, temp);

// We store instance variable offsets on the real class, since instance var tables are associated with the
// natural type of an object.
RubyClass clazz = object.getMetaClass().getRealClass();

// FIXME: Should add this as a field for instruction
clazz.getVariableAccessorForWrite(putField.getRef()).set(object,
putField.getValue().retrieve(context, self, currScope, currDynScope, temp));
break;
}

case BUILD_COMPOUND_STRING: case CONST_MISSING:
default:
@@ -616,33 +557,6 @@ public IRubyObject interpret(ThreadContext context, Block block, IRubyObject sel
rhc.callHelper(context, currScope, currDynScope, self, temp, blockType));
break;
}
case GET_FIELD: { // NO INTERP
GetFieldInstr gfi = (GetFieldInstr)instr;
IRubyObject object = (IRubyObject)gfi.getSource().retrieve(context, self, currScope, currDynScope, temp);
VariableAccessor a = gfi.getAccessor(object);
Object result = a == null ? null : (IRubyObject)a.get(object);
if (result == null) {
if (context.runtime.isVerbose()) {
context.runtime.getWarnings().warning(IRubyWarnings.ID.IVAR_NOT_INITIALIZED, "instance variable " + gfi.getRef() + " not initialized");
}
result = context.nil;
}
setResult(temp, currDynScope, gfi.getResult(), result);
break;
}
case PUT_FIELD: {
PutFieldInstr putField = (PutFieldInstr) instr;
IRubyObject object = (IRubyObject) putField.getTarget().retrieve(context, self, currScope, currDynScope, temp);

// We store instance variable offsets on the real class, since instance var tables are associated with the
// natural type of an object.
RubyClass clazz = object.getMetaClass().getRealClass();

// FIXME: Should add this as a field for instruction
clazz.getVariableAccessorForWrite(putField.getRef()).set(object,
putField.getValue().retrieve(context, self, currScope, currDynScope, temp));
break;
}

case BUILD_COMPOUND_STRING: case CONST_MISSING:
default:
@@ -820,33 +734,6 @@ public IRubyObject interpret(ThreadContext context, Block block, IRubyObject sel
rhc.callHelper(context, currScope, currDynScope, self, temp, blockType));
break;
}
case GET_FIELD: { // NO INTERP
GetFieldInstr gfi = (GetFieldInstr)instr;
IRubyObject object = (IRubyObject)gfi.getSource().retrieve(context, self, currScope, currDynScope, temp);
VariableAccessor a = gfi.getAccessor(object);
Object result = a == null ? null : (IRubyObject)a.get(object);
if (result == null) {
if (context.runtime.isVerbose()) {
context.runtime.getWarnings().warning(IRubyWarnings.ID.IVAR_NOT_INITIALIZED, "instance variable " + gfi.getRef() + " not initialized");
}
result = context.nil;
}
setResult(temp, currDynScope, gfi.getResult(), result);
break;
}
case PUT_FIELD: {
PutFieldInstr putField = (PutFieldInstr) instr;
IRubyObject object = (IRubyObject) putField.getTarget().retrieve(context, self, currScope, currDynScope, temp);

// We store instance variable offsets on the real class, since instance var tables are associated with the
// natural type of an object.
RubyClass clazz = object.getMetaClass().getRealClass();

// FIXME: Should add this as a field for instruction
clazz.getVariableAccessorForWrite(putField.getRef()).set(object,
putField.getValue().retrieve(context, self, currScope, currDynScope, temp));
break;
}

case BUILD_COMPOUND_STRING: case CONST_MISSING:
default:
@@ -1016,33 +903,6 @@ public IRubyObject interpret(ThreadContext context, Block block, IRubyObject sel
rhc.callHelper(context, currScope, currDynScope, self, temp, blockType));
break;
}
case GET_FIELD: { // NO INTERP
GetFieldInstr gfi = (GetFieldInstr)instr;
IRubyObject object = (IRubyObject)gfi.getSource().retrieve(context, self, currScope, currDynScope, temp);
VariableAccessor a = gfi.getAccessor(object);
Object result = a == null ? null : (IRubyObject)a.get(object);
if (result == null) {
if (context.runtime.isVerbose()) {
context.runtime.getWarnings().warning(IRubyWarnings.ID.IVAR_NOT_INITIALIZED, "instance variable " + gfi.getRef() + " not initialized");
}
result = context.nil;
}
setResult(temp, currDynScope, gfi.getResult(), result);
break;
}
case PUT_FIELD: {
PutFieldInstr putField = (PutFieldInstr) instr;
IRubyObject object = (IRubyObject) putField.getTarget().retrieve(context, self, currScope, currDynScope, temp);

// We store instance variable offsets on the real class, since instance var tables are associated with the
// natural type of an object.
RubyClass clazz = object.getMetaClass().getRealClass();

// FIXME: Should add this as a field for instruction
clazz.getVariableAccessorForWrite(putField.getRef()).set(object,
putField.getValue().retrieve(context, self, currScope, currDynScope, temp));
break;
}

case BUILD_COMPOUND_STRING: case CONST_MISSING:
default:
14 changes: 6 additions & 8 deletions core/src/main/java/org/jruby/ir/runtime/IRRuntimeHelpers.java
Original file line number Diff line number Diff line change
@@ -535,12 +535,12 @@ public static Block getBlockFromObject(ThreadContext context, Object value) {
return block;
}

public static void checkArity(ThreadContext context, Object[] args, int required, int opt, boolean rest,
public static void checkArity(Ruby runtime, StaticScope scope, Object[] args, int required, int opt, boolean rest,
boolean receivesKwargs, int restKey, Block.Type blockType) {
int argsLength = args.length;
RubyHash keywordArgs = extractKwargsHash(args, required, receivesKwargs);

if (restKey == -1 && keywordArgs != null) checkForExtraUnwantedKeywordArgs(context, keywordArgs);
if (restKey == -1 && keywordArgs != null) checkForExtraUnwantedKeywordArgs(runtime, scope, keywordArgs);

// keyword arguments value is not used for arity checking.
if (keywordArgs != null) argsLength -= 1;
@@ -549,7 +549,7 @@ public static void checkArity(ThreadContext context, Object[] args, int required
// System.out.println("NUMARGS: " + argsLength + ", REQUIRED: " + required + ", OPT: " + opt + ", AL: " + args.length + ",RKW: " + receivesKwargs );
// System.out.println("ARGS[0]: " + args[0]);

Arity.raiseArgumentError(context.runtime, argsLength, required, required + opt);
Arity.raiseArgumentError(runtime, argsLength, required, required + opt);
}
}

@@ -588,19 +588,17 @@ public static RubyHash extractKwargsHash(Object[] args, int requiredArgsCount, b
return null;
}

public static void checkForExtraUnwantedKeywordArgs(final ThreadContext context, RubyHash keywordArgs) {
final StaticScope scope = context.getCurrentStaticScope();

public static void checkForExtraUnwantedKeywordArgs(final Ruby runtime, final StaticScope scope, RubyHash keywordArgs) {
keywordArgs.visitAll(new RubyHash.Visitor() {
@Override
public void visit(IRubyObject key, IRubyObject value) {
String keyAsString = key.asJavaString();
int slot = scope.isDefined((keyAsString));

// Found name in higher variable scope. Therefore non for this block/method def.
if ((slot >> 16) > 0) throw context.runtime.newArgumentError("unknown keyword: " + keyAsString);
if ((slot >> 16) > 0) throw runtime.newArgumentError("unknown keyword: " + keyAsString);
// Could not find it anywhere.
if (((short) (slot & 0xffff)) < 0) throw context.runtime.newArgumentError("unknown keyword: " + keyAsString);
if (((short) (slot & 0xffff)) < 0) throw runtime.newArgumentError("unknown keyword: " + keyAsString);
}
});
}
Original file line number Diff line number Diff line change
@@ -150,7 +150,7 @@ public IRubyObject inheritanceSearchConst(ThreadContext context, IRubyObject cmV
throw runtime.newTypeError(cmVal + " is not a type/class");
}

IRubyObject constant = publicOnly ? module.getConstantFromNoConstMissing(name, false) : module.getConstantNoConstMissing(name);
IRubyObject constant = module.getConstantNoConstMissingSKipAutoload(name);

if (constant == null) {
constant = UndefinedValue.UNDEFINED;
@@ -190,7 +190,7 @@ public IRubyObject inheritanceSearchConst(ThreadContext context, IRubyObject cmV
public IRubyObject lexicalSearchConst(ThreadContext context, StaticScope scope) {
Ruby runtime = context.runtime;

IRubyObject constant = scope.getConstantInner(name);
IRubyObject constant = scope.getConstantDefined(name);

if (constant == null) {
constant = UndefinedValue.UNDEFINED;
9 changes: 5 additions & 4 deletions core/src/main/java/org/jruby/ir/targets/JVMVisitor.java
Original file line number Diff line number Diff line change
@@ -130,7 +130,7 @@ public void emitScope(IRScope scope, String name, Signature signature, boolean s
if (print && Options.IR_PRINT.load()) {
ByteArrayOutputStream baos = IRDumper.printIR(scope, true);

LOG.info("Printing JIT IR for " + scope.getName(), "\n" + new String(baos.toByteArray()));
LOG.info("Printing JIT IR for " + scope.getName() + ":\n" + new String(baos.toByteArray()));
}

Map<BasicBlock, Label> exceptionTable = scope.buildJVMExceptionTable();
@@ -968,15 +968,16 @@ public void CheckArityInstr(CheckArityInstr checkarityinstr) {
if (jvm.methodData().specificArity >= 0) {
// no arity check in specific arity path
} else {
jvmMethod().loadContext();
jvmMethod().loadRuntime();
jvmMethod().loadStaticScope();
jvmMethod().loadArgs();
jvmAdapter().ldc(checkarityinstr.required);
jvmAdapter().ldc(checkarityinstr.opt);
jvmAdapter().ldc(checkarityinstr.rest);
jvmAdapter().ldc(checkarityinstr.receivesKeywords);
jvmAdapter().ldc(checkarityinstr.restKey);
jvmMethod().loadBlockType();
jvmAdapter().invokestatic(p(IRRuntimeHelpers.class), "checkArity", sig(void.class, ThreadContext.class, Object[].class, int.class, int.class, boolean.class, boolean.class, int.class, Block.Type.class));
jvmAdapter().invokestatic(p(IRRuntimeHelpers.class), "checkArity", sig(void.class, Ruby.class, StaticScope.class, Object[].class, int.class, int.class, boolean.class, boolean.class, int.class, Block.Type.class));
}
}

@@ -1220,7 +1221,7 @@ public void InheritanceSearchConstInstr(InheritanceSearchConstInstr inheritances
jvmMethod().loadContext();
visit(inheritancesearchconstinstr.getCurrentModule());

jvmMethod().inheritanceSearchConst(inheritancesearchconstinstr.getConstName(), inheritancesearchconstinstr.isNoPrivateConsts());
jvmMethod().inheritanceSearchConst(inheritancesearchconstinstr.getConstName(), false);
jvmStoreLocal(inheritancesearchconstinstr.getResult());
}

19 changes: 19 additions & 0 deletions core/src/main/java/org/jruby/parser/StaticScope.java
Original file line number Diff line number Diff line change
@@ -258,6 +258,25 @@ public void setVariables(String[] names) {
System.arraycopy(names, 0, variableNames, 0, names.length);
}

/**
* Gets a constant back from lexical search from the cref in this scope.
* As it is for defined? we will not forced resolution of autoloads nor
* call const_defined
*/
public IRubyObject getConstantDefined(String internedName) {
IRubyObject result = cref.fetchConstant(internedName);

if (result != null) return result;

return previousCRefScope == null ? null : previousCRefScope.getConstantDefinedNoObject(internedName);
}

public IRubyObject getConstantDefinedNoObject(String internedName) {
if (previousCRefScope == null) return null;

return getConstantDefined(internedName);
}

public IRubyObject getConstant(String internedName) {
IRubyObject result = getConstantInner(internedName);

74 changes: 73 additions & 1 deletion core/src/main/java/org/jruby/runtime/Helpers.java
Original file line number Diff line number Diff line change
@@ -34,6 +34,7 @@
import org.jruby.runtime.invokedynamic.MethodNames;
import org.jruby.util.ByteList;
import org.jruby.util.DefinedMessage;
import org.jruby.util.MurmurHash;
import org.jruby.util.TypeConverter;

import java.util.ArrayList;
@@ -48,7 +49,9 @@
import org.jcodings.specific.UTF8Encoding;
import org.jcodings.unicode.UnicodeEncoding;

import static org.jruby.runtime.Helpers.invokedynamic;
import static org.jruby.runtime.invokedynamic.MethodNames.EQL;
import static org.jruby.runtime.invokedynamic.MethodNames.HASH;
import static org.jruby.runtime.invokedynamic.MethodNames.OP_EQUAL;
import static org.jruby.util.CodegenUtils.sig;
import static org.jruby.util.StringSupport.EMPTY_STRING_ARRAY;
@@ -2140,7 +2143,7 @@ public static boolean isModuleAndHasConstant(IRubyObject left, String name) {

public static RubyString getDefinedConstantOrBoundMethod(IRubyObject left, String name) {
if (isModuleAndHasConstant(left, name)) return left.getRuntime().getDefinedMessage(DefinedMessage.CONSTANT);
if (left.getMetaClass().isMethodBound(name, true)) left.getRuntime().getDefinedMessage(DefinedMessage.METHOD);
if (left.getMetaClass().isMethodBound(name, true)) return left.getRuntime().getDefinedMessage(DefinedMessage.METHOD);
return null;
}

@@ -2714,6 +2717,75 @@ public static boolean isRequiredKeywordArgumentValueNode(Node asgnNode) {
return asgnNode.childNodes().get(0) instanceof RequiredKeywordArgumentValueNode;
}

// MRI: rb_hash_start
public static long hashStart(Ruby runtime, long value) {
long hash = value +
(runtime.isSiphashEnabled() ?
runtime.getHashSeedK1() :
runtime.getHashSeedK0());
return hash;
}

public static long hashEnd(long value) {
value = murmur_step(value, 10);
value = murmur_step(value, 17);
return value;
}

// MRI: rb_hash
public static RubyFixnum safeHash(final ThreadContext context, IRubyObject obj) {
final Ruby runtime = context.runtime;
IRubyObject hval = runtime.safeRecurse(new Ruby.RecursiveFunction() {
public IRubyObject call(IRubyObject obj, boolean recur) {
if (recur) return RubyFixnum.zero(runtime);
return invokedynamic(context, obj, HASH);
}
}, obj, "hash", true);

while (!(hval instanceof RubyFixnum)) {
if (hval instanceof RubyBignum) {
// This is different from MRI because we don't have rb_integer_pack
return ((RubyBignum) hval).hash();
}
hval = hval.convertToInteger();
}

return (RubyFixnum) hval;
}

public static long murmurCombine(long h, long i)
{
long v = 0;
h += i;
v = murmur1(v + h);
v = murmur1(v + (h >>> 4*8));
return v;
}

public static long murmur(long h, long k, int r)
{
long m = MurmurHash.MURMUR2_MAGIC;
h += k;
h *= m;
h ^= h >> r;
return h;
}

public static long murmur_finish(long h)
{
h = murmur(h, 0, 10);
h = murmur(h, 0, 17);
return h;
}

public static long murmur_step(long h, long k) {
return murmur((h), (k), 16);
}

public static long murmur1(long h) {
return murmur_step(h, 16);
}

@Deprecated
public static String encodeParameterList(List<String[]> args) {
if (args.size() == 0) return "NONE";
Original file line number Diff line number Diff line change
@@ -71,7 +71,7 @@ public InterpreterContext ensureInstrsReady() {
if (Options.IR_PRINT.load()) {
ByteArrayOutputStream baos = IRDumper.printIR(closure, false);

LOG.info("Printing simple IR for " + closure.getName(), "\n" + new String(baos.toByteArray()));
LOG.info("Printing simple IR for " + closure.getName() + ":\n" + new String(baos.toByteArray()));
}

interpreterContext = closure.getInterpreterContext();
Original file line number Diff line number Diff line change
@@ -86,7 +86,7 @@ public InterpreterContext ensureInstrsReady() {
if (Options.IR_PRINT.load()) {
ByteArrayOutputStream baos = IRDumper.printIR(closure, false);

LOG.info("Printing simple IR for " + closure.getName(), "\n" + new String(baos.toByteArray()));
LOG.info("Printing simple IR for " + closure.getName() + ":\n" + new String(baos.toByteArray()));
}

interpreterContext = closure.getInterpreterContext();
Original file line number Diff line number Diff line change
@@ -63,7 +63,6 @@ private RubyStackTraceElement[] constructBacktrace(Map<String, Map<String, Strin

// skip unnumbered frames
int line = element.getLineNumber();
if (line == -1) continue;

String className = element.getClassName();
String methodName = element.getMethodName();
12 changes: 11 additions & 1 deletion core/src/main/java/org/jruby/runtime/ivars/VariableAccessor.java
Original file line number Diff line number Diff line change
@@ -134,7 +134,17 @@ public void set(Object object, Object value) {
public boolean verify(Object object) {
return ((RubyBasicObject)object).getMetaClass().getRealClass() == this.realClass;
}


/**
* Produce a string representation of this VariableAccessor.
*
* @return a string representation of this VariableAccessor
*/
@Override
public String toString() {
return "ivar:" + getName() + ":" + index;
}

/** a dummy accessor that will always return null */
public static final VariableAccessor DUMMY_ACCESSOR = new VariableAccessor(null, null, -1, -1);

2 changes: 1 addition & 1 deletion core/src/main/java/org/jruby/util/MurmurHash.java
Original file line number Diff line number Diff line change
@@ -15,7 +15,7 @@ public class MurmurHash {

// 'm' and 'r' are mixing constants generated offline.
// They're not really 'magic', they just happen to work well.
private static final int MURMUR2_MAGIC = 0x5bd1e995;
public static final int MURMUR2_MAGIC = 0x5bd1e995;
// CRuby 1.9 uses 16 but original C++ implementation uses 24 with above Magic.
private static final int MURMUR2_R = 24;

2 changes: 1 addition & 1 deletion core/src/main/java/org/jruby/util/cli/Options.java
Original file line number Diff line number Diff line change
@@ -218,7 +218,7 @@ public class Options {
public static final Option<String> CLI_BACKUP_EXTENSION = string(CLI, "cli.backup.extension", "Backup extension for in-place ARGV files. Same as -i.");
public static final Option<ProfilingMode> CLI_PROFILING_MODE = enumeration(CLI, "cli.profiling.mode", ProfilingMode.class, ProfilingMode.OFF, "Enable instrumented profiling modes.");
public static final Option<Boolean> CLI_RUBYGEMS_ENABLE = bool(CLI, "cli.rubygems.enable", true, "Enable/disable RubyGems.");
public static final Option<Boolean> CLI_DID_YOU_MEAN_ENABLE = bool(CLI, "cli.did_you_mean.enable", false, "Enable/disable did_you_mean.");
public static final Option<Boolean> CLI_DID_YOU_MEAN_ENABLE = bool(CLI, "cli.did_you_mean.enable", true, "Enable/disable did_you_mean.");
public static final Option<Boolean> CLI_RUBYOPT_ENABLE = bool(CLI, "cli.rubyopt.enable", true, "Enable/disable RUBYOPT processing at start.");
public static final Option<Boolean> CLI_STRIP_HEADER = bool(CLI, "cli.strip.header", false, "Strip text before shebang in script. Same as -x.");
public static final Option<Boolean> CLI_LOAD_GEMFILE = bool(CLI, "cli.load.gemfile", false, "Load a bundler Gemfile in cwd before running. Same as -G.");
1 change: 1 addition & 0 deletions core/src/main/ruby/jruby/kernel/gem_prelude.rb
Original file line number Diff line number Diff line change
@@ -8,6 +8,7 @@
begin
gem 'did_you_mean'
require 'did_you_mean'
Gem.clear_paths
rescue Gem::LoadError, LoadError
end if defined?(DidYouMean)
end
2 changes: 1 addition & 1 deletion lib/pom.rb
Original file line number Diff line number Diff line change
@@ -22,7 +22,7 @@ def initialize( name, version, default_spec = true )
ImportedGem.new( 'jar-dependencies', '${jar-dependencies.version}' ),
ImportedGem.new( 'racc', '${racc.version}'),
ImportedGem.new( 'net-telnet', '0.1.1'),
#ImportedGem.new( 'did_you_mean', '1.0.1'),
ImportedGem.new( 'did_you_mean', '1.0.1'),
]

project 'JRuby Lib Setup' do
17 changes: 15 additions & 2 deletions lib/pom.xml
Original file line number Diff line number Diff line change
@@ -12,7 +12,7 @@ DO NOT MODIFIY - GENERATED CODE
<parent>
<groupId>org.jruby</groupId>
<artifactId>jruby-parent</artifactId>
<version>9.1.1.0-SNAPSHOT</version>
<version>9.1.2.0-SNAPSHOT</version>
</parent>
<artifactId>jruby-stdlib</artifactId>
<name>JRuby Lib Setup</name>
@@ -28,7 +28,7 @@ DO NOT MODIFIY - GENERATED CODE
<dependency>
<groupId>org.jruby</groupId>
<artifactId>jruby-core</artifactId>
<version>9.1.1.0-SNAPSHOT</version>
<version>9.1.2.0-SNAPSHOT</version>
<scope>test</scope>
</dependency>
<dependency>
@@ -187,6 +187,19 @@ DO NOT MODIFIY - GENERATED CODE
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>rubygems</groupId>
<artifactId>did_you_mean</artifactId>
<version>1.0.1</version>
<type>gem</type>
<scope>provided</scope>
<exclusions>
<exclusion>
<artifactId>jar-dependencies</artifactId>
<groupId>rubygems</groupId>
</exclusion>
</exclusions>
</dependency>
</dependencies>
<repositories>
<repository>
7 changes: 7 additions & 0 deletions lib/ruby/truffle/cext/ruby.h
Original file line number Diff line number Diff line change
@@ -20,6 +20,8 @@ extern "C" {
#include <string.h>
#include <math.h>

#define JRUBY_TRUFFLE 1

#define xmalloc malloc
#define xfree free
#define ALLOC_N(type, n) malloc(sizeof(type) * n)
@@ -30,10 +32,14 @@ typedef void *VALUE;
VALUE get_Qfalse();
VALUE get_Qtrue();
VALUE get_Qnil();
VALUE get_rb_cProc();
VALUE get_rb_eException();

#define Qfalse get_Qfalse()
#define Qtrue get_Qtrue()
#define Qnil get_Qnil()
#define rb_cProc get_rb_cProc();
#define rb_eException get_rb_eException();

VALUE get_rb_cObject();
VALUE get_rb_cArray();
@@ -101,6 +107,7 @@ VALUE rb_const_get(VALUE object, ID name);

void rb_raise(VALUE exception, const char *format, ...);

VALUE rb_define_class(const char *name, VALUE superclass);
VALUE rb_define_module(const char *name);
VALUE rb_define_module_under(VALUE module, const char *name);

Binary file modified lib/ruby/truffle/cext/ruby.su
Binary file not shown.
14 changes: 14 additions & 0 deletions lib/ruby/truffle/cext/version.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
/*
* Copyright (c) 2016 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 1.0
* GNU General Public License version 2
* GNU Lesser General Public License version 2.1
*/

#ifndef TRUFFLE_VERSION_H
#define TRUFFLE_VERSION_H

#endif
2 changes: 1 addition & 1 deletion pom.xml
Original file line number Diff line number Diff line change
@@ -16,7 +16,7 @@ DO NOT MODIFIY - GENERATED CODE
</parent>
<groupId>org.jruby</groupId>
<artifactId>jruby-parent</artifactId>
<version>9.1.1.0-SNAPSHOT</version>
<version>9.1.2.0-SNAPSHOT</version>
<packaging>pom</packaging>
<name>JRuby</name>
<description>JRuby is the effort to recreate the Ruby (http://www.ruby-lang.org) interpreter in Java.</description>
1 change: 1 addition & 0 deletions rakelib/test.rake
Original file line number Diff line number Diff line change
@@ -115,6 +115,7 @@ namespace :test do
t.ruby_opts << '-Xaot.loadClasses=true' # disabled by default now
t.ruby_opts << '-I.'
t.ruby_opts << '-J-ea'
t.ruby_opts << '--headless'
classpath = %w[test test/target/test-classes core/target/test-classes].join(File::PATH_SEPARATOR)
t.ruby_opts << "-J-cp #{classpath}"
end
580 changes: 580 additions & 0 deletions spec/ruby/optional/capi/ext/jruby_truffle.h

Large diffs are not rendered by default.

2 changes: 2 additions & 0 deletions spec/ruby/optional/capi/ext/rubyspec.h
Original file line number Diff line number Diff line change
@@ -615,6 +615,8 @@
#include "rubinius.h"
#elif defined(JRUBY)
#include "jruby.h"
#elif defined(JRUBY_TRUFFLE)
#include "jruby_truffle.h"
#endif

#endif
18 changes: 18 additions & 0 deletions spec/ruby/optional/capi/spec_helper.rb
Original file line number Diff line number Diff line change
@@ -42,6 +42,8 @@ def compile_extension(name)
elsif RUBY_NAME == "maglev"
require 'mkmf'
hdrdir = $hdrdir
elsif RUBY_NAME == 'jruby+truffle'
return compile_extension_jruby_truffle(name)
else
raise "Don't know how to build C extensions with #{RUBY_NAME}"
end
@@ -99,6 +101,22 @@ def compile_extension(name)
ENV[preloadenv] = preload if preloadenv
end

def compile_extension_jruby_truffle(name)
sulong_config_file = File.join(extension_path, '.jruby-cext-build.yml')
output_file = File.join(object_path, "#{name}_spec.#{RbConfig::CONFIG['DLEXT']}")

File.open(sulong_config_file, 'w') do |f|
f.puts "src: #{name}_spec.c"
f.puts "out: #{output_file}"
end

system "#{RbConfig::CONFIG['bindir']}/jruby", "#{RbConfig::CONFIG['bindir']}/jruby-cext-c", extension_path

output_file
ensure
File.delete(sulong_config_file) if File.exist?(sulong_config_file)
end

def load_extension(name)
require compile_extension(name)
end
60 changes: 60 additions & 0 deletions spec/truffle/tags/optional/capi/array_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
fails:C-API Array function rb_Array returns obj if it is an array
fails:C-API Array function rb_Array tries to convert obj to an array
fails:C-API Array function rb_Array returns obj wrapped in an array if it cannot be converted to an array
fails:C-API Array function rb_ary_new2 returns an empty array
fails:C-API Array function rb_ary_new3 returns an array with the passed cardinality and varargs
fails:C-API Array function rb_ary_new_from_args returns an array with the passed cardinality and varargs
fails:C-API Array function rb_ary_new4 returns returns an array with the passed values
fails:C-API Array function rb_ary_push adds an element to the array
fails:C-API Array function rb_ary_pop removes and returns the last element in the array
fails:C-API Array function rb_ary_join joins elements of an array with a string
fails:C-API Array function rb_ary_to_s creates an Array literal representation as a String
fails:C-API Array function rb_ary_reverse reverses the order of elements in the array
fails:C-API Array function rb_ary_reverse returns the original array
fails:C-API Array function rb_ary_entry returns nil when passed an empty array
fails:C-API Array function rb_ary_entry returns elements from the end when passed a negative index
fails:C-API Array function rb_ary_entry returns nil if the index is out of range
fails:C-API Array function rb_ary_clear removes all elements from the array
fails:C-API Array function rb_ary_dup duplicates the array
fails:C-API Array function rb_ary_unshift prepends the element to the array
fails:C-API Array function rb_ary_shift removes and returns the first element
fails:C-API Array function rb_ary_shift returns nil when the array is empty
fails:C-API Array function rb_ary_store overwrites the element at the given position
fails:C-API Array function rb_ary_store writes to elements offset from the end if passed a negative index
fails:C-API Array function rb_ary_store raises on IndexError if the negative index is greater than the length
fails:C-API Array function rb_ary_store enlarges the array as needed
fails:C-API Array function rb_ary_concat concats two arrays
fails:C-API Array function rb_ary_plus adds two arrays together
fails:C-API Array function RARRAY_PTR returns a pointer to a C array of the array's elements
fails:C-API Array function RARRAY_PTR allows assigning to the elements of the C array
fails:C-API Array function RARRAY_LEN returns the size of the array
fails:C-API Array function RARRAY_AREF returns an element from the array
fails:C-API Array function rb_assoc_new returns an array containing the two elements
fails:C-API Array function rb_ary_includes returns true if the array includes the element
fails:C-API Array function rb_ary_includes returns false if the array does not include the element
fails:C-API Array function rb_ary_aref returns the element at the given index
fails:C-API Array function rb_ary_aref returns nil for an out of range index
fails:C-API Array function rb_ary_aref returns a new array where the first argument is the index and the second is the length
fails:C-API Array function rb_ary_aref accepts a range
fails:C-API Array function rb_ary_aref returns nil when the start of a range is out of bounds
fails:C-API Array function rb_ary_aref returns an empty array when the start of a range equals the last element
fails:C-API Array function rb_iterate calls an callback function as a block passed to an method
fails:C-API Array function rb_iterate calls a function with the other function available as a block
fails:C-API Array function rb_iterate calls a function which can yield into the original block
fails:C-API Array function rb_ary_delete removes an element from an array and returns it
fails:C-API Array function rb_ary_delete returns nil if the element is not in the array
fails:C-API Array function rb_mem_clear sets elements of a C array to nil
fails:C-API Array function rb_ary_freeze freezes the object exactly like Kernel#freeze
fails:C-API Array function rb_ary_delete_at removes an element from an array at a positive index
fails:C-API Array function rb_ary_delete_at removes an element from an array at a negative index
fails:C-API Array function rb_ary_delete_at returns nil if the index is out of bounds
fails:C-API Array function rb_ary_delete_at returns nil if the negative index is out of bounds
fails:C-API Array function rb_ary_to_ary with an array returns the given array
fails:C-API Array function rb_ary_to_ary with an object that responds to to_ary calls to_ary on the object
fails:C-API Array function rb_ary_to_ary with an object that responds to to_a returns the original object in an array
fails:C-API Array function rb_ary_to_ary with an object that doesn't respond to to_ary returns the original object in an array
fails:C-API Array function rb_ary_subseq returns a subsequence of the given array
fails:C-API Array function rb_ary_subseq returns an empty array for a subsequence of 0 elements
fails:C-API Array function rb_ary_subseq returns nil if the begin index is out of bound
fails:C-API Array function rb_ary_subseq returns the existing subsequence of the length is out of bounds
fails:C-API Array function rb_ary_subseq returns nil if the size is negative
20 changes: 20 additions & 0 deletions spec/truffle/tags/optional/capi/bignum_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
fails:CApiBignumSpecs rb_big2long converts a Bignum
fails:CApiBignumSpecs rb_big2long raises RangeError if passed Bignum overflow long
fails:CApiBignumSpecs rb_big2ll converts a Bignum
fails:CApiBignumSpecs rb_big2ll raises RangeError if passed Bignum overflow long
fails:CApiBignumSpecs rb_big2ulong converts a Bignum
fails:CApiBignumSpecs rb_big2ulong wraps around if passed a negative bignum
fails:CApiBignumSpecs rb_big2ulong raises RangeError if passed Bignum overflow long
fails:CApiBignumSpecs rb_big2dbl converts a Bignum to a double value
fails:CApiBignumSpecs rb_big2dbl returns Infinity if the number is too big for a double
fails:CApiBignumSpecs rb_big2dbl returns -Infinity if the number is negative and too big for a double
fails:CApiBignumSpecs rb_big2str converts a Bignum to a string with base 10
fails:CApiBignumSpecs rb_big2str converts a Bignum to a string with a different base
fails:CApiBignumSpecs rb_big_cmp compares a Bignum with a Bignum
fails:CApiBignumSpecs rb_big_cmp compares a Bignum with a Fixnum
fails:CApiBignumSpecs rb_big_pack packs a Bignum into a Fixnum
fails:CApiBignumSpecs rb_dbl2big returns a Fixnum for a Fixnum input value
fails:CApiBignumSpecs rb_dbl2big returns a Fixnum for a Float input value
fails:CApiBignumSpecs rb_dbl2big returns a Bignum for a large enough Float input value
fails:CApiBignumSpecs rb_dbl2big raises FloatDomainError for Infinity values
fails:CApiBignumSpecs rb_dbl2big raises FloatDomainError for NaN values
54 changes: 54 additions & 0 deletions spec/truffle/tags/optional/capi/class_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
fails:C-API Class function rb_class_new_instance allocates and initializes a new object
fails:C-API Class function rb_class_new_instance passes arguments to the #initialize method
fails:C-API Class function rb_include_module includes a module into a class
fails:C-API Class function rb_define_attr defines an attr_reader when passed true, false
fails:C-API Class function rb_define_attr defines an attr_writer when passed false, true
fails:C-API Class function rb_define_attr defines an attr_accessor when passed true, true
fails:C-API Class function rb_call_super calls the method in the superclass
fails:C-API Class function rb_call_super calls the method in the superclass through two native levels
fails:C-API Class function rb_class2name returns the class name
fails:C-API Class function rb_class2name returns a string for an anonymous class
fails:C-API Class function rb_class_path returns a String of a class path with no scope modifiers
fails:C-API Class function rb_class_path returns a String of a class path with scope modifiers
fails:C-API Class function rb_class_name returns the class name
fails:C-API Class function rb_class_name returns a string for an anonymous class
fails:C-API Class function rb_path2class returns a class or module from a scoped String
fails:C-API Class function rb_path2class resolves autoload constants
fails:C-API Class function rb_path2class raises an ArgumentError if a constant in the path does not exist
fails:C-API Class function rb_path2class raises an ArgumentError if the final constant does not exist
fails:C-API Class function rb_path2class raises a TypeError if the constant is not a class or module
fails:C-API Class function rb_path2class raises an ArgumentError even if a constant in the path exists on toplevel
fails:C-API Class function rb_path_to_class returns a class or module from a scoped String
fails:C-API Class function rb_path_to_class resolves autoload constants
fails:C-API Class function rb_path_to_class raises an ArgumentError if a constant in the path does not exist
fails:C-API Class function rb_path_to_class raises an ArgumentError if the final constant does not exist
fails:C-API Class function rb_path_to_class raises a TypeError if the constant is not a class or module
fails:C-API Class function rb_path_to_class raises an ArgumentError even if a constant in the path exists on toplevel
fails:C-API Class function rb_cvar_defined returns false when the class variable is not defined
fails:C-API Class function rb_cvar_defined returns true when the class variable is defined
fails:C-API Class function rb_cvar_defined returns true if the class instance variable is defined
fails:C-API Class function rb_cv_set sets a class variable
fails:C-API Class function rb_cv_get returns the value of the class variable
fails:C-API Class function rb_cvar_set sets a class variable
fails:C-API Class function rb_define_class_under creates a subclass of the superclass contained in a module
fails:C-API Class function rb_define_class_under sets the class name
fails:C-API Class function rb_define_class_under calls #inherited on the superclass
fails:C-API Class function rb_define_class_under raises a TypeError when given a non class object to superclass
fails:C-API Class function rb_define_class_under raises a TypeError when given a mismatched class to superclass
fails:C-API Class function rb_define_class_under defines a class for an existing Autoload
fails:C-API Class function rb_define_class_under raises a TypeError if class is defined and its superclass mismatches the given one
fails:C-API Class function rb_define_class_id_under creates a subclass of the superclass contained in a module
fails:C-API Class function rb_define_class_id_under sets the class name
fails:C-API Class function rb_define_class_id_under calls #inherited on the superclass
fails:C-API Class function rb_define_class_id_under defines a class for an existing Autoload
fails:C-API Class function rb_define_class_id_under raises a TypeError if class is defined and its superclass mismatches the given one
fails:C-API Class function rb_define_class_variable sets a class variable
fails:C-API Class function rb_cvar_get returns the value of the class variable
fails:C-API Class function rb_class_new returns an new subclass of the superclass
fails:C-API Class function rb_class_new raises a TypeError if passed Class as the superclass
fails:C-API Class function rb_class_new raises a TypeError if passed a singleton class as the superclass
fails:C-API Class function rb_class_superclass returns the superclass of a class
fails:C-API Class function rb_class_superclass returns nil if the class has no superclass
fails:C-API Class function rb_class_real returns the class of an object ignoring the singleton class
fails:C-API Class function rb_class_real returns the class of an object ignoring included modules
fails:C-API Class function rb_class_real returns 0 if passed 0
5 changes: 5 additions & 0 deletions spec/truffle/tags/optional/capi/complex_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
fails:CApiComplexSpecs rb_Complex creates a new Complex with numerator and denominator
fails:CApiComplexSpecs rb_Complex2 creates a new Complex with numerator and denominator
fails:CApiComplexSpecs rb_Complex1 creates a new Complex with real and imaginary of 0
fails:CApiComplexSpecs rb_complex_new creates a normalized Complex
fails:CApiComplexSpecs rb_complex_new2 creates a normalized Complex
61 changes: 61 additions & 0 deletions spec/truffle/tags/optional/capi/constants_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
fails:C-API constant rb_cArray references the Array class
fails:C-API constant rb_cBignum references the Bignum class
fails:C-API constant rb_cClass references the Class class
fails:C-API constant rb_mComparable references the Comparable module
fails:C-API constant rb_cData references the Data class
fails:C-API constant rb_mEnumerable references the Enumerable module
fails:C-API constant rb_cFalseClass references the FalseClass class
fails:C-API constant rb_cFile references the File class
fails:C-API constant rb_cFixnum references the Fixnum class
fails:C-API constant rb_cFloat references the Float class
fails:C-API constant rb_cHash references the Hash class
fails:C-API constant rb_cInteger references the Integer class
fails:C-API constant rb_cIO references the IO class
fails:C-API constant rb_mKernel references the Kernel module
fails:C-API constant rb_cMatch references the MatchData class
fails:C-API constant rb_cModule references the Module class
fails:C-API constant rb_cNilClass references the NilClass class
fails:C-API constant rb_cNumeric references the Numeric class
fails:C-API constant rb_cObject references the Object class
fails:C-API constant rb_cRange references the Range class
fails:C-API constant rb_cRegexp references the Regexp class
fails:C-API constant rb_cString references the String class
fails:C-API constant rb_cStruct references the Struct class
fails:C-API constant rb_cSymbol references the Symbol class
fails:C-API constant rb_cThread references the Thread class
fails:C-API constant rb_cTrueClass references the TrueClass class
fails:C-API constant rb_cProc references the Proc class
fails:C-API constant rb_cMethod references the Method class
fails:C-API constant rb_cDir references the Dir class
fails:C-API exception constant rb_eArgError references the ArgumentError class
fails:C-API exception constant rb_eEOFError references the EOFError class
fails:C-API exception constant rb_eErrno references the Errno module
fails:C-API exception constant rb_eException references the Exception class
fails:C-API exception constant rb_eFloatDomainError references the FloatDomainError class
fails:C-API exception constant rb_eIndexError references the IndexError class
fails:C-API exception constant rb_eInterrupt references the Interrupt class
fails:C-API exception constant rb_eIOError references the IOError class
fails:C-API exception constant rb_eLoadError references the LoadError class
fails:C-API exception constant rb_eLocalJumpError references the LocalJumpError class
fails:C-API exception constant rb_eMathDomainError references the Math::DomainError class
fails:C-API exception constant rb_eEncCompatError references the Encoding::CompatibilityError
fails:C-API exception constant rb_eNameError references the NameError class
fails:C-API exception constant rb_eNoMemError references the NoMemoryError class
fails:C-API exception constant rb_eNoMethodError references the NoMethodError class
fails:C-API exception constant rb_eNotImpError references the NotImplementedError class
fails:C-API exception constant rb_eRangeError references the RangeError class
fails:C-API exception constant rb_eRegexpError references the RegexpError class
fails:C-API exception constant rb_eRuntimeError references the RuntimeError class
fails:C-API exception constant rb_eScriptError references the ScriptError class
fails:C-API exception constant rb_eSecurityError references the SecurityError class
fails:C-API exception constant rb_eSignal references the SignalException class
fails:C-API exception constant rb_eStandardError references the StandardError class
fails:C-API exception constant rb_eSyntaxError references the SyntaxError class
fails:C-API exception constant rb_eSystemCallError references the SystemCallError class
fails:C-API exception constant rb_eSystemExit references the SystemExit class
fails:C-API exception constant rb_eSysStackError references the SystemStackError class
fails:C-API exception constant rb_eTypeError references the TypeError class
fails:C-API exception constant rb_eThreadError references the ThreadError class
fails:C-API exception constant rb_mWaitReadable references the IO::WaitReadable module
fails:C-API exception constant rb_mWaitWritable references the IO::WaitWritable module
fails:C-API exception constant rb_eZeroDivError references the ZeroDivisionError class
4 changes: 4 additions & 0 deletions spec/truffle/tags/optional/capi/enumerator_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
fails:C-API Enumerator function rb_enumeratorize constructs a new Enumerator for the given object, method and arguments
fails:C-API Enumerator function rb_enumeratorize enumerates the given object
fails:C-API Enumerator function rb_enumeratorize uses the given method for enumeration
fails:C-API Enumerator function rb_enumeratorize passes the given arguments to the enumeration method
8 changes: 8 additions & 0 deletions spec/truffle/tags/optional/capi/exception_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
fails:C-API Exception function rb_exc_new creates an exception from a C string and length
fails:C-API Exception function rb_exc_new2 creates an exception from a C string
fails:C-API Exception function rb_exc_new3 creates an exception from a Ruby string
fails:C-API Exception function rb_exc_raise raises passed exception
fails:C-API Exception function rb_exc_raise raises an exception with an empty backtrace
fails:C-API Exception function rb_set_errinfo accepts nil
fails:C-API Exception function rb_set_errinfo accepts an Exception instance
fails:C-API Exception function rb_set_errinfo raises a TypeError if the object is not nil or an Exception instance
14 changes: 14 additions & 0 deletions spec/truffle/tags/optional/capi/file_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
fails:C-API File function rb_file_open raises an ArgumentError if passed an empty mode string
fails:C-API File function rb_file_open opens a file in read-only mode with 'r'
fails:C-API File function rb_file_open creates and opens a non-existent file with 'w'
fails:C-API File function rb_file_open truncates an existing file with 'w'
fails:C-API File function rb_file_open_str raises an ArgumentError if passed an empty mode string
fails:C-API File function rb_file_open_str opens a file in read-only mode with 'r'
fails:C-API File function rb_file_open_str creates and opens a non-existent file with 'w'
fails:C-API File function rb_file_open_str truncates an existing file with 'w'
fails:C-API File function rb_file_open_str calls #to_path to convert on object to a path
fails:C-API File function rb_file_open_str calls #to_str to convert an object to a path if #to_path isn't defined
fails:C-API File function FilePathValue returns a String argument unchanged
fails:C-API File function FilePathValue does not call #to_str on a String
fails:C-API File function FilePathValue calls #to_path to convert an object to a String
fails:C-API File function FilePathValue calls #to_str to convert an object to a String if #to_path isn't defined
14 changes: 14 additions & 0 deletions spec/truffle/tags/optional/capi/fixnum_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
fails:CApiFixnumSpecs rb_fix2uint raises a TypeError if passed nil
fails:CApiFixnumSpecs rb_fix2uint converts a Fixnum
fails:CApiFixnumSpecs rb_fix2uint converts the maximum uint value
fails:CApiFixnumSpecs rb_fix2uint converts a Float
fails:CApiFixnumSpecs rb_fix2uint raises a RangeError if the value is more than 32bits
fails:CApiFixnumSpecs rb_fix2uint raises a RangeError if the value is more than 64bits
fails:CApiFixnumSpecs rb_fix2int raises a TypeError if passed nil
fails:CApiFixnumSpecs rb_fix2int converts a Fixnum
fails:CApiFixnumSpecs rb_fix2int converts the maximum uint value
fails:CApiFixnumSpecs rb_fix2int converts a Float
fails:CApiFixnumSpecs rb_fix2int converts a negative Bignum into an signed number
fails:CApiFixnumSpecs rb_fix2int raises a RangeError if the value is more than 32bits
fails:CApiFixnumSpecs rb_fix2int raises a RangeError if the value is more than 64bits
fails:CApiFixnumSpecs rb_fix2int calls #to_int to coerce the value
3 changes: 3 additions & 0 deletions spec/truffle/tags/optional/capi/float_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
fails:CApiFloatSpecs rb_float_new creates a new float
fails:CApiFloatSpecs RFLOAT_VALUE returns the C double value of the Float
fails:CApiFloatSpecs rb_Float creates a new Float from a String
5 changes: 5 additions & 0 deletions spec/truffle/tags/optional/capi/gc_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
fails:CApiGCSpecs correctly gets the value from a registered address
fails:CApiGCSpecs rb_gc_enable enables GC when disabled
fails:CApiGCSpecs rb_gc_enable GC stays enabled when enabled
fails:CApiGCSpecs rb_gc_enable disables GC when enabled
fails:CApiGCSpecs rb_gc_enable GC stays disabled when disabled
35 changes: 35 additions & 0 deletions spec/truffle/tags/optional/capi/globals_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
fails:CApiGlobalSpecs correctly gets global values
fails:CApiGlobalSpecs returns $~
fails:CApiGlobalSpecs correctly sets global values
fails:CApiGlobalSpecs lists all global variables
fails:CApiGlobalSpecs rb_define_readonly_variable should define a new readonly global variable
fails:CApiGlobalSpecs rb_rs returns \n by default
fails:CApiGlobalSpecs rb_rs returns the value of $/
fails:CApiGlobalSpecs rb_std streams rb_stdin returns $stdin
fails:CApiGlobalSpecs rb_std streams rb_stdout returns $stdout
fails:CApiGlobalSpecs rb_std streams rb_stderr returns $stderr
fails:CApiGlobalSpecs rb_std streams rb_defout returns $stdout
fails:CApiGlobalSpecs rb_default_rs returns \n
fails:CApiGlobalSpecs rb_output_rs returns nil by default
fails:CApiGlobalSpecs rb_output_rs returns the value of $\
fails:CApiGlobalSpecs rb_output_fs returns nil by default
fails:CApiGlobalSpecs rb_output_fs returns the value of $\
fails:CApiGlobalSpecs rb_lastline_set sets the value of $_
fails:CApiGlobalSpecs rb_lastline_set sets a Thread-local value
fails:CApiGlobalSpecs rb_lastline_get gets the value of $_
fails:CApiGlobalSpecs rb_lastline_get gets a Thread-local value
fails:CApiGlobalSpecs rb_rs returns \n by default
fails:CApiGlobalSpecs rb_rs returns the value of $/
fails:CApiGlobalSpecs rb_std streams rb_stdin returns $stdin
fails:CApiGlobalSpecs rb_std streams rb_stdout returns $stdout
fails:CApiGlobalSpecs rb_std streams rb_stderr returns $stderr
fails:CApiGlobalSpecs rb_std streams rb_defout returns $stdout
fails:CApiGlobalSpecs rb_default_rs returns \n
fails:CApiGlobalSpecs rb_output_rs returns nil by default
fails:CApiGlobalSpecs rb_output_rs returns the value of $\
fails:CApiGlobalSpecs rb_output_fs returns nil by default
fails:CApiGlobalSpecs rb_output_fs returns the value of $\
fails:CApiGlobalSpecs rb_lastline_set sets the value of $_
fails:CApiGlobalSpecs rb_lastline_set sets a Thread-local value
fails:CApiGlobalSpecs rb_lastline_get gets the value of $_
fails:CApiGlobalSpecs rb_lastline_get gets a Thread-local value
27 changes: 27 additions & 0 deletions spec/truffle/tags/optional/capi/hash_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
fails:C-API Hash function rb_hash calls #hash on the object
fails:C-API Hash function rb_hash converts a Bignum returned by #hash to a Fixnum
fails:C-API Hash function rb_hash calls #to_int to converts a value returned by #hash to a Fixnum
fails:C-API Hash function rb_hash raises a TypeError if the object does not implement #to_int
fails:C-API Hash function rb_hash_new returns a new hash
fails:C-API Hash function rb_hash_new creates a hash with no default proc
fails:C-API Hash function rb_hash_dup returns a copy of the hash
fails:C-API Hash function rb_hash_freeze freezes the hash
fails:C-API Hash function rb_hash_aref returns the value associated with the key
fails:C-API Hash function rb_hash_aref returns the default value if it exists
fails:C-API Hash function rb_hash_aref returns nil if the key does not exist
fails:C-API Hash function rb_hash_aset adds the key/value pair and returns the value
fails:C-API Hash function rb_hash_clear returns self that cleared keys and values
fails:C-API Hash function rb_hash_delete removes the key and returns the value
fails:C-API Hash function rb_hash_delete_if removes an entry if the block returns true
fails:C-API Hash function rb_hash_delete_if returns an Enumerator when no block is passed
fails:C-API Hash function rb_hash_foreach iterates over the hash
fails:C-API Hash function rb_hash_foreach stops via the callback
fails:C-API Hash function rb_hash_foreach deletes via the callback
fails:C-API Hash function rb_hash_size returns the size of the hash
fails:C-API Hash function rb_hash_size returns zero for an empty hash
fails:C-API Hash function rb_hash_lookup returns the value associated with the key
fails:C-API Hash function rb_hash_lookup does not return the default value if it exists
fails:C-API Hash function rb_hash_lookup returns nil if the key does not exist
fails:C-API Hash function rb_hash_lookup rb_hash_lookup2 returns the value associated with the key
fails:C-API Hash function rb_hash_lookup rb_hash_lookup2 returns the default value if the key does not exist
fails:C-API Hash function rb_hash_set_ifnone sets the default value of non existing keys
25 changes: 25 additions & 0 deletions spec/truffle/tags/optional/capi/integer_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
fails:CApiIntegerSpecs rb_integer_pack converts zero
fails:CApiIntegerSpecs rb_integer_pack without two's complement flag with big endian output converts a positive number
fails:CApiIntegerSpecs rb_integer_pack without two's complement flag with big endian output converts a negative number
fails:CApiIntegerSpecs rb_integer_pack without two's complement flag with big endian output converts a negative number exactly -2**(numwords*wordsize*8)
fails:CApiIntegerSpecs rb_integer_pack without two's complement flag with little endian output converts a positive number
fails:CApiIntegerSpecs rb_integer_pack without two's complement flag with little endian output converts a negative number
fails:CApiIntegerSpecs rb_integer_pack without two's complement flag with little endian output converts a negative number exactly -2**(numwords*wordsize*8)
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input less than 64 bits with big endian output converts a positive number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input less than 64 bits with big endian output converts a negative number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input less than 64 bits with little endian output converts a positive number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input less than 64 bits with little endian output converts a negative number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input less than 64 bits with native endian output converts a positive number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input less than 64 bits with native endian output converts a negative number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input greater than 64 bits with big endian output converts a positive number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input greater than 64 bits with big endian output converts a negative number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input greater than 64 bits with big endian output with overflow converts a positive number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input greater than 64 bits with big endian output with overflow converts a negative number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input greater than 64 bits with big endian output with overflow converts a negative number exactly -2**(numwords*wordsize*8)
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input greater than 64 bits with little endian output converts a positive number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input greater than 64 bits with little endian output converts a negative number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input greater than 64 bits with little endian output with overflow converts a positive number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input greater than 64 bits with little endian output with overflow converts a negative number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input greater than 64 bits with little endian output with overflow converts a negative number exactly -2**(numwords*wordsize*8)
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input greater than 64 bits with native endian output converts a positive number
fails:CApiIntegerSpecs rb_integer_pack with two's complement flag with input greater than 64 bits with native endian output converts a negative number
62 changes: 62 additions & 0 deletions spec/truffle/tags/optional/capi/kernel_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
fails:C-API Kernel function rb_block_given_p returns false if no block is passed
fails:C-API Kernel function rb_block_given_p returns true if a block is passed
fails:C-API Kernel function rb_need_block raises a LocalJumpError if no block is given
fails:C-API Kernel function rb_need_block does not raise a LocalJumpError if a block is given
fails:C-API Kernel function rb_block_call calls the block with a single argument
fails:C-API Kernel function rb_block_call calls the block with multiple arguments in argc / argv
fails:C-API Kernel function rb_block_call calls the method with no function callback and no block
fails:C-API Kernel function rb_block_call calls the method with no function callback and a block
fails:C-API Kernel function rb_raise raises an exception
fails:C-API Kernel function rb_raise terminates the function at the point it was called
fails:C-API Kernel function rb_throw sets the return value of the catch block to the specified value
fails:C-API Kernel function rb_throw terminates the function at the point it was called
fails:C-API Kernel function rb_throw raises an ArgumentError if there is no catch block for the symbol
fails:C-API Kernel function rb_throw_obj sets the return value of the catch block to the specified value
fails:C-API Kernel function rb_throw_obj terminates the function at the point it was called
fails:C-API Kernel function rb_throw_obj raises an ArgumentError if there is no catch block for the symbol
fails:C-API Kernel function rb_warn prints a message to $stderr if $VERBOSE evaluates to true
fails:C-API Kernel function rb_warn prints a message to $stderr if $VERBOSE evaluates to false
fails:C-API Kernel function rb_sys_fail raises an exception from the value of errno
fails:C-API Kernel function rb_sys_fail can take a NULL message
fails:C-API Kernel function rb_syserr_fail raises an exception from the given error
fails:C-API Kernel function rb_syserr_fail can take a NULL message
fails:C-API Kernel function rb_yield yields passed argument
fails:C-API Kernel function rb_yield returns the result from block evaluation
fails:C-API Kernel function rb_yield raises LocalJumpError when no block is given
fails:C-API Kernel function rb_yield_values yields passed arguments
fails:C-API Kernel function rb_yield_values returns the result from block evaluation
fails:C-API Kernel function rb_yield_values raises LocalJumpError when no block is given
fails:C-API Kernel function rb_yield_splat yields with passed array's contents
fails:C-API Kernel function rb_yield_splat returns the result from block evaluation
fails:C-API Kernel function rb_yield_splat raises LocalJumpError when no block is given
fails:C-API Kernel function rb_rescue executes passed function
fails:C-API Kernel function rb_rescue executes passed 'raise function' if a StandardError exception is raised
fails:C-API Kernel function rb_rescue passes the user supplied argument to the 'raise function' if a StandardError exception is raised
fails:C-API Kernel function rb_rescue passes the raised exception to the 'raise function' if a StandardError exception is raised
fails:C-API Kernel function rb_rescue raises an exception if passed function raises an exception other than StandardError
fails:C-API Kernel function rb_rescue raises an exception if any exception is raised inside 'raise function'
fails:C-API Kernel function rb_rescue makes $! available only during 'raise function' execution
fails:C-API Kernel function rb_rescue returns the break value if the passed function yields to a block with a break
fails:C-API Kernel function rb_rescue2 only rescues if one of the passed exceptions is raised
fails:C-API Kernel function rb_catch executes passed function
fails:C-API Kernel function rb_catch terminates the function at the point it was called
fails:C-API Kernel function rb_catch raises an ArgumentError if the throw symbol isn't caught
fails:C-API Kernel function rb_catch_obj executes passed function
fails:C-API Kernel function rb_catch_obj terminates the function at the point it was called
fails:C-API Kernel function rb_catch_obj raises an ArgumentError if the throw symbol isn't caught
fails:C-API Kernel function rb_ensure executes passed function and returns its value
fails:C-API Kernel function rb_ensure executes passed 'ensure function' when no exception is raised
fails:C-API Kernel function rb_ensure executes passed 'ensure function' when an exception is raised
fails:C-API Kernel function rb_ensure raises the same exception raised inside passed function
fails:C-API Kernel function rb_eval_string evaluates a string of ruby code
fails:C-API Kernel function rb_block_proc converts the implicit block into a proc
fails:C-API Kernel function rb_exec_recursive detects recursive invocations of a method and indicates as such
fails:C-API Kernel function rb_set_end_proc runs a C function on shutdown
fails:C-API Kernel function rb_f_sprintf returns a string according to format and arguments
fails:C-API Kernel function rb_make_backtrace returns a caller backtrace
fails:C-API Kernel function rb_obj_method returns the method object for a symbol
fails:C-API Kernel function rb_obj_method returns the method object for a string
fails:C-API Kernel function rb_funcall3 calls a public method
fails:C-API Kernel function rb_funcall3 does not call a private method
fails:C-API Kernel function rb_funcall_with_block calls a method with block
fails:C-API Kernel function rb_funcall_with_block does not call a private method
3 changes: 3 additions & 0 deletions spec/truffle/tags/optional/capi/marshal_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
fails:CApiMarshalSpecs rb_marshal_dump marshals an object
fails:CApiMarshalSpecs rb_marshal_dump marshals an object and write to an IO when passed
fails:CApiMarshalSpecs rb_marshal_load unmarshals an object
44 changes: 44 additions & 0 deletions spec/truffle/tags/optional/capi/module_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
fails:CApiModule rb_define_global_const defines a constant on Object
fails:CApiModule rb_const_set given a symbol name and a value sets a new constant on a module
fails:CApiModule rb_const_set given a symbol name and a value sets an existing constant's value
fails:CApiModule rb_define_module_under creates a new module inside the inner class
fails:CApiModule rb_define_module_under sets the module name
fails:CApiModule rb_define_module_under defines a module for an existing Autoload with an extension
fails:CApiModule rb_define_const given a String name and a value defines a new constant on a module
fails:CApiModule rb_define_const given a String name and a value sets an existing constant's value
fails:CApiModule rb_const_defined returns C non-zero if a constant is defined
fails:CApiModule rb_const_defined returns C non-zero if a constant is defined in Object
fails:CApiModule rb_const_defined_at returns C non-zero if a constant is defined
fails:CApiModule rb_const_defined_at does not search in ancestors for the constant
fails:CApiModule rb_const_defined_at does not search in Object
fails:CApiModule rb_const_get returns a constant defined in the module
fails:CApiModule rb_const_get returns a constant defined at toplevel
fails:CApiModule rb_const_get returns a constant defined in a superclass
fails:CApiModule rb_const_get calls #const_missing if the constant is not defined in the class or ancestors
fails:CApiModule rb_const_get resolves autoload constants in classes
fails:CApiModule rb_const_get resolves autoload constants in Object
fails:CApiModule rb_const_get_from returns a constant defined in the module
fails:CApiModule rb_const_get_from returns a constant defined in a superclass
fails:CApiModule rb_const_get_from calls #const_missing if the constant is not defined in the class or ancestors
fails:CApiModule rb_const_get_from resolves autoload constants
fails:CApiModule rb_const_get_at returns a constant defined in the module
fails:CApiModule rb_const_get_at resolves autoload constants
fails:CApiModule rb_const_get_at calls #const_missing if the constant is not defined in the module
fails:CApiModule rb_define_alias defines an alias for an existing method
fails:CApiModule rb_alias defines an alias for an existing method
fails:CApiModule rb_define_global_function defines a method on Object
fails:CApiModule rb_define_method defines a method on a class
fails:CApiModule rb_define_method defines a method on a module
fails:CApiModule rb_define_module_function defines a module function
fails:CApiModule rb_define_module_function defines a private instance method
fails:CApiModule rb_define_private_method defines a private method on a class
fails:CApiModule rb_define_private_method defines a private method on a module
fails:CApiModule rb_define_protected_method defines a protected method on a class
fails:CApiModule rb_define_protected_method defines a protected method on a module
fails:CApiModule rb_define_singleton_method defines a method on the singleton class
fails:CApiModule rb_undef_method undef'ines a method on a class
fails:CApiModule rb_undef_method does not raise exceptions when passed a missing name
fails:CApiModule rb_undef_method when given a frozen Class raises a RuntimeError when passed a name
fails:CApiModule rb_undef_method when given a frozen Class raises a RuntimeError when passed a missing name
fails:CApiModule rb_undef undef'ines a method on a class
fails:CApiModule rb_class2name returns the module name
11 changes: 11 additions & 0 deletions spec/truffle/tags/optional/capi/mutex_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
fails:C-API Mutex functions rb_mutex_new creates a new mutex
fails:C-API Mutex functions rb_mutex_locked_p returns true if the mutex is locked
fails:C-API Mutex functions rb_mutex_trylock locks the mutex if not locked
fails:C-API Mutex functions rb_mutex_trylock returns false if the mutex is already locked
fails:C-API Mutex functions rb_mutex_lock returns when the mutex isn't locked
fails:C-API Mutex functions rb_mutex_lock throws an exception when already locked in the same thread
fails:C-API Mutex functions rb_mutex_unlock raises an exception when not locked
fails:C-API Mutex functions rb_mutex_unlock unlocks the mutex when locked
fails:C-API Mutex functions rb_mutex_sleep throws an exception when the mutex is not locked
fails:C-API Mutex functions rb_mutex_sleep sleeps when the mutex is locked
fails:C-API Mutex functions rb_mutex_synchronize calls the function while the mutex is locked
69 changes: 69 additions & 0 deletions spec/truffle/tags/optional/capi/numeric_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
fails:CApiNumericSpecs rb_num2int raises a TypeError if passed nil
fails:CApiNumericSpecs rb_num2int converts a Float
fails:CApiNumericSpecs rb_num2int converts a Bignum
fails:CApiNumericSpecs rb_num2int converts a Fixnum
fails:CApiNumericSpecs rb_num2int converts -1 to an signed number
fails:CApiNumericSpecs rb_num2int converts a negative Bignum into an signed number
fails:CApiNumericSpecs rb_num2int raises a RangeError if the value is more than 32bits
fails:CApiNumericSpecs rb_num2int calls #to_int to coerce the value
fails:CApiNumericSpecs rb_num2uint raises a TypeError if passed nil
fails:CApiNumericSpecs rb_num2uint converts a Float
fails:CApiNumericSpecs rb_num2uint converts a Bignum
fails:CApiNumericSpecs rb_num2uint converts a Fixnum
fails:CApiNumericSpecs rb_num2uint converts a negative number to the complement
fails:CApiNumericSpecs rb_num2uint converts a signed int value to the complement
fails:CApiNumericSpecs rb_num2uint raises a RangeError if the value is more than 32bits
fails:CApiNumericSpecs rb_num2uint raises a RangeError if the value is less than 32bits negative
fails:CApiNumericSpecs rb_num2uint raises a RangeError if the value is more than 64bits
fails:CApiNumericSpecs rb_num2uint calls #to_int to coerce the value
fails:CApiNumericSpecs rb_num2long raises a TypeError if passed nil
fails:CApiNumericSpecs rb_num2long converts a Float
fails:CApiNumericSpecs rb_num2long converts a Bignum
fails:CApiNumericSpecs rb_num2long converts a Fixnum
fails:CApiNumericSpecs rb_num2long converts -1 to an signed number
fails:CApiNumericSpecs rb_num2long converts a negative Bignum into an signed number
fails:CApiNumericSpecs rb_num2long raises a RangeError if the value is more than 64bits
fails:CApiNumericSpecs rb_num2long calls #to_int to coerce the value
fails:CApiNumericSpecs rb_int2num raises a TypeError if passed nil
fails:CApiNumericSpecs rb_int2num converts a Float
fails:CApiNumericSpecs rb_int2num raises a RangeError when passed a Bignum
fails:CApiNumericSpecs rb_int2num converts a Fixnum
fails:CApiNumericSpecs rb_int2num converts a negative Fixnum
fails:CApiNumericSpecs rb_num2ulong raises a TypeError if passed nil
fails:CApiNumericSpecs rb_num2ulong converts a Float
fails:CApiNumericSpecs rb_num2ulong converts a Bignum
fails:CApiNumericSpecs rb_num2ulong converts a Fixnum
fails:CApiNumericSpecs rb_num2ulong converts -1 to an unsigned number
fails:CApiNumericSpecs rb_num2ulong converts a negative Bignum into an unsigned number
fails:CApiNumericSpecs rb_num2ulong raises a RangeError if the value is more than 64bits
fails:CApiNumericSpecs rb_num2ulong calls #to_int to coerce the value
fails:CApiNumericSpecs rb_Integer creates a new Integer from a String
fails:CApiNumericSpecs rb_ll2inum creates a new Fixnum from a small signed long long
fails:CApiNumericSpecs rb_int2inum creates a new Fixnum from a long
fails:CApiNumericSpecs rb_num2dbl raises a TypeError if passed nil
fails:CApiNumericSpecs rb_num2dbl raises a TypeError if passed a String
fails:CApiNumericSpecs rb_num2dbl converts a Float
fails:CApiNumericSpecs rb_num2dbl converts a Bignum
fails:CApiNumericSpecs rb_num2dbl converts a Fixnum
fails:CApiNumericSpecs rb_num2dbl calls #to_f to coerce the value
fails:CApiNumericSpecs NUM2CHR returns the first character of a String
fails:CApiNumericSpecs NUM2CHR returns the least significant byte of an Integer
fails:CApiNumericSpecs NUM2CHR returns the least significant byte of a Float converted to an Integer
fails:CApiNumericSpecs NUM2CHR raises a TypeError when passed an empty String
fails:CApiNumericSpecs rb_num_zerodiv raises a RuntimeError
fails:CApiNumericSpecs rb_cmpint returns a Fixnum if passed one
fails:CApiNumericSpecs rb_cmpint uses > to check if the value is greater than 1
fails:CApiNumericSpecs rb_cmpint uses < to check if the value is less than 1
fails:CApiNumericSpecs rb_cmpint returns 0 if < and > are false
fails:CApiNumericSpecs rb_cmpint raises an ArgumentError when passed nil
fails:CApiNumericSpecs rb_num_coerce_bin calls #coerce on the first argument
fails:CApiNumericSpecs rb_num_coerce_bin calls the specified method on the first argument returned by #coerce
fails:CApiNumericSpecs rb_num_coerce_bin raises a TypeError if #coerce does not return an Array
fails:CApiNumericSpecs rb_num_coerce_cmp calls #coerce on the first argument
fails:CApiNumericSpecs rb_num_coerce_cmp calls the specified method on the first argument returned by #coerce
fails:CApiNumericSpecs rb_num_coerce_cmp returns nil if passed nil
fails:CApiNumericSpecs rb_num_coerce_cmp returns nil if #coerce does not return an Array
fails:CApiNumericSpecs rb_num_coerce_relop calls #coerce on the first argument
fails:CApiNumericSpecs rb_num_coerce_relop calls the specified method on the first argument returned by #coerce
fails:CApiNumericSpecs rb_num_coerce_relop raises an ArgumentError if #<op> returns nil
fails:CApiNumericSpecs rb_num_coerce_relop raises an ArgumentError if #coerce does not return an Array
102 changes: 102 additions & 0 deletions spec/truffle/tags/optional/capi/object_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
fails:CApiObject rb_obj_alloc allocates a new uninitialized object
fails:CApiObject rb_obj_dup duplicates an object
fails:CApiObject rb_obj_call_init sends #initialize
fails:CApiObject rb_is_instance_of returns true if an object is an instance
fails:CApiObject rb_is_kind_of returns true if an object is an instance or descendent
fails:CApiObject rb_respond_to returns 1 if respond_to? is true and 0 if respond_to? is false
fails:CApiObject rb_obj_respond_to returns true if respond_to? is true and false if respond_to? is false
fails:CApiObject rb_method_boundp returns true when the given method is bound
fails:CApiObject rb_method_boundp returns false when the given method is not bound
fails:CApiObject rb_to_id returns a symbol representation of the object
fails:CApiObject rb_require requires a ruby file
fails:CApiObject rb_attr_get gets an instance variable
fails:CApiObject rb_obj_instance_variables returns an array with instance variable names as symbols
fails:CApiObject rb_check_convert_type returns the passed object and does not call the converting method if the object is the specified type
fails:CApiObject rb_check_convert_type returns the passed object and does not call the converting method if the object is a subclass of the specified type
fails:CApiObject rb_check_convert_type returns nil if the converting method returns nil
fails:CApiObject rb_check_convert_type raises a TypeError if the converting method returns an object that is not the specified type
fails:CApiObject rb_convert_type returns the passed object and does not call the converting method if the object is the specified type
fails:CApiObject rb_convert_type returns the passed object and does not call the converting method if the object is a subclass of the specified type
fails:CApiObject rb_convert_type raises a TypeError if the converting method returns nil
fails:CApiObject rb_convert_type raises a TypeError if the converting method returns an object that is not the specified type
fails:CApiObject rb_check_array_type returns the argument if it's an Array
fails:CApiObject rb_check_array_type returns the argument if it's a kind of Array
fails:CApiObject rb_check_array_type returns nil when the argument does not respond to #to_ary
fails:CApiObject rb_check_array_type sends #to_ary to the argument and returns the result if it's nil
fails:CApiObject rb_check_array_type sends #to_ary to the argument and returns the result if it's an Array
fails:CApiObject rb_check_array_type sends #to_ary to the argument and returns the result if it's a kind of Array
fails:CApiObject rb_check_array_type sends #to_ary to the argument and raises TypeError if it's not a kind of Array
fails:CApiObject rb_check_array_type does not rescue exceptions raised by #to_ary
fails:CApiObject rb_check_string_type returns the argument if it's a String
fails:CApiObject rb_check_string_type returns the argument if it's a kind of String
fails:CApiObject rb_check_string_type returns nil when the argument does not respond to #to_str
fails:CApiObject rb_check_string_type sends #to_str to the argument and returns the result if it's nil
fails:CApiObject rb_check_string_type sends #to_str to the argument and returns the result if it's a String
fails:CApiObject rb_check_string_type sends #to_str to the argument and returns the result if it's a kind of String
fails:CApiObject rb_check_string_type sends #to_str to the argument and raises TypeError if it's not a kind of String
fails:CApiObject rb_check_string_type does not rescue exceptions raised by #to_str
fails:CApiObject rb_check_to_integer returns the object when passed a Fixnum
fails:CApiObject rb_check_to_integer returns the object when passed a Bignum
fails:CApiObject rb_check_to_integer calls the converting method and returns a Fixnum value
fails:CApiObject rb_check_to_integer calls the converting method and returns a Bignum value
fails:CApiObject rb_check_to_integer returns nil when the converting method returns nil
fails:CApiObject rb_check_to_integer returns nil when the converting method does not return an Integer
fails:CApiObject rb_inspect returns a string with the inspect representation
fails:CApiObject rb_class_of returns the class of an object
fails:CApiObject rb_obj_classname returns the class name of an object
fails:CApiObject rb_type returns the type constant for the object
fails:CApiObject rb_type_p returns whether object is of the given type
fails:CApiObject BUILTIN_TYPE returns the type constant for the object
fails:CApiObject RTEST returns C false if passed Qfalse
fails:CApiObject RTEST returns C false if passed Qnil
fails:CApiObject RTEST returns C true if passed Qtrue
fails:CApiObject RTEST returns C true if passed a Symbol
fails:CApiObject RTEST returns C true if passed an Object
fails:CApiObject rb_special_const_p returns true if passed Qfalse
fails:CApiObject rb_special_const_p returns true if passed Qtrue
fails:CApiObject rb_special_const_p returns true if passed Qnil
fails:CApiObject rb_special_const_p returns true if passed a Symbol
fails:CApiObject rb_special_const_p returns true if passed a Fixnum
fails:CApiObject rb_special_const_p returns false if passed an Object
fails:CApiObject rb_extend_object adds the module's instance methods to the object
fails:CApiObject OBJ_TAINT taints the object
fails:CApiObject OBJ_TAINTED returns C true if the object is tainted
fails:CApiObject OBJ_TAINTED returns C false if the object is not tainted
fails:CApiObject OBJ_INFECT does not taint the first argument if the second argument is not tainted
fails:CApiObject OBJ_INFECT taints the first argument if the second argument is tainted
fails:CApiObject OBJ_INFECT does not untrust the first argument if the second argument is trusted
fails:CApiObject OBJ_INFECT untrusts the first argument if the second argument is untrusted
fails:CApiObject OBJ_INFECT propagates both taint and distrust
fails:CApiObject rb_obj_freeze freezes the object passed to it
fails:CApiObject rb_obj_instance_eval evaluates the block in the object context, that includes private methods
fails:CApiObject rb_obj_frozen_p returns true if object passed to it is frozen
fails:CApiObject rb_obj_frozen_p returns false if object passed to it is not frozen
fails:CApiObject rb_obj_taint marks the object passed as tainted
fails:CApiObject rb_obj_taint raises a RuntimeError if the object passed is frozen
fails:CApiObject rb_check_frozen raises a RuntimeError if the obj is frozen
fails:CApiObject rb_check_frozen does nothing when object isn't frozen
fails:CApiObject rb_any_to_s converts obj to string
fails:CApiObject rb_to_int returns self when called on an Integer
fails:CApiObject rb_to_int returns self when called on a Bignum
fails:CApiObject rb_to_int calls #to_int to convert and object to an integer
fails:CApiObject rb_to_int converts a Float to an Integer by truncation
fails:CApiObject rb_to_int raises a TypeError if #to_int does not return an Integer
fails:CApiObject rb_to_int raises a TypeError if called with nil
fails:CApiObject rb_to_int raises a TypeError if called with true
fails:CApiObject rb_to_int raises a TypeError if called with false
fails:CApiObject rb_to_int raises a TypeError if called with a String
fails:CApiObject rb_equal returns true if the arguments are the same exact object
fails:CApiObject rb_equal calls == to check equality and coerces to true/false
fails:CApiObject rb_class_inherited_p returns true if mod equals arg
fails:CApiObject rb_class_inherited_p returns true if mod is a subclass of arg
fails:CApiObject rb_class_inherited_p returns nil if mod is not a subclass of arg
fails:CApiObject rb_class_inherited_p raises a TypeError if arg is no class or module
fails:CApiObject instance variable access rb_iv_get returns the instance variable on an object
fails:CApiObject instance variable access rb_iv_get returns nil if the instance variable has not been initialized
fails:CApiObject instance variable access rb_iv_set sets and returns the instance variable on an object
fails:CApiObject instance variable access rb_iv_set sets and returns the instance variable with a bare name
fails:CApiObject instance variable access rb_ivar_get returns the instance variable on an object
fails:CApiObject instance variable access rb_ivar_get returns nil if the instance variable has not been initialized
fails:CApiObject instance variable access rb_ivar_set sets and returns the instance variable on an object
fails:CApiObject instance variable access rb_ivar_defined returns true if the instance variable is defined
fails:CApiObject instance variable access rb_ivar_defined returns false if the instance variable is not defined
4 changes: 4 additions & 0 deletions spec/truffle/tags/optional/capi/range_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
fails:C-API Range function rb_range_new constructs a range using the given start and end
fails:C-API Range function rb_range_new includes the end object when the third parameter is omitted or false
fails:C-API Range function rb_range_new raises an ArgumentError when the given start and end can't be compared by using #<=>
fails:C-API Range function rb_range_values stores the range properties
7 changes: 7 additions & 0 deletions spec/truffle/tags/optional/capi/rational_tags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
fails:CApiRationalSpecs rb_Rational creates a new Rational with numerator and denominator
fails:CApiRationalSpecs rb_Rational2 creates a new Rational with numerator and denominator
fails:CApiRationalSpecs rb_Rational1 creates a new Rational with numerator and denominator of 1
fails:CApiRationalSpecs rb_rational_new creates a normalized Rational
fails:CApiRationalSpecs rb_rational_new2 creates a normalized Rational
fails:CApiRationalSpecs rb_rational_num returns the numerator of a Rational
fails:CApiRationalSpecs rb_rational_den returns the denominator of a Rational
Loading

0 comments on commit e17bcea

Please sign in to comment.