aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/tools/android/java/com/google/devtools/build/android/resources
diff options
context:
space:
mode:
authorGravatar corysmith <corysmith@google.com>2017-05-17 19:14:56 +0200
committerGravatar Dmitry Lomov <dslomov@google.com>2017-05-19 15:07:43 +0200
commitba23f313daf8d0afd8c35ccc72c5661fd897bd5e (patch)
tree322f19965d38f3040aa00cd636c883c5b721f081 /src/tools/android/java/com/google/devtools/build/android/resources
parent98d29f81bafe7ab6b0ff05ade92b4987d7b27bbf (diff)
Remove the RTxtSymbolEntry in favor of the FieldInitializer class.
RELNOTES: None PiperOrigin-RevId: 156321468
Diffstat (limited to 'src/tools/android/java/com/google/devtools/build/android/resources')
-rw-r--r--src/tools/android/java/com/google/devtools/build/android/resources/FieldInitializer.java9
-rw-r--r--src/tools/android/java/com/google/devtools/build/android/resources/FieldInitializers.java31
-rw-r--r--src/tools/android/java/com/google/devtools/build/android/resources/IntArrayFieldInitializer.java14
-rw-r--r--src/tools/android/java/com/google/devtools/build/android/resources/IntFieldInitializer.java16
-rw-r--r--src/tools/android/java/com/google/devtools/build/android/resources/RClassGenerator.java11
-rw-r--r--src/tools/android/java/com/google/devtools/build/android/resources/RSourceGenerator.java14
-rw-r--r--src/tools/android/java/com/google/devtools/build/android/resources/ResourceSymbols.java116
7 files changed, 87 insertions, 124 deletions
diff --git a/src/tools/android/java/com/google/devtools/build/android/resources/FieldInitializer.java b/src/tools/android/java/com/google/devtools/build/android/resources/FieldInitializer.java
index eb671ddd03..edcc464c18 100644
--- a/src/tools/android/java/com/google/devtools/build/android/resources/FieldInitializer.java
+++ b/src/tools/android/java/com/google/devtools/build/android/resources/FieldInitializer.java
@@ -15,7 +15,7 @@ package com.google.devtools.build.android.resources;
import java.io.IOException;
import java.io.Writer;
-import java.util.Set;
+import java.util.Collection;
import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.commons.InstructionAdapter;
@@ -41,6 +41,9 @@ public interface FieldInitializer extends Comparable<FieldInitializer> {
/** Write the source code for the initializer to the given writer. */
void writeInitSource(Writer writer, boolean finalFields) throws IOException;
- /** Tests if the field's name is in the provided set. */
- boolean nameIsIn(Set<String> fieldNames);
+ /** Tests if the field's name is in the provided collection. */
+ boolean nameIsIn(Collection<String> fieldNames);
+
+ /** Adds fieldName to the provided set. */
+ void addTo(Collection<String> fieldNames);
}
diff --git a/src/tools/android/java/com/google/devtools/build/android/resources/FieldInitializers.java b/src/tools/android/java/com/google/devtools/build/android/resources/FieldInitializers.java
index c8961f9f16..45ffadf66d 100644
--- a/src/tools/android/java/com/google/devtools/build/android/resources/FieldInitializers.java
+++ b/src/tools/android/java/com/google/devtools/build/android/resources/FieldInitializers.java
@@ -14,6 +14,7 @@
package com.google.devtools.build.android.resources;
import com.android.resources.ResourceType;
+import com.google.common.base.MoreObjects;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.MultimapBuilder;
import com.google.common.collect.SortedSetMultimap;
@@ -21,9 +22,12 @@ import java.util.Collection;
import java.util.Iterator;
import java.util.Map;
import java.util.Map.Entry;
-import java.util.Set;
+import java.util.SortedSet;
-/** A wrapper for a {@link Collection} of {@link FieldInitializer}s. */
+/**
+ * Represents a collection of resource symbols and values suitable for writing java sources and
+ * classes.
+ */
public class FieldInitializers
implements Iterable<Entry<ResourceType, Collection<FieldInitializer>>> {
@@ -40,10 +44,22 @@ public class FieldInitializers
}
public Iterable<Entry<ResourceType, Collection<FieldInitializer>>> filter(
- Map<ResourceType, Set<String>> symbolsToWrite) {
+ FieldInitializers fieldsToWrite) {
final SortedSetMultimap<ResourceType, FieldInitializer> initializersToWrite =
MultimapBuilder.enumKeys(ResourceType.class).treeSetValues().build();
- for (Entry<ResourceType, Set<String>> entry : symbolsToWrite.entrySet()) {
+
+ // Create a map to filter with.
+ final SortedSetMultimap<ResourceType, String> symbolsToWrite =
+ MultimapBuilder.enumKeys(ResourceType.class).treeSetValues().build();
+ for (Entry<ResourceType, Collection<FieldInitializer>> entry :
+ fieldsToWrite.initializers.entrySet()) {
+ for (FieldInitializer initializer : entry.getValue()) {
+ final SortedSet<String> fieldNames = symbolsToWrite.get(entry.getKey());
+ initializer.addTo(fieldNames);
+ }
+ }
+
+ for (Entry<ResourceType, Collection<String>> entry : symbolsToWrite.asMap().entrySet()) {
// Resource type may be missing if resource overriding eliminates resources at the binary
// level, which were originally present at the library level.
if (initializers.containsKey(entry.getKey())) {
@@ -61,4 +77,11 @@ public class FieldInitializers
public Iterator<Entry<ResourceType, Collection<FieldInitializer>>> iterator() {
return initializers.entrySet().iterator();
}
+
+ @Override
+ public String toString() {
+ return MoreObjects.toStringHelper(FieldInitializers.class)
+ .add("initializers", initializers)
+ .toString();
+ }
}
diff --git a/src/tools/android/java/com/google/devtools/build/android/resources/IntArrayFieldInitializer.java b/src/tools/android/java/com/google/devtools/build/android/resources/IntArrayFieldInitializer.java
index df3a80dcda..2f595c90f5 100644
--- a/src/tools/android/java/com/google/devtools/build/android/resources/IntArrayFieldInitializer.java
+++ b/src/tools/android/java/com/google/devtools/build/android/resources/IntArrayFieldInitializer.java
@@ -20,8 +20,8 @@ import com.google.common.collect.ImmutableCollection;
import com.google.common.collect.ImmutableList;
import java.io.IOException;
import java.io.Writer;
+import java.util.Collection;
import java.util.Objects;
-import java.util.Set;
import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.Type;
import org.objectweb.asm.commons.InstructionAdapter;
@@ -103,7 +103,7 @@ public final class IntArrayFieldInitializer implements FieldInitializer {
}
@Override
- public boolean nameIsIn(Set<String> fieldNames) {
+ public boolean nameIsIn(Collection<String> fieldNames) {
return fieldNames.contains(fieldName);
}
@@ -128,14 +128,18 @@ public final class IntArrayFieldInitializer implements FieldInitializer {
public int hashCode() {
return Objects.hash(fieldName, values);
}
-
+
@Override
public boolean equals(Object obj) {
if (obj instanceof IntArrayFieldInitializer) {
IntArrayFieldInitializer other = (IntArrayFieldInitializer) obj;
- return Objects.equals(fieldName, other.fieldName)
- && Objects.equals(values, other.values);
+ return Objects.equals(fieldName, other.fieldName) && Objects.equals(values, other.values);
}
return false;
}
+
+ @Override
+ public void addTo(Collection<String> fieldNames) {
+ fieldNames.add(fieldName);
+ }
}
diff --git a/src/tools/android/java/com/google/devtools/build/android/resources/IntFieldInitializer.java b/src/tools/android/java/com/google/devtools/build/android/resources/IntFieldInitializer.java
index 85679eb484..ffbd64fcda 100644
--- a/src/tools/android/java/com/google/devtools/build/android/resources/IntFieldInitializer.java
+++ b/src/tools/android/java/com/google/devtools/build/android/resources/IntFieldInitializer.java
@@ -16,8 +16,8 @@ package com.google.devtools.build.android.resources;
import com.google.common.base.MoreObjects;
import java.io.IOException;
import java.io.Writer;
+import java.util.Collection;
import java.util.Objects;
-import java.util.Set;
import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.commons.InstructionAdapter;
@@ -63,7 +63,7 @@ public final class IntFieldInitializer implements FieldInitializer {
}
@Override
- public boolean nameIsIn(Set<String> fieldNames) {
+ public boolean nameIsIn(Collection<String> fieldNames) {
return fieldNames.contains(fieldName);
}
@@ -83,19 +83,23 @@ public final class IntFieldInitializer implements FieldInitializer {
// IntFields will go before Intarrays
return -1;
}
-
+
@Override
public int hashCode() {
return Objects.hash(fieldName, value);
}
-
+
@Override
public boolean equals(Object obj) {
if (obj instanceof IntFieldInitializer) {
IntFieldInitializer other = (IntFieldInitializer) obj;
- return Objects.equals(fieldName, other.fieldName)
- && value == other.value;
+ return Objects.equals(fieldName, other.fieldName) && value == other.value;
}
return false;
}
+
+ @Override
+ public void addTo(Collection<String> fieldNames) {
+ fieldNames.add(fieldName);
+ }
}
diff --git a/src/tools/android/java/com/google/devtools/build/android/resources/RClassGenerator.java b/src/tools/android/java/com/google/devtools/build/android/resources/RClassGenerator.java
index b36b752829..54375fab14 100644
--- a/src/tools/android/java/com/google/devtools/build/android/resources/RClassGenerator.java
+++ b/src/tools/android/java/com/google/devtools/build/android/resources/RClassGenerator.java
@@ -25,7 +25,6 @@ import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
-import java.util.Set;
import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.MethodVisitor;
import org.objectweb.asm.Opcodes;
@@ -80,8 +79,7 @@ public class RClassGenerator {
* Builds bytecode and writes out R.class file, and R$inner.class files for provided package and
* symbols.
*/
- public void write(String packageName, Map<ResourceType, Set<String>> symbolsToWrite)
- throws IOException {
+ public void write(String packageName, FieldInitializers symbolsToWrite) throws IOException {
writeClasses(packageName, initializers.filter(symbolsToWrite));
}
@@ -103,7 +101,7 @@ public class RClassGenerator {
// At least create the outFolder that was requested. However, if there are no symbols, don't
// create the R.class and inner class files (no need to have an empty class).
Files.createDirectories(packageDir);
-
+
if (Iterables.isEmpty(initializersToWrite)) {
return;
}
@@ -124,12 +122,11 @@ public class RClassGenerator {
writeConstructor(classWriter);
// Build the R.class w/ the inner classes, then later build the individual R$inner.class.
for (Entry<ResourceType, Collection<FieldInitializer>> entry : initializersToWrite) {
- final String resourceType = entry.getKey().toString();
- String innerClassName = rClassName + "$" + resourceType;
+ String innerClassName = rClassName + "$" + entry.getKey().toString();
classWriter.visitInnerClass(
innerClassName,
rClassName,
- resourceType,
+ entry.getKey().toString(),
Opcodes.ACC_PUBLIC | Opcodes.ACC_FINAL | Opcodes.ACC_STATIC);
}
classWriter.visitEnd();
diff --git a/src/tools/android/java/com/google/devtools/build/android/resources/RSourceGenerator.java b/src/tools/android/java/com/google/devtools/build/android/resources/RSourceGenerator.java
index e2d19b1c73..4c3ef8581f 100644
--- a/src/tools/android/java/com/google/devtools/build/android/resources/RSourceGenerator.java
+++ b/src/tools/android/java/com/google/devtools/build/android/resources/RSourceGenerator.java
@@ -23,9 +23,7 @@ import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.Collection;
-import java.util.Map;
import java.util.Map.Entry;
-import java.util.Set;
/** Writes out an R.java source. */
public class RSourceGenerator {
@@ -48,23 +46,21 @@ public class RSourceGenerator {
/** Writes the java source with the writer values to the specified package and derived dir. */
public void write(String packageName) throws IOException {
- write(packageName, values);
+ writeSource(packageName, values);
}
/**
* Writes the java source with the passed subset of the writer values.
*
- * @param packageName The package and the dir to write the R java source to under the output
- * path.
+ * @param packageName The package and the dir to write the R java source to under the output path.
* @param symbolsToWrite A map of ResourceType to resource name that will be written. If the map
* specifies a resource that does not exist in the writer values, it will be ignored.
*/
- public void write(String packageName, Map<ResourceType, Set<String>> symbolsToWrite)
- throws IOException {
- write(packageName, values.filter(symbolsToWrite));
+ public void write(String packageName, FieldInitializers symbolsToWrite) throws IOException {
+ writeSource(packageName, values.filter(symbolsToWrite));
}
- private void write(
+ private void writeSource(
String packageName,
Iterable<Entry<ResourceType, Collection<FieldInitializer>>> initializersToWrite)
throws IOException {
diff --git a/src/tools/android/java/com/google/devtools/build/android/resources/ResourceSymbols.java b/src/tools/android/java/com/google/devtools/build/android/resources/ResourceSymbols.java
index d18eceeca5..6b2dbcff7b 100644
--- a/src/tools/android/java/com/google/devtools/build/android/resources/ResourceSymbols.java
+++ b/src/tools/android/java/com/google/devtools/build/android/resources/ResourceSymbols.java
@@ -16,14 +16,10 @@ package com.google.devtools.build.android.resources;
import com.android.builder.core.VariantConfiguration;
import com.android.builder.dependency.SymbolFileProvider;
import com.android.resources.ResourceType;
-import com.android.utils.ILogger;
-import com.google.common.base.Preconditions;
-import com.google.common.collect.HashBasedTable;
import com.google.common.collect.HashMultimap;
import com.google.common.collect.Multimap;
import com.google.common.collect.MultimapBuilder;
-import com.google.common.collect.SetMultimap;
-import com.google.common.collect.Table;
+import com.google.common.collect.SortedSetMultimap;
import com.google.common.util.concurrent.ListenableFuture;
import com.google.common.util.concurrent.ListeningExecutorService;
import java.io.File;
@@ -32,57 +28,20 @@ import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.Collection;
-import java.util.EnumMap;
import java.util.HashMap;
-import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Objects;
-import java.util.Set;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.logging.Logger;
import javax.annotation.Nullable;
-/** This provides a unified interface for working with R.txt symbols files. */
+/** Encapsulates the logic for loading and writing resource symbols. */
public class ResourceSymbols {
private static final Logger logger = Logger.getLogger(ResourceSymbols.class.getCanonicalName());
- /** Represents a resource symbol with a value. */
- // Forked from com.android.builder.internal.SymbolLoader.SymbolEntry.
- static class RTxtSymbolEntry {
- private final String name;
- private final String type;
- private final String value;
-
- RTxtSymbolEntry(String name, String type, String value) {
- this.name = name;
- this.type = type;
- this.value = value;
- }
-
- public String getValue() {
- return value;
- }
-
- public String getName() {
- return name;
- }
-
- public String getType() {
- return type;
- }
-
- public FieldInitializer toInitializer() {
- if (type.equals("int")) {
- return IntFieldInitializer.of(name, value);
- }
- Preconditions.checkArgument(type.equals("int[]"));
- return IntArrayFieldInitializer.of(name, value);
- }
- }
-
/** Task to load and parse R.txt symbols */
private static final class SymbolLoadingTask implements Callable<ResourceSymbols> {
@@ -96,7 +55,8 @@ public class ResourceSymbols {
public ResourceSymbols call() throws Exception {
List<String> lines = Files.readAllLines(rTxtSymbols, StandardCharsets.UTF_8);
- Table<String, String, RTxtSymbolEntry> symbols = HashBasedTable.create();
+ final SortedSetMultimap<ResourceType, FieldInitializer> initializers =
+ MultimapBuilder.enumKeys(ResourceType.class).treeSetValues().build();
for (int lineIndex = 1; lineIndex <= lines.size(); lineIndex++) {
String line = null;
@@ -113,7 +73,12 @@ public class ResourceSymbols {
String name = line.substring(pos2 + 1, pos3);
String value = line.substring(pos3 + 1);
- symbols.put(className, name, new RTxtSymbolEntry(name, type, value));
+ final ResourceType resourceType = ResourceType.getEnum(className);
+ if ("int".equals(type)) {
+ initializers.put(resourceType, IntFieldInitializer.of(name, value));
+ } else {
+ initializers.put(resourceType, IntArrayFieldInitializer.of(name, value));
+ }
} catch (IndexOutOfBoundsException e) {
String s =
String.format(
@@ -123,7 +88,7 @@ public class ResourceSymbols {
throw new IOException(s, e);
}
}
- return ResourceSymbols.from(symbols);
+ return ResourceSymbols.from(FieldInitializers.copyOf(initializers.asMap()));
}
}
@@ -146,7 +111,6 @@ public class ResourceSymbols {
*
* @param dependencies The full set of library symbols to load.
* @param executor The executor use during loading.
- * @param iLogger Android logger to use.
* @param packageToExclude A string package to elide if it exists in the providers.
* @return A list of loading {@link ResourceSymbols} instances.
* @throws ExecutionException
@@ -155,7 +119,6 @@ public class ResourceSymbols {
public static Multimap<String, ListenableFuture<ResourceSymbols>> loadFrom(
Collection<SymbolFileProvider> dependencies,
ListeningExecutorService executor,
- ILogger iLogger,
@Nullable String packageToExclude)
throws InterruptedException, ExecutionException {
Map<SymbolFileProvider, ListenableFuture<String>> providerToPackage = new HashMap<>();
@@ -173,16 +136,20 @@ public class ResourceSymbols {
return packageToTable;
}
- public static ResourceSymbols from(Table<String, String, RTxtSymbolEntry> table) {
- return new ResourceSymbols(table);
+ public static ResourceSymbols from(FieldInitializers fieldInitializers) {
+ return new ResourceSymbols(fieldInitializers);
}
public static ResourceSymbols merge(Collection<ResourceSymbols> symbolTables) {
- final Table<String, String, RTxtSymbolEntry> mergedTable = HashBasedTable.create();
+ final SortedSetMultimap<ResourceType, FieldInitializer> initializers =
+ MultimapBuilder.enumKeys(ResourceType.class).treeSetValues().build();
for (ResourceSymbols symbolTableProvider : symbolTables) {
- mergedTable.putAll(symbolTableProvider.asTable());
+ for (Entry<ResourceType, Collection<FieldInitializer>> entry :
+ symbolTableProvider.asInitializers()) {
+ initializers.putAll(entry.getKey(), entry.getValue());
+ }
}
- return from(mergedTable);
+ return from(FieldInitializers.copyOf(initializers.asMap()));
}
/** Read the symbols from the provided symbol file. */
@@ -191,14 +158,10 @@ public class ResourceSymbols {
return executorService.submit(new SymbolLoadingTask(primaryRTxt));
}
- private final Table<String, String, RTxtSymbolEntry> values;
+ private final FieldInitializers values;
- private ResourceSymbols(Table<String, String, RTxtSymbolEntry> values) {
- this.values = values;
- }
-
- public Table<String, String, RTxtSymbolEntry> asTable() {
- return values;
+ private ResourceSymbols(FieldInitializers fieldInitializers) {
+ this.values = fieldInitializers;
}
/**
@@ -216,39 +179,12 @@ public class ResourceSymbols {
Collection<ResourceSymbols> packageSymbols,
boolean finalFields)
throws IOException {
-
- Map<ResourceType, Set<String>> symbols = new EnumMap<>(ResourceType.class);
- for (ResourceSymbols packageSymbol : packageSymbols) {
- symbols.putAll(packageSymbol.asFilterMap());
- }
- RSourceGenerator.with(sourceOut, asInitializers(), finalFields).write(packageName, symbols);
+ RSourceGenerator.with(sourceOut, asInitializers(), finalFields)
+ .write(packageName, merge(packageSymbols).asInitializers());
}
public FieldInitializers asInitializers() {
- SetMultimap<ResourceType, FieldInitializer> valuesOut =
- MultimapBuilder.enumKeys(ResourceType.class).treeSetValues().build();
- Table<String, String, RTxtSymbolEntry> symbolTable = asTable();
- for (String typeName : symbolTable.rowKeySet()) {
- final ResourceType type = ResourceType.getEnum(typeName);
- for (RTxtSymbolEntry symbolEntry : symbolTable.row(typeName).values()) {
- valuesOut.put(type, symbolEntry.toInitializer());
- }
- }
- return FieldInitializers.copyOf(valuesOut.asMap());
+ return values;
}
- public Map<ResourceType, Set<String>> asFilterMap() {
- Map<ResourceType, Set<String>> filter = new EnumMap<>(ResourceType.class);
- Table<String, String, RTxtSymbolEntry> symbolTable = asTable();
- for (String typeName : symbolTable.rowKeySet()) {
- Set<String> fields = new HashSet<>();
- for (RTxtSymbolEntry symbolEntry : symbolTable.row(typeName).values()) {
- fields.add(symbolEntry.getName());
- }
- if (!fields.isEmpty()) {
- filter.put(ResourceType.getEnum(typeName), fields);
- }
- }
- return filter;
- }
}