Skip to content

Commit 9608c4d

Browse files
[Mono.Android] Enumify, stabilize API-37.2 (#12633)
Context: 1162306 Context: https://github.com/jpobst/BindingStudio Context: #10005 Commit 1162306 mentioned: > Step 1: bind it! > Step 2: Enumify it, make stable. This is Step 2 for API-37.2. Use jpobst/BindingStudio to enumify API-37.2. Note: current dotnet/java-interop emits an "extra" `,` on `map.csv` output, which would make for a "noisy" diff (every line changed!). The diff size is reduced by removing trailing commas: tr -d '\r' < src/Mono.Android/map.csv > src/Mono.Android/new-map.csv sed 's/,$//' < src/Mono.Android/new-map.csv > src/Mono.Android/map.csv This keeps the diff to a reasonable size. Sanity check: during enumification, this should have no matches: git grep '\.[A-Z][a-z]\.' src/Mono.Android/map.csv Two-letter namespace parts should be all upper-case. TODO (lol): update `map.csv` to current BindingStudio output after this is merged. Additionally, rename the following Java package parts: * `contentsafety` => `ContentSafety` * `personalcontext` => `PersonalContext` * `multisensory` => `MultiSensory` * `authenticationpolicy` => `AuthenticationPolicy` For example, Java `android.service.personalcontext` becomes C# `Android.Service.PersonalContext`. Furthermore, for "methodmap.csv", BindingStudio emits JNI names with `/` as the package-part separator, not Java names with `.` as the separator. Please remember the instructions to manually fix this as mentioned in `HowToAddNewApiLevel.md`. Finally (?), as *mentioned* in `HowToAddNewApiLevel`, update manifest-attribute-codegen by running: ./dotnet-local.sh build -t:GenerateManifestAttributes build-tools/manifest-attribute-codegen/manifest-attribute-codegen.csproj Co-authored-by: Jonathan Peppers <jonathan.peppers@microsoft.com>
1 parent b4f3cd0 commit 9608c4d

6 files changed

Lines changed: 489 additions & 48 deletions

File tree

Configuration.props

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@
2525
<AndroidLatestStablePlatformId Condition="'$(AndroidLatestStablePlatformId)' == ''">37.0</AndroidLatestStablePlatformId>
2626
<AndroidLatestStableFrameworkVersion Condition="'$(AndroidLatestStableFrameworkVersion)'==''">v17.0</AndroidLatestStableFrameworkVersion>
2727
<!-- If there is a second *stable* API level (e.g. 38.1 alongside 38), set it here: -->
28-
<AndroidLatestStableApiLevel2 Condition="'$(AndroidLatestStableApiLevel2)' == ''">37.1</AndroidLatestStableApiLevel2>
28+
<AndroidLatestStableApiLevel2 Condition="'$(AndroidLatestStableApiLevel2)' == ''">37.2</AndroidLatestStableApiLevel2>
2929
<!-- *Latest* *unstable* API level binding that we support; this can be the same as *stable* -->
3030
<AndroidLatestUnstableApiLevel Condition="'$(AndroidLatestUnstableApiLevel)' == ''">37.2</AndroidLatestUnstableApiLevel>
3131
<AndroidLatestUnstablePlatformId Condition="'$(AndroidLatestUnstablePlatformId)' == ''">37.2</AndroidLatestUnstablePlatformId>
@@ -56,7 +56,7 @@
5656
<AndroidBuildApiLevel Include="37.2">
5757
<PlatformId>37.2</PlatformId>
5858
<FrameworkVersion>v17.2</FrameworkVersion>
59-
<Unstable>true</Unstable>
59+
<Unstable>false</Unstable>
6060
</AndroidBuildApiLevel>
6161
</ItemGroup>
6262
<PropertyGroup Condition=" '$(HostOS)' == '' ">

Documentation/workflow/HowToAddNewApiLevel.md

Lines changed: 30 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -474,16 +474,39 @@ BindingStudio crashes.
474474
475475
The left tree view can be updated by saving and reopening the `map.csv` file.
476476
477-
Once `map.csv` has been updated, run the following command:
477+
Once `map.csv` has been updated, run the following commands:
478478
479479
```sh
480+
# BindingStudio currently produces a slightly different CSV format.
481+
# "Update" to what's currently in git(1) to reduce diff size.
482+
tr -d '\r' < src/Mono.Android/map.csv > src/Mono.Android/new-map.csv
483+
sed 's/,$//' < src/Mono.Android/new-map.csv > src/Mono.Android/map.csv
484+
485+
# Check for two-letter package parts.
480486
git grep '\.[A-Z][a-z]\.' src/Mono.Android/map.csv
481487
```
482488
483489
This checks for any namespace-parts which are two letters long, the first letter is
484490
upper-case, and the second letter is lower-case, e.g. `.Pm.`. These should be all
485491
upper-case, e.g. `.PM.`.
486492
493+
See the next section on how to rename Java "package parts".
494+
495+
### PascalCase new namespaces
496+
497+
If you have the "Android API Differences Report", e.g.
498+
[this one for API-37.2 vs. API-37.1](https://developer.android.com/sdk/api_diff/37.2/changes),
499+
review the **Added Packages** section for *new* packages, and consider PascalCasing them.
500+
501+
PascalCasing namespaces requires changes to three places:
502+
503+
1. Add `<ns-replace/>` elements to [`src/Mono.Android/metadata`](../../src/Mono.Android/metadata).
504+
2. [`src/Mono.Android/map.csv`](../../src/Mono.Android/map.csv) will need to be updated to match (1).
505+
2. [`src/Mono.Android/methodmap.csv`](../../src/Mono.Android/methodmap.csv) will need to be updated to match (1).
506+
507+
As BindingStudio doesn't know about `<ns-replace/>`, it is recommended that namespace renames
508+
be done after enum creation.
509+
487510
### Extract methods that possibly need enums
488511
489512
Using BindingStudio:
@@ -562,12 +585,14 @@ the `csv` variable within `MainForm.FindAPILevelMethodsToolStripMenuItem_Click`.
562585
Once this process is complete, use `Tools` -> `Export Final Method Map`, and create a *new*
563586
`.csv` file, e.g. `new-methodmap.csv`.
564587
565-
Note: `new-methodmap.csv` will likely use JNI syntax for package names, e.g. `android/widget`.
566-
`methodmap.csv` ***must*** use *Java* syntax for package names, e.g. `android.widget`.
567-
Use **sed**(1) to fix package names and nested class names:
588+
Note: `new-methodmap.csv` will likely use JNI syntax for package names, e.g. `android/widget`,
589+
and contain a leading action column. `methodmap.csv` ***must*** contain only the enumified rows,
590+
without the action column, and use *Java* syntax for package names, e.g. `android.widget`.
591+
Use **grep**(1) and **sed**(1) to normalize the output:
568592
569593
```sh
570-
sed 's,/,.,g;s/\$/./g' < src/Mono.Android/new-methodmap.csv > src/Mono.Android/new-methodmap2.csv
594+
grep '^E,' src/Mono.Android/new-methodmap.csv |
595+
sed 's/^E,//;s,/,.,g;s/\$/./g' > src/Mono.Android/new-methodmap2.csv
571596
```
572597
573598
Copy the contents of `new-methodmap2.csv` and *append* to `src/Mono.Android/methodmap.csv`.

build-tools/manifest-attribute-codegen/manifest-definition.xml

Lines changed: 41 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -95,14 +95,14 @@
9595
<a name='resetEnabledSettingsOnAppDataCleared' format='boolean' api-level='33' />
9696
<a name='knownActivityEmbeddingCerts' api-level='33' />
9797
<a name='enableOnBackInvokedCallback' format='boolean' api-level='33' />
98-
<a name='allowCrossUidActivitySwitchFromBelow' format='boolean' api-level='35' />
98+
<a name='allowCrossUidActivitySwitchFromBelow' format='boolean' api-level='35-2' />
9999
<a name='pageSizeCompat' api-level='36.1' />
100100
<a name='intentMatchingFlags' api-level='36.1' />
101101
<a name='alternateLauncherIcons' format='reference' api-level='36.1' />
102102
<a name='alternateLauncherLabels' format='reference' api-level='36.1' />
103-
<a name='backupAgentProcess' api-level='37.0' />
104-
<a name='zygotePreloadNativeLib' api-level='37.0' />
105-
<a name='zygotePreloadNativeFunc' api-level='37.0' />
103+
<a name='backupAgentProcess' api-level='37.0-2' />
104+
<a name='zygotePreloadNativeLib' api-level='37.0-2' />
105+
<a name='zygotePreloadNativeFunc' api-level='37.0-2' />
106106
</e>
107107
<e name='permission' api-level='10'>
108108
<parent>manifest</parent>
@@ -122,8 +122,8 @@
122122
<a name='maxSdkVersion' api-level='34' />
123123
<a name='requiresPurpose' format='boolean' api-level='36.1' />
124124
<a name='requiresPurposeTargetSdkVersion' format='integer' api-level='36.1' />
125-
<a name='requiresGeneralPurposeTargetSdkVersion' format='integer' api-level='37.0' />
126-
<a name='requiresPurposeStringTargetSdkVersion' format='integer' api-level='37.0' />
125+
<a name='requiresGeneralPurposeTargetSdkVersion' format='integer' api-level='37.0-2' />
126+
<a name='requiresPurposeStringTargetSdkVersion' format='integer' api-level='37.0-2' />
127127
</e>
128128
<e name='permission-group' api-level='10'>
129129
<parent>manifest</parent>
@@ -158,7 +158,7 @@
158158
<a name='requiredNotFeature' format='string' api-level='26' />
159159
<a name='usesPermissionFlags' api-level='31' />
160160
<a name='minSdkVersion' format='integer|string' api-level='34' />
161-
<a name='purposeString' format='reference' api-level='37.0' />
161+
<a name='purposeString' format='reference' api-level='37.0-2' />
162162
</e>
163163
<e name='uses-configuration' api-level='10'>
164164
<parent>manifest</parent>
@@ -233,9 +233,9 @@
233233
<a name='splitName' api-level='26' />
234234
<a name='forceUriPermissions' api-level='29' />
235235
<a name='attributionTags' api-level='31' />
236-
<a name='systemUserOnly' format='boolean' api-level='35' />
236+
<a name='systemUserOnly' format='boolean' api-level='35-2' />
237237
<a name='intentMatchingFlags' api-level='36.1' />
238-
<a name='privateComputeCore' api-level='37.0' />
238+
<a name='privateComputeCore' api-level='37.0-2' />
239239
</e>
240240
<e name='grant-uri-permission' api-level='10'>
241241
<parent>provider</parent>
@@ -280,10 +280,10 @@
280280
<a name='foregroundServiceType' api-level='29' />
281281
<a name='attributionTags' api-level='31' />
282282
<a name='allowSharedIsolatedProcess' format='boolean' api-level='34' />
283-
<a name='systemUserOnly' format='boolean' api-level='35' />
283+
<a name='systemUserOnly' format='boolean' api-level='35-2' />
284284
<a name='intentMatchingFlags' api-level='36.1' />
285-
<a name='privateComputeCore' api-level='37.0' />
286-
<a name='nativeService' format='boolean' api-level='37.0' />
285+
<a name='privateComputeCore' api-level='37.0-2' />
286+
<a name='nativeService' format='boolean' api-level='37.0-2' />
287287
</e>
288288
<e name='receiver' api-level='10'>
289289
<parent>application</parent>
@@ -302,7 +302,7 @@
302302
<a name='roundIcon' api-level='25' />
303303
<a name='attributionTags' api-level='31' />
304304
<a name='intentMatchingFlags' api-level='36.1' />
305-
<a name='privateComputeCore' api-level='37.0' />
305+
<a name='privateComputeCore' api-level='37.0-2' />
306306
</e>
307307
<e name='activity' api-level='10'>
308308
<parent>application</parent>
@@ -373,9 +373,9 @@
373373
<a name='knownActivityEmbeddingCerts' api-level='33' />
374374
<a name='requiredDisplayCategory' format='string' api-level='34' />
375375
<a name='enableOnBackInvokedCallback' format='boolean' api-level='34' />
376-
<a name='requireContentUriPermissionFromCaller' format='string' api-level='35' />
376+
<a name='requireContentUriPermissionFromCaller' format='string' api-level='35-2' />
377377
<a name='intentMatchingFlags' api-level='36.1' />
378-
<a name='privateComputeCore' api-level='37.0' />
378+
<a name='privateComputeCore' api-level='37.0-2' />
379379
</e>
380380
<e name='activity-alias' api-level='10'>
381381
<parent>application</parent>
@@ -395,7 +395,7 @@
395395
<a name='allowUntrustedActivityEmbedding' api-level='33' />
396396
<a name='knownActivityEmbeddingCerts' api-level='33' />
397397
<a name='intentMatchingFlags' api-level='36.1' />
398-
<a name='privateComputeCore' api-level='37.0' />
398+
<a name='privateComputeCore' api-level='37.0-2' />
399399
</e>
400400
<e name='meta-data' api-level='10'>
401401
<parent>application</parent>
@@ -444,16 +444,16 @@
444444
<a name='sspAdvancedPattern' format='string' api-level='31' />
445445
<a name='sspSuffix' format='string' api-level='31' />
446446
<a name='pathSuffix' api-level='31' />
447-
<a name='query' format='string' api-level='35' />
448-
<a name='queryPrefix' format='string' api-level='35' />
449-
<a name='queryPattern' format='string' api-level='35' />
450-
<a name='queryAdvancedPattern' format='string' api-level='35' />
451-
<a name='querySuffix' format='string' api-level='35' />
452-
<a name='fragment' format='string' api-level='35' />
453-
<a name='fragmentPrefix' format='string' api-level='35' />
454-
<a name='fragmentPattern' format='string' api-level='35' />
455-
<a name='fragmentAdvancedPattern' format='string' api-level='35' />
456-
<a name='fragmentSuffix' format='string' api-level='35' />
447+
<a name='query' format='string' api-level='35-2' />
448+
<a name='queryPrefix' format='string' api-level='35-2' />
449+
<a name='queryPattern' format='string' api-level='35-2' />
450+
<a name='queryAdvancedPattern' format='string' api-level='35-2' />
451+
<a name='querySuffix' format='string' api-level='35-2' />
452+
<a name='fragment' format='string' api-level='35-2' />
453+
<a name='fragmentPrefix' format='string' api-level='35-2' />
454+
<a name='fragmentPattern' format='string' api-level='35-2' />
455+
<a name='fragmentAdvancedPattern' format='string' api-level='35-2' />
456+
<a name='fragmentSuffix' format='string' api-level='35-2' />
457457
</e>
458458
<e name='category' api-level='10'>
459459
<parent>intent-filter</parent>
@@ -618,7 +618,7 @@
618618
<a name='memtagMode' api-level='31' />
619619
<a name='nativeHeapZeroInitialized' api-level='31' />
620620
<a name='name' api-level='33' />
621-
<a name='useEmbeddedDex' api-level='35' />
621+
<a name='useEmbeddedDex' api-level='35-2' />
622622
<a name='singleUser' api-level='37.1' />
623623
</e>
624624
<e name='deny-permission' api-level='30'>
@@ -660,7 +660,7 @@
660660
<a name='name' api-level='33' />
661661
<a name='versionMajor' format='integer' api-level='33' />
662662
<a name='certDigest' format='string' api-level='33' />
663-
<a name='optional' format='boolean' api-level='35' />
663+
<a name='optional' format='boolean' api-level='35-2' />
664664
</e>
665665
<e name='apex-system-service' api-level='33'>
666666
<parent>application</parent>
@@ -677,9 +677,9 @@
677677
<parent>install-constraints</parent>
678678
<a name='value' api-level='34' />
679679
</e>
680-
<e name='uri-relative-filter-group' api-level='35'>
680+
<e name='uri-relative-filter-group' api-level='35-2'>
681681
<parent>intent-filter</parent>
682-
<a name='allow' format='boolean' api-level='35' />
682+
<a name='allow' format='boolean' api-level='35-2' />
683683
</e>
684684
<e name='valid-purpose' api-level='36.1'>
685685
<parent>permission</parent>
@@ -696,24 +696,24 @@
696696
<parent>manifest</parent>
697697
<a name='name' api-level='36.1' />
698698
</e>
699-
<e name='valid-general-purpose' api-level='37.0'>
699+
<e name='valid-general-purpose' api-level='37.0-2'>
700700
<parent>permission</parent>
701-
<a name='name' format='string' api-level='37.0' />
702-
<a name='maxTargetSdkVersion' format='integer' api-level='37.0' />
701+
<a name='name' format='string' api-level='37.0-2' />
702+
<a name='maxTargetSdkVersion' format='integer' api-level='37.0-2' />
703703
</e>
704-
<e name='general-purpose' api-level='37.0'>
704+
<e name='general-purpose' api-level='37.0-2'>
705705
<parent>uses-permission</parent>
706-
<a name='name' format='string' api-level='37.0' />
707-
<a name='minSdkVersion' format='integer|string' api-level='37.0' />
708-
<a name='maxSdkVersion' format='integer' api-level='37.0' />
706+
<a name='name' format='string' api-level='37.0-2' />
707+
<a name='minSdkVersion' format='integer|string' api-level='37.0-2' />
708+
<a name='maxSdkVersion' format='integer' api-level='37.0-2' />
709709
</e>
710-
<e name='allow-component-access' api-level='37.0'>
710+
<e name='allow-component-access' api-level='37.0-2'>
711711
<parent>manifest</parent>
712712
</e>
713-
<e name='allow-component-access-package' api-level='37.0'>
713+
<e name='allow-component-access-package' api-level='37.0-2'>
714714
<parent>allow-component-access</parent>
715-
<a name='name' api-level='37.0' />
716-
<a name='certDigest' format='string' api-level='37.0' />
715+
<a name='name' api-level='37.0-2' />
716+
<a name='certDigest' format='string' api-level='37.0-2' />
717717
</e>
718718
<e name='memory-budget' api-level='37.1'>
719719
<parent>application</parent>

0 commit comments

Comments
 (0)