use of aQute.bnd.service.classparser.ClassParser in project bnd by bndtools.
the class Analyzer method analyze.
/**
* Calculates the data structures for generating a manifest.
*
* @throws IOException
*/
public void analyze() throws Exception {
if (!analyzed) {
analyzed = true;
uses.clear();
apiUses.clear();
classspace.clear();
classpathExports.clear();
contracts.clear();
packagesVisited.clear();
// Parse all the class in the
// the jar according to the OSGi bcp
analyzeBundleClasspath();
for (Jar current : getClasspath()) {
getManifestInfoFromClasspath(current, classpathExports, contracts);
Manifest m = current.getManifest();
if (m == null)
for (String dir : current.getDirectories().keySet()) {
learnPackage(current, "", getPackageRef(dir), classpathExports);
}
}
// Handle the bundle activator
String s = getProperty(BUNDLE_ACTIVATOR);
if (s != null && !s.isEmpty()) {
activator = getTypeRefFromFQN(s);
referTo(activator);
logger.debug("activator {} {}", s, activator);
}
// Conditional packages
doConditionalPackages();
// Execute any plugins
// TODO handle better reanalyze
doPlugins();
//
for (Clazz c : classspace.values()) {
ees.add(c.getFormat());
}
if (since(About._2_3)) {
try (ClassDataCollectors cds = new ClassDataCollectors(this)) {
List<ClassParser> parsers = getPlugins(ClassParser.class);
for (ClassParser cp : parsers) {
cds.add(cp.getClassDataCollector(this));
}
//
// built ins
//
cds.add(annotationHeaders = new AnnotationHeaders(this));
for (Clazz c : classspace.values()) {
cds.parse(c);
}
}
}
referred.keySet().removeAll(contained.keySet());
//
// EXPORTS
//
{
Set<Instruction> unused = Create.set();
Instructions filter = new Instructions(getExportPackage());
filter.append(getExportContents());
exports = filter(filter, contained, unused);
if (!unused.isEmpty()) {
warning("Unused " + Constants.EXPORT_PACKAGE + " instructions: %s ", unused).header(Constants.EXPORT_PACKAGE).context(unused.iterator().next().input);
}
// See what information we can find to augment the
// exports. I.e. look on the classpath
augmentExports(exports);
}
//
// IMPORTS
// Imports MUST come after exports because we use information from
// the exports
//
{
// Add all exports that do not have an -noimport: directive
// to the imports.
Packages referredAndExported = new Packages(referred);
referredAndExported.putAll(doExportsToImports(exports));
removeDynamicImports(referredAndExported);
// Remove any Java references ... where are the closures???
for (Iterator<PackageRef> i = referredAndExported.keySet().iterator(); i.hasNext(); ) {
if (i.next().isJava())
i.remove();
}
Set<Instruction> unused = Create.set();
String h = getProperty(IMPORT_PACKAGE);
if (// If not set use a default
h == null)
h = "*";
if (isPedantic() && h.trim().length() == 0)
warning("Empty " + Constants.IMPORT_PACKAGE + " header");
Instructions filter = new Instructions(h);
imports = filter(filter, referredAndExported, unused);
if (!unused.isEmpty()) {
// We ignore the end wildcard catch
if (!(unused.size() == 1 && unused.iterator().next().toString().equals("*")))
warning("Unused " + Constants.IMPORT_PACKAGE + " instructions: %s ", unused).header(Constants.IMPORT_PACKAGE).context(unused.iterator().next().input);
}
// See what information we can find to augment the
// imports. I.e. look in the exports
augmentImports(imports, exports);
}
//
// USES
//
// Add the uses clause to the exports
// brave,
boolean api = true;
// lets see
doUses(exports, api ? apiUses : uses, imports);
//
// Verify that no exported package has a reference to a private
// package
// This can cause a lot of harm.
// TODO restrict the check to public API only, but even then
// exported packages
// should preferably not refer to private packages.
//
Set<PackageRef> privatePackages = getPrivates();
for (Iterator<PackageRef> p = privatePackages.iterator(); p.hasNext(); ) if (p.next().isJava())
p.remove();
for (PackageRef exported : exports.keySet()) {
List<PackageRef> used = uses.get(exported);
if (used != null) {
Set<PackageRef> privateReferences = new HashSet<PackageRef>(apiUses.get(exported));
privateReferences.retainAll(privatePackages);
if (!privateReferences.isEmpty())
msgs.Export_Has_PrivateReferences_(exported, privateReferences.size(), privateReferences);
}
}
//
if (referred.containsKey(Descriptors.DEFAULT_PACKAGE)) {
error("The default package '.' is not permitted by the " + Constants.IMPORT_PACKAGE + " syntax.%n" + " This can be caused by compile errors in Eclipse because Eclipse creates%n" + "valid class files regardless of compile errors.%n" + "The following package(s) import from the default package %s", uses.transpose().get(Descriptors.DEFAULT_PACKAGE));
}
}
}
Aggregations