Merge "Parse -applymapping filename."
diff --git a/src/main/java/com/android/tools/r8/R8Command.java b/src/main/java/com/android/tools/r8/R8Command.java
index ec040a5..0959167 100644
--- a/src/main/java/com/android/tools/r8/R8Command.java
+++ b/src/main/java/com/android/tools/r8/R8Command.java
@@ -5,7 +5,6 @@
 
 import com.android.tools.r8.graph.DexItemFactory;
 import com.android.tools.r8.shaking.ProguardConfiguration;
-import com.android.tools.r8.shaking.ProguardConfiguration.Builder;
 import com.android.tools.r8.shaking.ProguardConfigurationParser;
 import com.android.tools.r8.shaking.ProguardConfigurationRule;
 import com.android.tools.r8.shaking.ProguardRuleParserException;
@@ -194,6 +193,8 @@
         addLibraryFiles(configuration.getLibraryjars());
       }
 
+      // TODO(b/64802420): setProguardMapFile if configuration.hasApplyMappingFile
+
       if (packageDistributionFile != null) {
         getAppBuilder().setPackageDistributionFile(packageDistributionFile);
       }
diff --git a/src/main/java/com/android/tools/r8/shaking/ProguardConfiguration.java b/src/main/java/com/android/tools/r8/shaking/ProguardConfiguration.java
index e39faa0..f47adbd 100644
--- a/src/main/java/com/android/tools/r8/shaking/ProguardConfiguration.java
+++ b/src/main/java/com/android/tools/r8/shaking/ProguardConfiguration.java
@@ -31,6 +31,7 @@
     private Path printUsageFile;
     private boolean printMapping;
     private Path printMappingFile;
+    private Path applyMappingFile = null;
     private boolean verbose = false;
     private final List<String> attributesRemovalPatterns = new ArrayList<>();
     private final Set<ProguardTypeMatcher> dontWarnPatterns = new HashSet<>();
@@ -104,6 +105,10 @@
       this.printMappingFile = file;
     }
 
+    public void setApplyMappingFile(Path file) {
+      this.applyMappingFile = file;
+    }
+
     public void setVerbose(boolean verbose) {
       this.verbose = verbose;
     }
@@ -155,6 +160,7 @@
           printUsageFile,
           printMapping,
           printMappingFile,
+          applyMappingFile,
           verbose,
           attributesRemovalPatterns,
           dontWarnPatterns,
@@ -180,6 +186,7 @@
   private final Path printUsageFile;
   private final boolean printMapping;
   private final Path printMappingFile;
+  private final Path applyMappingFile;
   private final boolean verbose;
   private final ImmutableList<String> attributesRemovalPatterns;
   private final ImmutableSet<ProguardTypeMatcher> dontWarnPatterns;
@@ -204,6 +211,7 @@
       Path printUsageFile,
       boolean printMapping,
       Path printMappingFile,
+      Path applyMappingFile,
       boolean verbose,
       List<String> attributesRemovalPatterns,
       Set<ProguardTypeMatcher> dontWarnPatterns,
@@ -226,6 +234,7 @@
     this.printUsageFile = printUsageFile;
     this.printMapping = printMapping;
     this.printMappingFile = printMappingFile;
+    this.applyMappingFile = applyMappingFile;
     this.verbose = verbose;
     this.attributesRemovalPatterns = ImmutableList.copyOf(attributesRemovalPatterns);
     this.dontWarnPatterns = ImmutableSet.copyOf(dontWarnPatterns);
@@ -280,6 +289,14 @@
     return printMappingFile;
   }
 
+  public boolean hasApplyMappingFile() {
+    return applyMappingFile != null;
+  }
+
+  public Path getApplyMappingFile() {
+    return applyMappingFile;
+  }
+
   public boolean isIgnoreWarnings() {
     return ignoreWarnings;
   }
@@ -347,7 +364,8 @@
           false                 /* printUsage */,
           null                  /* printUsageFile */,
           false                 /* printMapping */,
-          null                  /* outputMapping */,
+          null                  /* printMappingFile */,
+          null                  /* applyMapping */,
           false                 /* verbose */,
           ImmutableList.of()    /* attributesRemovalPatterns */,
           ImmutableSet.of()     /* dontWarnPatterns */,
diff --git a/src/main/java/com/android/tools/r8/shaking/ProguardConfigurationParser.java b/src/main/java/com/android/tools/r8/shaking/ProguardConfigurationParser.java
index 4fb7357..5292a45 100644
--- a/src/main/java/com/android/tools/r8/shaking/ProguardConfigurationParser.java
+++ b/src/main/java/com/android/tools/r8/shaking/ProguardConfigurationParser.java
@@ -219,6 +219,10 @@
         if (isOptionalArgumentGiven()) {
           configurationBuilder.setPrintMappingFile(parseFileName());
         }
+      } else if (acceptString("applymapping")) {
+        configurationBuilder.setApplyMappingFile(parseFileName());
+        // TODO(b/64802420): warn until it is fully implemented.
+        warnIgnoringOptions("applymapping");
       } else if (acceptString("assumenosideeffects")) {
         ProguardAssumeNoSideEffectRule rule = parseAssumeNoSideEffectsRule();
         configurationBuilder.addRule(rule);
diff --git a/src/main/java/com/android/tools/r8/utils/AndroidApp.java b/src/main/java/com/android/tools/r8/utils/AndroidApp.java
index 97a3679..4c6c56f 100644
--- a/src/main/java/com/android/tools/r8/utils/AndroidApp.java
+++ b/src/main/java/com/android/tools/r8/utils/AndroidApp.java
@@ -586,6 +586,15 @@
     }
 
     /**
+     * Inform whether ProGuard map has already been set or not.
+     *
+     * ProGuard option -applymapping will override R8/Dissemble option -pg-map.
+     */
+    public boolean hasProguardMap() {
+      return proguardMap != null;
+    }
+
+    /**
      * Set proguard-map file.
      */
     public Builder setProguardMapFile(Path file) {
diff --git a/src/test/java/com/android/tools/r8/shaking/ProguardConfigurationParserTest.java b/src/test/java/com/android/tools/r8/shaking/ProguardConfigurationParserTest.java
index ea28214..ac0178c 100644
--- a/src/test/java/com/android/tools/r8/shaking/ProguardConfigurationParserTest.java
+++ b/src/test/java/com/android/tools/r8/shaking/ProguardConfigurationParserTest.java
@@ -69,6 +69,10 @@
       VALID_PROGUARD_DIR + "package-obfuscation-5.flags";
   private static final String PACKAGE_OBFUSCATION_6 =
       VALID_PROGUARD_DIR + "package-obfuscation-6.flags";
+  private static final String APPLY_MAPPING =
+      VALID_PROGUARD_DIR + "applymapping.flags";
+  private static final String APPLY_MAPPING_WITHOUT_FILE =
+      INVALID_PROGUARD_DIR + "applymapping-without-file.flags";
   private static final String DONT_SHRINK =
       VALID_PROGUARD_DIR + "dontshrink.flags";
   private static final String DONT_SKIP_NON_PUBLIC_LIBRARY_CLASSES =
@@ -339,6 +343,25 @@
   }
 
   @Test
+  public void parseApplyMapping() throws IOException, ProguardRuleParserException {
+    ProguardConfigurationParser parser = new ProguardConfigurationParser(new DexItemFactory());
+    parser.parse(Paths.get(APPLY_MAPPING));
+    ProguardConfiguration config = parser.getConfig();
+    assertTrue(config.hasApplyMappingFile());
+  }
+
+  @Test
+  public void parseApplyMappingWithoutFile() throws IOException, ProguardRuleParserException {
+    try {
+      ProguardConfigurationParser parser = new ProguardConfigurationParser(new DexItemFactory());
+      parser.parse(Paths.get(APPLY_MAPPING_WITHOUT_FILE));
+      fail("Expect to fail due to the lack of file name.");
+    } catch (ProguardRuleParserException e) {
+      assertTrue(e.getMessage().contains("File name expected"));
+    }
+  }
+
+  @Test
   public void parseIncluding() throws IOException, ProguardRuleParserException {
     new ProguardConfigurationParser(new DexItemFactory()).parse(Paths.get(INCLUDING));
   }
diff --git a/src/test/proguard/invalid/applymapping-without-file.flags b/src/test/proguard/invalid/applymapping-without-file.flags
new file mode 100644
index 0000000..ef5abe5
--- /dev/null
+++ b/src/test/proguard/invalid/applymapping-without-file.flags
@@ -0,0 +1,6 @@
+# Copyright (c) 2017, the R8 project authors. Please see the AUTHORS file
+# for details. All rights reserved. Use of this source code is governed by a
+# BSD-style license that can be found in the LICENSE file.
+
+# file name should be followed.
+-applymapping
diff --git a/src/test/proguard/valid/applymapping.flags b/src/test/proguard/valid/applymapping.flags
new file mode 100644
index 0000000..8d427f9
--- /dev/null
+++ b/src/test/proguard/valid/applymapping.flags
@@ -0,0 +1,5 @@
+# Copyright (c) 2017, the R8 project authors. Please see the AUTHORS file
+# for details. All rights reserved. Use of this source code is governed by a
+# BSD-style license that can be found in the LICENSE file.
+
+-applymapping bogus-file-name.ext