Skip to content
Permalink

Comparing changes

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

Open a pull request

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

Commits on Mar 2, 2015

  1. Copy the full SHA
    f47369d View commit details
  2. [Truffle] Fix require_relative from main script.

    * Main script path is not a full path, contrary to all other files.
      (On purpose, so it appears as a relative path in bactraces).
    eregon committed Mar 2, 2015
    Copy the full SHA
    1c6189c View commit details
  3. [Truffle] Simplify FeatureManager.require by only allowing a single p…

    …ath.
    
    * Refactor to FeatureManager.getSourcePath instead of if(main script).
    eregon committed Mar 2, 2015
    Copy the full SHA
    4897cd6 View commit details
Original file line number Diff line number Diff line change
@@ -172,6 +172,8 @@ public Object execute(final TranslatorDriver.ParserContext parserContext, final
source = Source.fromBytes(bytes, inputFile, new BytesDecoder.UTF8BytesDecoder());
}

truffleContext.getFeatureManager().setMainScriptSource(source);

truffleContext.load(source, null, new NodeWrapper() {
@Override
public RubyNode wrap(RubyNode node) {
Original file line number Diff line number Diff line change
@@ -18,6 +18,7 @@
import com.oracle.truffle.api.dsl.Specialization;
import com.oracle.truffle.api.frame.*;
import com.oracle.truffle.api.nodes.UnexpectedResultException;
import com.oracle.truffle.api.source.Source;
import com.oracle.truffle.api.source.SourceSection;
import com.oracle.truffle.api.utilities.ConditionProfile;

@@ -52,6 +53,7 @@
import org.jruby.truffle.runtime.hash.HashOperations;
import org.jruby.truffle.runtime.hash.KeyValue;
import org.jruby.truffle.runtime.methods.InternalMethod;
import org.jruby.truffle.runtime.subsystems.FeatureManager;
import org.jruby.truffle.runtime.subsystems.ThreadManager.BlockingActionWithoutGlobalLock;
import org.jruby.util.ByteList;
import org.jruby.util.cli.Options;
@@ -1594,7 +1596,7 @@ public boolean require(RubyString feature) {
}

try {
getContext().getFeatureManager().require(null, feature.toString(), this);
getContext().getFeatureManager().require(feature.toString(), this);
} catch (IOException e) {
throw new RuntimeException(e);
}
@@ -1618,11 +1620,27 @@ public RequireRelativeNode(RequireRelativeNode prev) {
public boolean require(RubyString feature) {
notDesignedForCompilation();

final String sourcePath = Truffle.getRuntime().getCallerFrame().getCallNode().getEncapsulatingSourceSection().getSource().getPath();
final String directoryPath = new File(sourcePath).getParent();
final FeatureManager featureManager = getContext().getFeatureManager();

final String featureString = feature.toString();
final String featurePath;

if (featureManager.isAbsolutePath(featureString)) {
featurePath = featureString;
} else {
final Source source = Truffle.getRuntime().getCallerFrame().getCallNode().getEncapsulatingSourceSection().getSource();
final String sourcePath = featureManager.getSourcePath(source);

if (sourcePath == null) {
CompilerDirectives.transferToInterpreter();
throw new RaiseException(getContext().getCoreLibrary().loadError("cannot infer basepath", this));
}

featurePath = new File(new File(sourcePath).getParent(), featureString).toString();
}

try {
getContext().getFeatureManager().require(directoryPath, feature.toString(), this);
featureManager.require(featurePath, this);
} catch (IOException e) {
throw new RuntimeException(e);
}
Original file line number Diff line number Diff line change
@@ -161,11 +161,11 @@ public void loadFile(String fileName, Node currentNode) {
}
}

private void loadFileAbsolute(String fileName, Node currentNode) {
final byte[] bytes = FileUtils.readAllBytesInterruptedly(this, fileName);
private void loadFileAbsolute(String path, Node currentNode) {
final byte[] bytes = FileUtils.readAllBytesInterruptedly(this, path);

// Assume UTF-8 for the moment
final Source source = Source.fromBytes(bytes, fileName, new BytesDecoder.UTF8BytesDecoder());
final Source source = Source.fromBytes(bytes, path, new BytesDecoder.UTF8BytesDecoder());

load(source, currentNode, NodeWrapper.IDENTITY);
}
Original file line number Diff line number Diff line change
@@ -10,6 +10,8 @@
package org.jruby.truffle.runtime.subsystems;

import com.oracle.truffle.api.nodes.Node;
import com.oracle.truffle.api.source.Source;

import org.jruby.truffle.nodes.RubyNode;
import org.jruby.truffle.runtime.LexicalScope;
import org.jruby.truffle.runtime.ModuleOperations;
@@ -34,18 +36,24 @@ public class FeatureManager {

private final RubyContext context;

private Source mainScriptSource = null;
private String mainScriptFullPath = null;

public FeatureManager(RubyContext context) {
this.context = context;
}

public boolean require(String path, String feature, Node currentNode) throws IOException {
public boolean require(String feature, Node currentNode) throws IOException {
final RubyConstant dataConstantBefore = ModuleOperations.lookupConstant(context, LexicalScope.NONE, context.getCoreLibrary().getObjectClass(), "DATA");

try {
if (path != null) {
if (requireInPath(path, feature, currentNode)) {
if (isAbsolutePath(feature)) {
// Try as a full path

if (requireInPath(null, feature, currentNode)) {
return true;
}

} else {
// Some features are handled specially

@@ -59,20 +67,14 @@ public boolean require(String path, String feature, Node currentNode) throws IOE
return true;
}

if (new File(feature).isAbsolute()) {
// Try as a full path
if (requireInPath(null, feature, currentNode)) {
// Try each load path in turn

for (Object pathObject : context.getCoreLibrary().getLoadPath().slowToArray()) {
final String loadPath = pathObject.toString();

if (requireInPath(loadPath, feature, currentNode)) {
return true;
}
} else {
// Try each load path in turn
for (Object pathObject : context.getCoreLibrary().getLoadPath().slowToArray()) {
final String loadPath = pathObject.toString();

if (requireInPath(loadPath, feature, currentNode)) {
return true;
}
}
}
}

@@ -100,6 +102,10 @@ private boolean requireInPath(String path, String feature, Node currentNode) thr
return false;
}

public boolean isAbsolutePath(String path) {
return path.startsWith("uri:classloader:") || path.startsWith("core:") || new File(path).isAbsolute();
}

private boolean requireFile(String path, Node currentNode) throws IOException {
// We expect '/' in various classpath URLs, so normalize Windows file paths to use '/'
path = path.replace('\\', '/');
@@ -170,4 +176,19 @@ else if (path.startsWith("core:/")) {
return true;
}

public void setMainScriptSource(Source source) {
this.mainScriptSource = source;
if (!source.getPath().equals("-e")) {
this.mainScriptFullPath = RubyFile.expandPath(context, source.getPath());
}
}

public String getSourcePath(Source source) {
if (source == mainScriptSource) {
return mainScriptFullPath;
} else {
return source.getPath();
}
}

}