pascal.taie.AbstractWorldBuilder Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of tai-e Show documentation
Show all versions of tai-e Show documentation
An easy-to-learn/use static analysis framework for Java
The newest version!
/*
* Tai-e: A Static Analysis Framework for Java
*
* Copyright (C) 2022 Tian Tan
* Copyright (C) 2022 Yue Li
*
* This file is part of Tai-e.
*
* Tai-e is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License
* as published by the Free Software Foundation, either version 3
* of the License, or (at your option) any later version.
*
* Tai-e is distributed in the hope that it will be useful,but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General
* Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with Tai-e. If not, see .
*/
package pascal.taie;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import pascal.taie.config.Options;
import pascal.taie.language.classes.ClassHierarchy;
import pascal.taie.language.natives.DefaultNativeModel;
import pascal.taie.language.natives.EmptyNativeModel;
import pascal.taie.language.natives.NativeModel;
import pascal.taie.language.type.TypeSystem;
import pascal.taie.util.ClassNameExtractor;
import pascal.taie.util.collection.Streams;
import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;
import java.util.stream.Stream;
/**
* Common functionality for {@link WorldBuilder} implementations.
*/
public abstract class AbstractWorldBuilder implements WorldBuilder {
private static final Logger logger = LogManager.getLogger(AbstractWorldBuilder.class);
protected static final String JREs = "java-benchmarks/JREs";
protected static final List implicitEntries = List.of(
"",
"(java.lang.ThreadGroup,java.lang.Runnable)>",
"(java.lang.ThreadGroup,java.lang.String)>",
"",
"()>",
"(java.lang.ThreadGroup,java.lang.String)>",
"",
"()>",
"",
"",
"",
"",
"(java.lang.Exception)>"
);
protected static String getClassPath(Options options) {
if (options.isPrependJVM()) {
return Streams.concat(
options.getAppClassPath().stream(),
options.getClassPath().stream())
.collect(Collectors.joining(File.pathSeparator));
} else { // when prependJVM is not set, we manually specify JRE jars
// check existence of JREs
File jreDir = new File(JREs);
if (!jreDir.exists()) {
throw new RuntimeException("""
Failed to locate Java library.
Please clone submodule 'java-benchmarks' by command:
'git submodule update --init --recursive' (if you are running Tai-e)
or 'git clone https://github.com/pascal-lab/java-benchmarks' (if you are using Tai-e as a dependency),
then put it in Tai-e's working directory.""");
}
String jrePath = String.format("%s/jre1.%d",
JREs, options.getJavaVersion());
try (Stream paths = Files.walk(Path.of(jrePath))) {
return Streams.concat(
paths.map(Path::toString).filter(p -> p.endsWith(".jar")),
options.getAppClassPath().stream(),
options.getClassPath().stream())
.collect(Collectors.joining(File.pathSeparator));
} catch (IOException e) {
throw new RuntimeException("Analysis on Java " +
options.getJavaVersion() + " library is not supported yet", e);
}
}
}
protected static NativeModel getNativeModel(
TypeSystem typeSystem, ClassHierarchy hierarchy, Options options) {
return options.enableNativeModel() ?
new DefaultNativeModel(typeSystem, hierarchy, options.getJavaVersion()) :
new EmptyNativeModel();
}
/**
* Obtains all input classes specified in {@code options}.
*/
protected static List getInputClasses(Options options) {
List classes = new ArrayList<>();
// process --input-classes
options.getInputClasses().forEach(value -> {
if (value.endsWith(".txt")) {
// value is a path to a file that contains class names
try (Stream lines = Files.lines(Path.of(value))) {
lines.forEach(classes::add);
} catch (IOException e) {
logger.warn("Failed to read input class file {} due to {}",
value, e);
}
} else {
// value is a class name
classes.add(value);
}
});
// process --app-class-path
for (String path : options.getAppClassPath()) {
classes.addAll(ClassNameExtractor.extract(path));
}
return classes;
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy