Skip to content

Commit 0a7cf49

Browse files
xaionaro@dx.centerxaionaro@dx.center
authored andcommitted
feat: codegen auto-fills identity params from CallerIdentity
The AIDL code generator now recognizes specific parameter names (callingPackage, opPackageName, attributionTag, callingFeatureId, userId, userHandle, callingUserId, callingPid, appPid, callingUid, appUid) as caller-identity parameters. These are omitted from proxy method signatures and automatically filled from p.remote.Identity() in the method body. The interface type retains all parameters since server implementations need them.
1 parent 903e487 commit 0a7cf49

3 files changed

Lines changed: 462 additions & 3 deletions

File tree

Lines changed: 98 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,98 @@
1+
package codegen
2+
3+
import (
4+
"github.com/xaionaro-go/binder/tools/pkg/parser"
5+
)
6+
7+
// identityParamMapping associates an AIDL parameter name with the
8+
// CallerIdentity field it corresponds to and the AIDL type that must match.
9+
type identityParamMapping struct {
10+
// IdentityField is the CallerIdentity struct field name
11+
// (e.g. "PackageName", "UID").
12+
IdentityField string
13+
14+
// AIDLType is the AIDL type the parameter must have for the mapping
15+
// to apply (e.g. "String" for PackageName, "int" for UID).
16+
AIDLType string
17+
}
18+
19+
// identityParamNames maps AIDL parameter names to their CallerIdentity field
20+
// mappings. Only unambiguously caller-identity names are included;
21+
// names like "packageName" are excluded because they may refer to a
22+
// target package rather than the calling package.
23+
var identityParamNames = map[string]identityParamMapping{
24+
// PackageName — the calling app's package name.
25+
"callingPackage": {IdentityField: "PackageName", AIDLType: "String"},
26+
"opPackageName": {IdentityField: "PackageName", AIDLType: "String"},
27+
28+
// AttributionTag — the calling feature / attribution tag.
29+
"attributionTag": {IdentityField: "AttributionTag", AIDLType: "String"},
30+
"callingFeatureId": {IdentityField: "AttributionTag", AIDLType: "String"},
31+
32+
// UserID — the Android user ID of the caller.
33+
"userId": {IdentityField: "UserID", AIDLType: "int"},
34+
"userHandle": {IdentityField: "UserID", AIDLType: "int"},
35+
"callingUserId": {IdentityField: "UserID", AIDLType: "int"},
36+
37+
// PID — the process ID of the caller.
38+
"callingPid": {IdentityField: "PID", AIDLType: "int"},
39+
"appPid": {IdentityField: "PID", AIDLType: "int"},
40+
41+
// UID — the user ID (Linux UID) of the caller.
42+
"callingUid": {IdentityField: "UID", AIDLType: "int"},
43+
"appUid": {IdentityField: "UID", AIDLType: "int"},
44+
}
45+
46+
// identityFieldForParam returns the CallerIdentity field name that the given
47+
// AIDL parameter maps to, or "" if the parameter is not an identity param.
48+
// Matching is based on both the AIDL parameter name and its type.
49+
func identityFieldForParam(param *parser.ParamDecl) string {
50+
mapping, ok := identityParamNames[param.ParamName]
51+
if !ok {
52+
return ""
53+
}
54+
55+
if param.Type == nil {
56+
return ""
57+
}
58+
59+
// Only match simple (non-array, non-generic) types.
60+
if param.Type.IsArray || len(param.Type.TypeArgs) > 0 {
61+
return ""
62+
}
63+
64+
if param.Type.Name != mapping.AIDLType {
65+
return ""
66+
}
67+
68+
return mapping.IdentityField
69+
}
70+
71+
// identityWriteExpr maps AIDL types used in identity parameters to
72+
// the parcel write expression format string. The %s placeholder is
73+
// replaced with the value expression (e.g. "_identity.PackageName").
74+
var identityWriteExpr = map[string]string{
75+
"String": "_data.WriteString16(%s)",
76+
"int": "_data.WriteInt32(%s)",
77+
}
78+
79+
// classifyParams separates method parameters into regular parameters and
80+
// identity-auto-filled parameters. For each identity parameter, it records
81+
// which CallerIdentity field to use and the original parameter for parcel
82+
// serialization.
83+
func classifyParams(
84+
params []*parser.ParamDecl,
85+
) (regular []*parser.ParamDecl, identity map[int]string) {
86+
identity = make(map[int]string)
87+
88+
for i, param := range params {
89+
field := identityFieldForParam(param)
90+
if field == "" {
91+
regular = append(regular, param)
92+
continue
93+
}
94+
identity[i] = field
95+
}
96+
97+
return regular, identity
98+
}

0 commit comments

Comments
 (0)