Skip to content

Commit 1641294

Browse files
authored
Merge branch 'main' into feat/reduce-module-environment-lookup
2 parents 3a26b0c + 3cb5ead commit 1641294

20 files changed

+285
-67
lines changed

src/org/rascalmpl/compiler/lang/rascalcore/check/Import.rsc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -442,7 +442,7 @@ ModuleStatus doSaveModule(set[str] component, map[str,set[str]] m_imports, map[s
442442
m1.specializedFacts = (key : tm.specializedFacts[key] | key <- tm.specializedFacts, isContainedInComponentScopes(key), any(fms <- filteredModuleScopes, isContainedIn(key, fms)));
443443
m1.facts += m1.specializedFacts;
444444
445-
m1.messages = sort( { msg | msg <- tm.messages, msg.at.path == mscope.path || msg is error}, bool(Message a, Message b){ return a.at.begin.line < b.at.begin.line; });
445+
m1.messages = [ msg | msg <- tm.messages, msg.at.path == mscope.path || msg is error ];
446446
ms.messages[qualifiedModuleName] = toSet(m1.messages);
447447
448448
filteredModuleScopePaths = {ml.path |loc ml <- filteredModuleScopes};

src/org/rascalmpl/dap/RascalDebugAdapter.java

Lines changed: 18 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@
4747
import org.rascalmpl.debug.DebugHandler;
4848
import org.rascalmpl.debug.DebugMessageFactory;
4949
import org.rascalmpl.debug.IRascalFrame;
50+
import org.rascalmpl.exceptions.RuntimeExceptionFactory;
5051
import org.rascalmpl.exceptions.Throw;
5152
import org.rascalmpl.ideservices.IDEServices;
5253
import org.rascalmpl.interpreter.Evaluator;
@@ -64,6 +65,7 @@
6465
import org.rascalmpl.values.parsetrees.ProductionAdapter;
6566
import org.rascalmpl.values.parsetrees.TreeAdapter;
6667

68+
import io.usethesource.vallang.IConstructor;
6769
import io.usethesource.vallang.IList;
6870
import io.usethesource.vallang.INode;
6971
import io.usethesource.vallang.ISourceLocation;
@@ -151,25 +153,37 @@ public CompletableFuture<Capabilities> initialize(InitializeRequestArguments arg
151153
public CompletableFuture<SetBreakpointsResponse> setBreakpoints(SetBreakpointsArguments args) {
152154
return CompletableFuture.supplyAsync(() -> {
153155
SetBreakpointsResponse response = new SetBreakpointsResponse();
156+
response.setBreakpoints(new Breakpoint[0]);
154157
String extension = args.getSource().getName().substring(args.getSource().getName().lastIndexOf('.') + 1);
155158
if (!extension.equals("rsc")) {
156-
response.setBreakpoints(new Breakpoint[0]);
157159
return response;
158160
}
159161
ISourceLocation loc = getLocationFromPath(args.getSource().getPath());
160162
if(loc == null){
161-
response.setBreakpoints(new Breakpoint[0]);
162163
return response;
163164
}
164165

166+
var reg = URIResolverRegistry.getInstance();
167+
if (!reg.exists(loc)) {
168+
return response;
169+
}
170+
171+
var cannotSetMsg = String.format("Cannot set breakpoint%s", args.getBreakpoints().length > 1 ? "s" : "");
172+
165173
ITree parseTree;
166174
try {
167175
parseTree = Reflective.parseModuleWithSpaces(loc);
168176
} catch (Throw t) {
169-
services.warning("Cannot set breakpoint(s): " + t.getMessage(), loc);
177+
if (t.getException().getType().isConstructor()) {
178+
var e = (IConstructor) t.getException();
179+
var et = e.getConstructorType();
180+
if (et != RuntimeExceptionFactory.IO) {
181+
services.warning(String.format("%s: %s", cannotSetMsg, t.getMessage()), loc);
182+
}
183+
}
170184
return response;
171185
} catch (ParseError e) {
172-
services.warning("Cannot set breakpoint(s): " + e.toString(), loc);
186+
services.warning(String.format("%s: %s", cannotSetMsg, e.getMessage()), loc);
173187
return response;
174188
}
175189
breakpointsCollection.clearBreakpointsOfFile(loc.getPath());

src/org/rascalmpl/dap/variable/RascalVariable.java

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
package org.rascalmpl.dap.variable;
2828

2929
import org.rascalmpl.ideservices.IDEServices;
30+
import org.rascalmpl.values.RascalValueFactory;
3031

3132
import io.usethesource.vallang.IValue;
3233
import io.usethesource.vallang.type.Type;
@@ -85,7 +86,7 @@ public boolean hasSubFields(){
8586
return false;
8687
}
8788

88-
return type.isList() || type.isMap() || type.isSet() || type.isAliased() || type.isNode() || type.isConstructor() || type.isRelation() || type.isTuple() || type.isDateTime();
89+
return type.isList() || type.isMap() || type.isSet() || type.isAliased() || type.isNode() || type.isConstructor() || type.isRelation() || type.isTuple() || type.isDateTime() || (type.isExternalType() && type.equals(RascalValueFactory.Tree));
8990
}
9091

9192
public int getNamedVariables() {

src/org/rascalmpl/dap/variable/RascalVariableUtils.java

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,8 @@
3232
import org.rascalmpl.dap.RascalDebugAdapter;
3333
import org.rascalmpl.ideservices.IDEServices;
3434
import org.rascalmpl.interpreter.utils.LimitedResultWriter;
35+
import org.rascalmpl.values.parsetrees.ITree;
36+
import org.rascalmpl.values.parsetrees.TreeAdapter;
3537

3638
import io.usethesource.vallang.IValue;
3739
import io.usethesource.vallang.io.StandardTextWriter;
@@ -45,6 +47,9 @@ public static String getDisplayString(IValue value, IDEServices services) {
4547
if(value == null) {
4648
return "null";
4749
}
50+
if (value instanceof ITree) {
51+
return "(" + value.getType() + ")`" + TreeAdapter.yield((ITree)value) + "`";
52+
}
4853
Writer w = new LimitedResultWriter(MAX_SIZE_STRING_NAME);
4954
try {
5055
new StandardTextWriter(true, 2).write(value, w);

src/org/rascalmpl/dap/variable/VariableSubElementsCounterVisitor.java

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,9 @@
2626
*/
2727
package org.rascalmpl.dap.variable;
2828

29+
import org.rascalmpl.types.NonTerminalType;
30+
import org.rascalmpl.values.parsetrees.ITree;
31+
2932
import io.usethesource.vallang.*;
3033
import io.usethesource.vallang.visitors.IValueVisitor;
3134

@@ -96,6 +99,10 @@ public VariableSubElementsCounter visitBoolean(IBool boolValue) throws RuntimeEx
9699

97100
@Override
98101
public VariableSubElementsCounter visitExternal(IExternalValue externalValue) throws RuntimeException {
102+
if (externalValue.getType() instanceof NonTerminalType) {
103+
return new VariableSubElementsCounter(0, ((ITree)externalValue).arity());
104+
105+
}
99106
return new VariableSubElementsCounter(0, 0);
100107
}
101108

src/org/rascalmpl/library/Messages.java

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -44,15 +44,19 @@ public class Messages {
4444
private static final io.usethesource.vallang.type.Type Message_error = tf.constructor(ts, Message, "error", tf.stringType(), "msg", tf.sourceLocationType(), "at");
4545

4646
public static IConstructor info(String message, ISourceLocation loc) {
47-
return vf.constructor(Message_info, vf.string(message), loc);
47+
return message(Message_info, message, loc);
4848
}
4949

5050
public static IConstructor warning(String message, ISourceLocation loc) {
51-
return vf.constructor(Message_warning, vf.string(message), loc);
51+
return message(Message_warning, message, loc);
5252
}
5353

5454
public static IConstructor error(String message, ISourceLocation loc) {
55-
return vf.constructor(Message_error, vf.string(message), loc);
55+
return message(Message_error, message, loc);
56+
}
57+
58+
private static IConstructor message(io.usethesource.vallang.type.Type type, String message, ISourceLocation loc) {
59+
return vf.constructor(type, vf.string(message), loc);
5660
}
5761

5862
public static boolean isError(IValue v) {

src/org/rascalmpl/library/util/PathConfig.java

Lines changed: 10 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@
2929
import org.rascalmpl.uri.jar.JarURIResolver;
3030
import org.rascalmpl.util.maven.Artifact;
3131
import org.rascalmpl.util.maven.ArtifactCoordinate;
32+
import org.rascalmpl.util.maven.MavenMessages;
3233
import org.rascalmpl.util.maven.MavenParser;
3334
import org.rascalmpl.util.maven.ModelResolutionError;
3435
import org.rascalmpl.util.maven.Scope;
@@ -603,12 +604,13 @@ private static void addArtifactToPathConfig(Artifact art, ISourceLocation manife
603604
ISourceLocation projectLoc = URIUtil.correctLocation("project", art.getCoordinate().getArtifactId(), "");
604605
if (reg.exists(projectLoc)) {
605606
if (mode == RascalConfigMode.INTERPRETER) {
606-
messages.append(Messages.info("Redirected: " + art.getCoordinate() + " to: " + projectLoc, getPomXmlLocation(manifestRoot)));
607+
// Note that this is not the main project pom so art.getOrigin() should not be null
608+
messages.append(MavenMessages.info("Redirected: " + art.getCoordinate() + " to: " + projectLoc, art));
607609
}
608610
addProjectAndItsDependencies(mode, srcs, libs, messages, projectLoc);
609611
}
610612
else {
611-
messages.append(Messages.error("Declared dependency does not exist: " + art.getCoordinate(), getPomXmlLocation(manifestRoot)));
613+
messages.append(MavenMessages.error("Declared dependency does not exist: " + art.getCoordinate(), art));
612614
}
613615
return;
614616
}
@@ -625,7 +627,7 @@ private static void addArtifactToPathConfig(Artifact art, ISourceLocation manife
625627
return;
626628
}
627629
if (libProjectName.equals("rascal-lsp")) {
628-
checkLSPVersionsMatch(manifestRoot, messages, dep);
630+
checkLSPVersionsMatch(manifestRoot, messages, dep, art);
629631
// we'll be adding the rascal-lsp by hand later
630632
// so we ignore the rascal-lsp dependency
631633
return;
@@ -636,7 +638,7 @@ private static void addArtifactToPathConfig(Artifact art, ISourceLocation manife
636638
// The project we depend on is available in the current workspace.
637639
// so we configure for using the current state of that project.
638640
if (mode == RascalConfigMode.INTERPRETER) {
639-
messages.append(Messages.info("Redirected: " + art.getCoordinate() + " to: " + projectLoc, getPomXmlLocation(manifestRoot)));
641+
messages.append(MavenMessages.info("Redirected: " + art.getCoordinate() + " to: " + projectLoc, art));
640642
}
641643
addProjectAndItsDependencies(mode, srcs, libs, messages, projectLoc);
642644
}
@@ -648,7 +650,7 @@ private static void addArtifactToPathConfig(Artifact art, ISourceLocation manife
648650
}
649651
}
650652
} catch (URISyntaxException e) {
651-
messages.append(Messages.error("Could not convert " + art.getCoordinate() + " to a loc: " + e, manifestRoot));
653+
messages.append(MavenMessages.error("Could not convert " + art.getCoordinate() + " to a loc: " + e, art));
652654
}
653655
}
654656

@@ -659,19 +661,19 @@ private static void addProjectAndItsDependencies(RascalConfigMode mode, IListWri
659661
buildNormalProjectConfig(projectLoc, mode, childMavenClasspath, false, srcs, libs, messages);
660662
}
661663

662-
private static void checkLSPVersionsMatch(ISourceLocation manifestRoot, IListWriter messages, ISourceLocation dep) throws IOException {
664+
private static void checkLSPVersionsMatch(ISourceLocation manifestRoot, IListWriter messages, ISourceLocation jarLocation, Artifact artifact) throws IOException {
663665
// Rascal LSP is special because the VScode extension pre-loads it into the parametric DSL VM.
664666
// If the version is different, then the debugger may point to the wrong code, and also the Rascal
665667
// IDE features like "jump-to-definition" could be off.
666668
try {
667669
var loadedRascalLsp = resolveProjectOnClasspath("rascal-lsp");
668670
var reg = URIResolverRegistry.getInstance();
669-
try (InputStream in = reg.getInputStream(loadedRascalLsp); InputStream in2 = reg.getInputStream(dep)) {
671+
try (InputStream in = reg.getInputStream(loadedRascalLsp); InputStream in2 = reg.getInputStream(jarLocation)) {
670672
var version = new Manifest(in).getMainAttributes().getValue("Specification-Version");
671673
var otherVersion = new Manifest(in2).getMainAttributes().getValue("Specification-Version");
672674

673675
if (version != null && !version.equals(otherVersion)) {
674-
messages.append(Messages.warning("Pom.xml dependency on rascal-lsp has version " + otherVersion + " while the effective version in the VScode extension is " + version + ". This can have funny effects in the IDE while debugging or code browsing, for that reason we've replaced it with the effective one, please update your pom.xml.", getPomXmlLocation(manifestRoot)));
676+
messages.append(MavenMessages.warning("Pom.xml dependency on rascal-lsp has version " + otherVersion + " while the effective version in the VScode extension is " + version + ". This can have funny effects in the IDE while debugging or code browsing, for that reason we've replaced it with the effective one, please update your pom.xml.", artifact));
675677
}
676678
}
677679
}

src/org/rascalmpl/library/util/Webserver.java

Lines changed: 19 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,9 @@
11
package org.rascalmpl.library.util;
22

3+
import java.io.BufferedInputStream;
34
import java.io.ByteArrayInputStream;
45
import java.io.ByteArrayOutputStream;
6+
import java.io.CharArrayWriter;
57
import java.io.FileNotFoundException;
68
import java.io.FileReader;
79
import java.io.IOException;
@@ -12,7 +14,10 @@
1214
import java.io.StringReader;
1315
import java.net.URI;
1416
import java.net.URISyntaxException;
17+
import java.nio.ByteBuffer;
18+
import java.nio.CharBuffer;
1519
import java.nio.charset.Charset;
20+
import java.nio.charset.StandardCharsets;
1621
import java.util.HashMap;
1722
import java.util.Map;
1823
import java.util.Map.Entry;
@@ -322,10 +327,20 @@ private Response translateTextResponse(Method method, IConstructor cons) {
322327
}
323328

324329
private InputStream toInputStream(IString data, Charset encoding) throws IOException {
325-
return new ReaderInputStream.Builder()
326-
.setReader(data.asReader())
327-
.setCharset(encoding)
328-
.get();
330+
// get the characters on the line with the least amount of copying
331+
CharArrayWriter w = new CharArrayWriter(data.length());
332+
333+
// that's the single copy
334+
data.write(w);
335+
336+
// this just wraps the array from the CharArrayWriter
337+
ByteBuffer byteBuffer = StandardCharsets
338+
.UTF_8.newEncoder()
339+
.encode(CharBuffer.wrap(w.toCharArray()));
340+
341+
// here we stream directly from the encoded bytebuffer's result, but we buffer it at the
342+
// buffer size that NanoHTTPD likes
343+
return new BufferedInputStream(new ByteArrayInputStream(byteBuffer.array(), 0, byteBuffer.limit()), 32 * 1024);
329344
}
330345

331346
private void addHeaders(Response response, IMap header) {

src/org/rascalmpl/repl/http/REPLContentServer.java

Lines changed: 23 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -26,14 +26,23 @@
2626
*/
2727
package org.rascalmpl.repl.http;
2828

29+
import java.io.BufferedInputStream;
2930
import java.io.ByteArrayInputStream;
3031
import java.io.ByteArrayOutputStream;
32+
import java.io.CharArrayWriter;
3133
import java.io.IOException;
3234
import java.io.InputStream;
3335
import java.io.OutputStreamWriter;
36+
import java.io.PipedReader;
37+
import java.io.PipedWriter;
3438
import java.io.PrintWriter;
3539
import java.io.StringWriter;
40+
import java.io.UncheckedIOException;
41+
import java.nio.ByteBuffer;
42+
import java.nio.CharBuffer;
3643
import java.nio.charset.Charset;
44+
import java.nio.charset.CharsetEncoder;
45+
import java.nio.charset.StandardCharsets;
3746
import java.util.HashMap;
3847
import java.util.Map;
3948
import java.util.Map.Entry;
@@ -244,10 +253,20 @@ private static Response translateTextResponse(Method method, IConstructor cons)
244253
}
245254

246255
private static InputStream toInputStream(IString data, Charset encoding) throws IOException {
247-
return new ReaderInputStream.Builder()
248-
.setReader(data.asReader())
249-
.setCharset(encoding)
250-
.get();
256+
// get the characters on the line with the least amount of copying
257+
CharArrayWriter w = new CharArrayWriter(data.length());
258+
259+
// that's the single copy
260+
data.write(w);
261+
262+
// this just wraps the array from the CharArrayWriter
263+
ByteBuffer byteBuffer = StandardCharsets
264+
.UTF_8.newEncoder()
265+
.encode(CharBuffer.wrap(w.toCharArray()));
266+
267+
// here we stream directly from the encoded bytebuffer's result, but we buffer it at the
268+
// buffer size that NanoHTTPD likes
269+
return new BufferedInputStream(new ByteArrayInputStream(byteBuffer.array(), 0, byteBuffer.limit()), 32 * 1024);
251270
}
252271

253272
private static void addHeaders(Response response, IMap header) {

src/org/rascalmpl/util/Func.java

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
package org.rascalmpl.util;
2+
3+
public interface Func<T, R, E extends Exception> {
4+
R apply(T param) throws E;
5+
}

0 commit comments

Comments
 (0)