Repository: bazelbuild/bazel
Issue: Remove warning for multiple copts in same string
Labels: type: feature request
P3

### Description of the problem / feature request / question:

Consider the BUILD file below:

```
cc_binary(
    name = "foo",
    srcs = ["foo.cc"],
    copts = ["-framework IOKit"],
    linkopts = ["-framework IOKit"],
)
```

When building this binary, Bazel emits a warning:

```
WARNING: /Users/jayconrod/Code/scratch/BUILD:4:13: in copts attribute of cc_binary rule //:foo: each item in the list should contain only one option
```

Bazel performs Bourne shell tokenization and Make variable expansion on both `copts` and `linkopts`, so these options will be passed to the compiler as separate arguments. Additionally, Bazel performs label expansion on `linkopts` strings that don't start with '-'. This means that the framework above *must* be passed to `linkopts` as a single string to prevent `IOKit` from being interpreted as a label.

It would be awkward to break up the string for `copts` but not for `linkopts`, but there's no other way to avoid the warning. The tokenization doesn't seem to cause problems, so I think the warning should be removed.

We are seeing this warning a lot in the Go rules for generated BUILD files. Because `-framework` options in cgo code must be specified together, we don't split option strings extracted from cgo LDFLAGS directives. We would prefer to process CFLAGS directives the same way.

### Environment info
* Operating System: Linux, Darwin

* Bazel version (output of `bazel info release`): Observed on 0.5.1, 0.5.3.


Issue comments:

Pull request review comments:

Patch that resolved the issue:
diff --git a/src/main/java/com/google/devtools/build/lib/rules/cpp/CcCommon.java b/src/main/java/com/google/devtools/build/lib/rules/cpp/CcCommon.java
index 47aa40a0ecd578..0f439d39b99940 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/cpp/CcCommon.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/cpp/CcCommon.java
@@ -156,10 +156,6 @@ public ImmutableList<String> getCopts() {
       tokens.clear();
       try {
         ShellUtils.tokenize(tokens, str);
-        if (tokens.size() > 1) {
-          ruleContext.attributeWarning("copts",
-              "each item in the list should contain only one option");
-        }
       } catch (ShellUtils.TokenizationException e) {
         // ignore, the error is reported in the getAttributeCopts call
       }


Test patch:
diff --git a/src/test/java/com/google/devtools/build/lib/rules/cpp/CcCommonTest.java b/src/test/java/com/google/devtools/build/lib/rules/cpp/CcCommonTest.java
index 2ff18b43797a28..5f2a3fddeb8ce3 100644
--- a/src/test/java/com/google/devtools/build/lib/rules/cpp/CcCommonTest.java
+++ b/src/test/java/com/google/devtools/build/lib/rules/cpp/CcCommonTest.java
@@ -160,7 +160,6 @@ public void testCoptsTokenization() throws Exception {
         "    copts = ['-Wmy-warning -frun-faster'])");
     List<String> copts = getCopts("//copts:c_lib");
     assertThat(copts).containsAllOf("-Wmy-warning", "-frun-faster");
-    assertContainsEvent("each item in the list should contain only one option");
   }
 
   @Test