Create --incompatible_disable_objc_provider_resources to disable deprecated objc provider skylark fields.

This flag is not fully implemented -- there should also be a way to disable the provider getters using this flag, but, since @SkylarkCallable does not allow for evaluation of SkylarkSemantics, this is not yet possible.

RELNOTES: None.
PiperOrigin-RevId: 187542004
diff --git a/src/main/java/com/google/devtools/build/lib/packages/SkylarkSemanticsCodec.java b/src/main/java/com/google/devtools/build/lib/packages/SkylarkSemanticsCodec.java
index 9f729b5..978e7e9 100644
--- a/src/main/java/com/google/devtools/build/lib/packages/SkylarkSemanticsCodec.java
+++ b/src/main/java/com/google/devtools/build/lib/packages/SkylarkSemanticsCodec.java
@@ -47,6 +47,7 @@
     codedOut.writeBoolNoTag(semantics.incompatibleDepsetIsNotIterable());
     codedOut.writeBoolNoTag(semantics.incompatibleDepsetUnion());
     codedOut.writeBoolNoTag(semantics.incompatibleDisableGlobTracking());
+    codedOut.writeBoolNoTag(semantics.incompatibleDisableObjcProviderResources());
     codedOut.writeBoolNoTag(semantics.incompatibleDisallowDictPlus());
     codedOut.writeBoolNoTag(semantics.incompatibleDisallowToplevelIfStatement());
     codedOut.writeBoolNoTag(semantics.incompatibleDisallowUncalledSetConstructor());
@@ -69,6 +70,7 @@
     builder.incompatibleDepsetIsNotIterable(codedIn.readBool());
     builder.incompatibleDepsetUnion(codedIn.readBool());
     builder.incompatibleDisableGlobTracking(codedIn.readBool());
+    builder.incompatibleDisableObjcProviderResources(codedIn.readBool());
     builder.incompatibleDisallowDictPlus(codedIn.readBool());
     builder.incompatibleDisallowToplevelIfStatement(codedIn.readBool());
     builder.incompatibleDisallowUncalledSetConstructor(codedIn.readBool());
diff --git a/src/main/java/com/google/devtools/build/lib/packages/SkylarkSemanticsOptions.java b/src/main/java/com/google/devtools/build/lib/packages/SkylarkSemanticsOptions.java
index 1bcd5a1..86f6b44 100644
--- a/src/main/java/com/google/devtools/build/lib/packages/SkylarkSemanticsOptions.java
+++ b/src/main/java/com/google/devtools/build/lib/packages/SkylarkSemanticsOptions.java
@@ -111,6 +111,17 @@
   public boolean incompatibleDisableGlobTracking;
 
   @Option(
+      name = "incompatible_disable_objc_provider_resources",
+      defaultValue = "false",
+      category = "incompatible changes",
+      documentationCategory = OptionDocumentationCategory.UNCATEGORIZED,
+      effectTags = {OptionEffectTag.UNKNOWN},
+      metadataTags = {OptionMetadataTag.INCOMPATIBLE_CHANGE},
+      help = "If set to true, disallow use of deprecated resource fields on the Objc provider."
+  )
+  public boolean incompatibleDisableObjcProviderResources;
+
+  @Option(
     name = "incompatible_disallow_dict_plus",
     defaultValue = "false",
     category = "incompatible changes",
@@ -238,6 +249,7 @@
         .incompatibleDepsetIsNotIterable(incompatibleDepsetIsNotIterable)
         .incompatibleDepsetUnion(incompatibleDepsetUnion)
         .incompatibleDisableGlobTracking(incompatibleDisableGlobTracking)
+        .incompatibleDisableObjcProviderResources(incompatibleDisableObjcProviderResources)
         .incompatibleDisallowDictPlus(incompatibleDisallowDictPlus)
         .incompatibleDisallowToplevelIfStatement(incompatibleDisallowToplevelIfStatement)
         .incompatibleDisallowUncalledSetConstructor(incompatibleDisallowUncalledSetConstructor)
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/AppleSkylarkCommon.java b/src/main/java/com/google/devtools/build/lib/rules/objc/AppleSkylarkCommon.java
index 5e8881a..fa2cee2 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/AppleSkylarkCommon.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/AppleSkylarkCommon.java
@@ -43,6 +43,7 @@
 import com.google.devtools.build.lib.skylarkinterface.SkylarkModule;
 import com.google.devtools.build.lib.skylarkinterface.SkylarkSignature;
 import com.google.devtools.build.lib.syntax.BuiltinFunction;
+import com.google.devtools.build.lib.syntax.Environment;
 import com.google.devtools.build.lib.syntax.EvalException;
 import com.google.devtools.build.lib.syntax.Runtime;
 import com.google.devtools.build.lib.syntax.SkylarkDict;
@@ -375,14 +376,18 @@
           type = SkylarkDict.class,
           defaultValue = "{}",
           doc = "Dictionary of arguments."
-        )
+        ),
+    useEnvironment = true
   )
   public static final BuiltinFunction NEW_OBJC_PROVIDER =
       new BuiltinFunction("new_objc_provider") {
         @SuppressWarnings("unused")
         // This method is registered statically for skylark, and never called directly.
         public ObjcProvider invoke(
-            AppleSkylarkCommon self, Boolean usesSwift, SkylarkDict<String, Object> kwargs) {
+            AppleSkylarkCommon self, Boolean usesSwift, SkylarkDict<String, Object> kwargs,
+            Environment environment) {
+          boolean disableObjcResourceKeys =
+              environment.getSemantics().incompatibleDisableObjcProviderResources();
           ObjcProvider.Builder resultBuilder = new ObjcProvider.Builder();
           if (usesSwift) {
             resultBuilder.add(ObjcProvider.FLAG, ObjcProvider.Flag.USES_SWIFT);
@@ -390,6 +395,9 @@
           for (Entry<String, Object> entry : kwargs.entrySet()) {
             Key<?> key = ObjcProvider.getSkylarkKeyForString(entry.getKey());
             if (key != null) {
+              if (disableObjcResourceKeys && ObjcProvider.isDeprecatedResourceKey(key)) {
+                throw new IllegalArgumentException(String.format(BAD_KEY_ERROR, entry.getKey()));
+              }
               resultBuilder.addElementsFromSkylark(key, entry.getValue());
             } else if (entry.getKey().equals("providers")) {
               resultBuilder.addProvidersFromSkylark(entry.getValue());
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcProvider.java b/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcProvider.java
index 3dfada9..1cc56ae 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcProvider.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcProvider.java
@@ -411,6 +411,19 @@
           XCDATAMODEL,
           XIB);
 
+  /** Deprecated keys in ObjcProvider pertaining to resource files. */
+  static final ImmutableList<Key<?>> DEPRECATED_RESOURCE_KEYS =
+      ImmutableList.<Key<?>>of(
+          ASSET_CATALOG,
+          BUNDLE_FILE,
+          MERGE_ZIP,
+          ROOT_MERGE_ZIP,
+          STORYBOARD,
+          STRINGS,
+          XCASSETS_DIR,
+          XCDATAMODEL,
+          XIB);
+
   @SkylarkCallable(name = "asset_catalog",
       structField = true,
       doc = "<b>Deprecated. Resource-related fields will be migrated to another provider.</b> "
@@ -808,6 +821,10 @@
     return null;
   }
 
+  static boolean isDeprecatedResourceKey(Key<?> key) {
+    return DEPRECATED_RESOURCE_KEYS.contains(key);
+  }
+
   // Items which should be passed to strictly direct dependers, but not transitive dependers.
   private final ImmutableMap<Key<?>, NestedSet<?>> strictDependencyItems;
 
diff --git a/src/main/java/com/google/devtools/build/lib/syntax/SkylarkSemantics.java b/src/main/java/com/google/devtools/build/lib/syntax/SkylarkSemantics.java
index 85f5c08..95edc23 100644
--- a/src/main/java/com/google/devtools/build/lib/syntax/SkylarkSemantics.java
+++ b/src/main/java/com/google/devtools/build/lib/syntax/SkylarkSemantics.java
@@ -45,6 +45,7 @@
   public abstract boolean incompatibleDepsetUnion();
 
   public abstract boolean incompatibleDisableGlobTracking();
+  public abstract boolean incompatibleDisableObjcProviderResources();
 
   public abstract boolean incompatibleDisallowDictPlus();
   public abstract boolean incompatibleDisallowToplevelIfStatement();
@@ -79,6 +80,7 @@
           .incompatibleDepsetIsNotIterable(false)
           .incompatibleDepsetUnion(false)
           .incompatibleDisableGlobTracking(true)
+          .incompatibleDisableObjcProviderResources(false)
           .incompatibleDisallowDictPlus(false)
           .incompatibleDisallowToplevelIfStatement(true)
           .incompatibleDisallowUncalledSetConstructor(true)
@@ -102,6 +104,7 @@
     public abstract Builder incompatibleDepsetUnion(boolean value);
 
     public abstract Builder incompatibleDisableGlobTracking(boolean value);
+    public abstract Builder incompatibleDisableObjcProviderResources(boolean value);
 
     public abstract Builder incompatibleDisallowDictPlus(boolean value);
     public abstract Builder incompatibleDisallowToplevelIfStatement(boolean value);
diff --git a/src/test/java/com/google/devtools/build/lib/packages/SkylarkSemanticsConsistencyTest.java b/src/test/java/com/google/devtools/build/lib/packages/SkylarkSemanticsConsistencyTest.java
index 925b477..0eb5f2d 100644
--- a/src/test/java/com/google/devtools/build/lib/packages/SkylarkSemanticsConsistencyTest.java
+++ b/src/test/java/com/google/devtools/build/lib/packages/SkylarkSemanticsConsistencyTest.java
@@ -123,6 +123,7 @@
         "--incompatible_depset_is_not_iterable=" + rand.nextBoolean(),
         "--incompatible_depset_union=" + rand.nextBoolean(),
         "--incompatible_disable_glob_tracking=" + rand.nextBoolean(),
+        "--incompatible_disable_objc_provider_resources=" + rand.nextBoolean(),
         "--incompatible_disallow_dict_plus=" + rand.nextBoolean(),
         "--incompatible_disallow_toplevel_if_statement=" + rand.nextBoolean(),
         "--incompatible_disallow_uncalled_set_constructor=" + rand.nextBoolean(),
@@ -146,6 +147,7 @@
         .incompatibleDepsetIsNotIterable(rand.nextBoolean())
         .incompatibleDepsetUnion(rand.nextBoolean())
         .incompatibleDisableGlobTracking(rand.nextBoolean())
+        .incompatibleDisableObjcProviderResources(rand.nextBoolean())
         .incompatibleDisallowDictPlus(rand.nextBoolean())
         .incompatibleDisallowToplevelIfStatement(rand.nextBoolean())
         .incompatibleDisallowUncalledSetConstructor(rand.nextBoolean())
diff --git a/src/test/java/com/google/devtools/build/lib/rules/objc/ObjcSkylarkTest.java b/src/test/java/com/google/devtools/build/lib/rules/objc/ObjcSkylarkTest.java
index 9e6fe98..9638eac 100644
--- a/src/test/java/com/google/devtools/build/lib/rules/objc/ObjcSkylarkTest.java
+++ b/src/test/java/com/google/devtools/build/lib/rules/objc/ObjcSkylarkTest.java
@@ -1263,6 +1263,66 @@
         .contains("ios_arm64");
   }
 
+  @Test
+  public void testDisableObjcProviderResources() throws Exception {
+    scratch.file("examples/rule/BUILD");
+    scratch.file(
+        "examples/rule/apple_rules.bzl",
+        "def my_rule_impl(ctx):",
+        "   file = ctx.actions.declare_file('foo.ast')",
+        "   ctx.actions.run_shell(outputs=[file], command='echo')",
+        "   objc_provider = apple_common.new_objc_provider(xib=depset([file]))",
+        "   return struct(objc=objc_provider)",
+        "my_rule = rule(implementation = my_rule_impl,",
+        "   attrs = {})");
+
+    scratch.file(
+        "examples/apple_skylark/BUILD",
+        "package(default_visibility = ['//visibility:public'])",
+        "load('//examples/rule:apple_rules.bzl', 'my_rule')",
+        "my_rule(",
+        "   name='my_target',",
+        ")");
+
+    try {
+      setSkylarkSemanticsOptions("--incompatible_disable_objc_provider_resources=true");
+      getConfiguredTarget("//examples/apple_skylark:my_target");
+    } catch (AssertionError e) {
+      assertThat(e)
+          .hasMessageThat()
+          .contains("in call to new_objc_provider: Argument xib not a recognized key");
+    }
+  }
+
+  @Test
+  public void testEnabledObjcProviderResources() throws Exception {
+    scratch.file("examples/rule/BUILD");
+    scratch.file(
+        "examples/rule/apple_rules.bzl",
+        "def my_rule_impl(ctx):",
+        "   file = ctx.actions.declare_file('foo.ast')",
+        "   ctx.actions.run_shell(outputs=[file], command='echo')",
+        "   objc_provider = apple_common.new_objc_provider(xib=depset([file]))",
+        "   return struct(objc=objc_provider)",
+        "my_rule = rule(implementation = my_rule_impl,",
+        "   attrs = {})");
+
+    scratch.file(
+        "examples/apple_skylark/BUILD",
+        "package(default_visibility = ['//visibility:public'])",
+        "load('//examples/rule:apple_rules.bzl', 'my_rule')",
+        "my_rule(",
+        "   name='my_target',",
+        ")");
+
+    setSkylarkSemanticsOptions("--incompatible_disable_objc_provider_resources=false");
+    ConfiguredTarget binaryTarget = getConfiguredTarget("//examples/apple_skylark:my_target");
+
+    ObjcProvider objcProvider = binaryTarget.get(ObjcProvider.SKYLARK_CONSTRUCTOR);
+
+    assertThat(objcProvider.get(ObjcProvider.XIB)).isNotNull();
+  }
+
   private void checkSkylarkRunMemleaksWithExpectedValue(boolean expectedValue) throws Exception {
     scratch.file("examples/rule/BUILD");
     scratch.file(