Skip to content

Commit eb08bb4

Browse files
authored
[Mono.Android] Support API-O Rebuilds (#579)
*Rebuilding* API-O (571546a) results in a build failure: # First build is fine: $ make framework-assemblies API_LEVELS=26 CONFIGURATIONS=Debug # Second+ builds are not: $ make framework-assemblies API_LEVELS=26 CONFIGURATIONS=Debug ... obj/Debug/android-26/mcw/Android.Content.IComponentCallbacks.cs(23,17): error CS0101: The namespace 'Android.Content' already contains a definition for 'IComponentCallbacksInvoker' ... 170582 Error(s) The cause of the build error is that `Android.Content.IComponentCallbacks.cs` -- among many other files -- *is* specified twice (!): * obj/Debug/android-26/mcw//Android.Content.IComponentCallbacks.cs * full/path/to/…/xamarin-android/src/Mono.Android/obj/Debug/android-26/mcw//Android.Content.IComponentCallbacks.cs This in turn is related to 98880bd: There are two "environments" in which `Mono.Android.csproj` is built: * A "clean" environment * A previously built environment In the clean environment, `Mono.Android.projitems` -- created by `generator.exe` in the `_GenerateBinding` target -- does not exist. Consequently, after `generator.exe` is run, all of the generated `$(IntermediateOutputPath)\**\*.cs` files are added to `@(Compile)` so that the compiler will "see" all of the generated files and things will build. In the previously built environment, `Mono.Android.projitems` *does* exist, and is `<Import/>`ed. The `_GenerateBinding` target is *skipped*, "preventing" the `@(Compile)` group from being updated to contain the generated files -- which is desirable, because those files are already listed in `Mono.Android.projitems`, and including them would result in "duplicating" the files provided to the compiler. Note that the `_GenerateBinding` target depends on the `_GenerateApiDescription` target, so that when `_GenerateApiDescription` creates an `api.xml` file, then `_GenerateBinding` will *re-execute*. This is where API-O rebuilds go wrong: 1. This is a previously built environment, so `Mono.Android.projitems` (1) exists, and (2) is `<Import/>`ed. 2. The `_GenerateApiDescription` always executes (!). 3. (2) results in `_GenerateBinding` always executing, causing the `@(Compile)` group to be updated, resulting filenames being provided to the compiler *twice*. (2) is where things go bad: Target _GenerateApiDescription needs to be built as input file 'Profiles/api-26.xml.in' does not exist. Specifically, `_GenerateApiDescription` listed as an `Input` the file `Profiles\api-$(AndroidApiLevel).xml.in`. However, commit 571546a named the API-O binding `Profiles\api-O.xml.in`, meaning `Profiles\api-26.xml.in` does not exist, *and won't exist* (until API-26 is actually released as "stable" by Google, at some unknown point in the future). Which is why API-O rebuilds fail. :-) The fix? Don't use `$(AndroidApiLevel)`, use `$(AndroidPlatformId)`. For API-O, `$(AndroidPlatformId)` will have the value "O", allowing `Profiles\api-O.xml.in` to be found, preventing `_GenerateApiDescription` from unnecessarily executing. --- This scenario *does* raise a potential (unresolved) workflow problem: when: 1. `Mono.Android.csproj` is built, and 2. `Profiles\api-*.xml.in` is modified, and 3. `Mono.Android.csproj` is built again, then everything will break in the same manner as described here: `Mono.Android.projitems` will exist, thus adding generated files to `@(Compile)`, then the `_GenerateApiDescription` & `_GenerateBinding` targets will execute, re-adding files to `@(Compile)`, and things will break. A subsequent rebuild will "fix" the error, so long as a `Profiles\api-*.xml.in` file isn't modified, but this will be annoying to anyone who encounters it.
1 parent 6829b7d commit eb08bb4

File tree

1 file changed

+2
-2
lines changed

1 file changed

+2
-2
lines changed

src/Mono.Android/Mono.Android.targets

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -47,14 +47,14 @@
4747
</ItemGroup>
4848
<Target Name="_GenerateApiDescription"
4949
BeforeTargets="_GenerateBinding"
50-
Inputs="Profiles\api-$(AndroidApiLevel).xml.in"
50+
Inputs="Profiles\api-$(AndroidPlatformId).xml.in"
5151
Outputs="$(IntermediateOutputPath)mcw\api.xml">
5252
<MakeDir Directories="$(IntermediateOutputPath)mcw" />
5353
<PropertyGroup>
5454
<ApiMerge>..\..\bin\Build$(Configuration)\api-merge.exe</ApiMerge>
5555
<_Profiles>@(_AndroidProfile->'%(Identity)', ' ')</_Profiles>
5656
<_Glob>-s 'Profiles\api-*.xml.in'</_Glob>
57-
<_LastProfile>--last-description=Profiles\api-$(AndroidApiLevel).xml.in</_LastProfile>
57+
<_LastProfile>--last-description=Profiles\api-$(AndroidPlatformId).xml.in</_LastProfile>
5858
<_Out>-o "$(IntermediateOutputPath)mcw\api.xml"</_Out>
5959
</PropertyGroup>
6060
<Exec

0 commit comments

Comments
 (0)