Skip to content

Commit 2919281

Browse files
bzbarsky-applepull[bot]
authored andcommitted
Make attributes whose values are lists of structs that have nullables/optionals at least compile. (#11105)
This doesn't give us correct behavior across all of our bindings (chip-tool command line, yaml, darwin, python, java). But it at least allows code generation to produce output and allows that output to compile. More work is needed to address the various TODO issues.
1 parent 974b1e4 commit 2919281

File tree

28 files changed

+1116
-249
lines changed

28 files changed

+1116
-249
lines changed

examples/all-clusters-app/all-clusters-common/all-clusters-app.zap

+15
Original file line numberDiff line numberDiff line change
@@ -15486,6 +15486,21 @@
1548615486
"maxInterval": 65534,
1548715487
"reportableChange": 0
1548815488
},
15489+
{
15490+
"name": "list_nullables_and_optionals_struct",
15491+
"code": 35,
15492+
"mfgCode": null,
15493+
"side": "server",
15494+
"included": 1,
15495+
"storageOption": "External",
15496+
"singleton": 0,
15497+
"bounded": 0,
15498+
"defaultValue": "",
15499+
"reportable": 0,
15500+
"minInterval": 1,
15501+
"maxInterval": 65534,
15502+
"reportableChange": 0
15503+
},
1548915504
{
1549015505
"name": "ClusterRevision",
1549115506
"code": 65533,

examples/chip-tool/templates/commands.zapt

+28-6
Original file line numberDiff line numberDiff line change
@@ -151,19 +151,40 @@ static void On{{asUpperCamelCase parent.name}}{{asUpperCamelCase name}}ListAttri
151151
uint16_t i = 0;
152152
while (iter.Next())
153153
{
154+
++i;
154155
#if CHIP_PROGRESS_LOGGING
155156
auto & entry = iter.GetValue();
156-
#endif // CHIP_PROGRESS_LOGGING
157-
++i;
158157
{{#if isStruct}}
159158
ChipLogProgress(chipTool, "{{type}}[%" PRIu16 "]:", i);
160159
{{#chip_attribute_list_entryTypes}}
161-
{{#if (isOctetString type)}}
162-
ChipLogProgress(Zcl, " {{asSymbol label}}: %zu", entry.{{asLowerCamelCase name}}.size());
160+
{{~#*inline "field"}}entry.{{asLowerCamelCase name}}{{#if isOptional}}.Value(){{/if}}{{/inline~}}
161+
{{~#*inline "fieldValue"}}{{>field}}{{#if isNullable}}.Value(){{/if}}{{/inline~}}
162+
{{#if isOptional}}
163+
if (entry.{{asLowerCamelCase name}}.HasValue()) {
164+
{{/if}}
165+
{{#if isNullable}}
166+
if ({{>field}}.IsNull()) {
167+
ChipLogProgress(chipTool, " {{asSymbol label}}: null");
168+
} else {
169+
{{/if}}
170+
{{#if isArray}}
171+
{{! TODO: Add support for printing list member of struct element of list attribute }}
172+
ChipLogProgress(chipTool, " {{asSymbol label}}: list member of struct element of list attribute printing not supported yet");
173+
{{else if (isOctetString type)}}
174+
ChipLogProgress(Zcl, " {{asSymbol label}}: %zu", {{>fieldValue}}.size());
163175
{{else if (isCharString type)}}
164-
ChipLogProgress(Zcl, " {{asSymbol label}}: %.*s", static_cast<int>(entry.{{asLowerCamelCase name}}.size()), entry.{{asLowerCamelCase name}}.data());
176+
ChipLogProgress(Zcl, " {{asSymbol label}}: %.*s", static_cast<int>({{>fieldValue}}.size()), {{>fieldValue}}.data());
177+
{{else if isStruct}}
178+
{{! TODO: Add support for printing struct member of struct element of list attribute }}
179+
ChipLogProgress(chipTool, " {{asSymbol label}}: struct member of struct element of list attribute printing not supported yet");
165180
{{else}}
166-
ChipLogProgress(chipTool, " {{asLowerCamelCase name}}: {{asPrintFormat type}}", entry.{{asLowerCamelCase name}});
181+
ChipLogProgress(chipTool, " {{asSymbol label}}: {{asPrintFormat type}}", {{>fieldValue}});
182+
{{/if}}
183+
{{#if isNullable}}
184+
}
185+
{{/if}}
186+
{{#if isOptional}}
187+
}
167188
{{/if}}
168189
{{/chip_attribute_list_entryTypes}}
169190
{{else}}
@@ -175,6 +196,7 @@ static void On{{asUpperCamelCase parent.name}}{{asUpperCamelCase name}}ListAttri
175196
ChipLogProgress(chipTool, "{{type}}[%" PRIu16 "]: {{asPrintFormat type}}", i, entry);
176197
{{/if}}
177198
{{/if}}
199+
#endif // CHIP_PROGRESS_LOGGING
178200
}
179201
command->SetCommandExitStatus(iter.GetStatus());
180202
}

src/app/clusters/test-cluster-server/test-cluster-server.cpp

+16
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,7 @@ class TestAttrAccess : public AttributeAccessInterface
5858
CHIP_ERROR ReadListInt8uAttribute(AttributeValueEncoder & aEncoder);
5959
CHIP_ERROR ReadListOctetStringAttribute(AttributeValueEncoder & aEncoder);
6060
CHIP_ERROR ReadListStructOctetStringAttribute(AttributeValueEncoder & aEncoder);
61+
CHIP_ERROR ReadListNullablesAndOptionalsStructAttribute(AttributeValueEncoder & aEncoder);
6162
};
6263

6364
TestAttrAccess gAttrAccess;
@@ -75,6 +76,9 @@ CHIP_ERROR TestAttrAccess::Read(const ConcreteAttributePath & aPath, AttributeVa
7576
case ListStructOctetString::Id: {
7677
return ReadListStructOctetStringAttribute(aEncoder);
7778
}
79+
case ListNullablesAndOptionalsStruct::Id: {
80+
return ReadListNullablesAndOptionalsStructAttribute(aEncoder);
81+
}
7882
default: {
7983
break;
8084
}
@@ -221,6 +225,18 @@ CHIP_ERROR TestAttrAccess::ReadListStructOctetStringAttribute(AttributeValueEnco
221225
return CHIP_NO_ERROR;
222226
});
223227
}
228+
229+
CHIP_ERROR TestAttrAccess::ReadListNullablesAndOptionalsStructAttribute(AttributeValueEncoder & aEncoder)
230+
{
231+
return aEncoder.EncodeList([](const TagBoundEncoder & encoder) -> CHIP_ERROR {
232+
// Just encode a single default-initialized
233+
// entry for now.
234+
Structs::NullablesAndOptionalsStruct::Type entry;
235+
ReturnErrorOnFailure(encoder.Encode(entry));
236+
return CHIP_NO_ERROR;
237+
});
238+
}
239+
224240
} // namespace
225241

226242
bool emberAfTestClusterClusterTestCallback(app::CommandHandler *, const app::ConcreteCommandPath & commandPath,

src/app/zap-templates/zcl/data-model/chip/test-cluster.xml

+2
Original file line numberDiff line numberDiff line change
@@ -135,6 +135,8 @@ limitations under the License.
135135
<attribute side="server" code="0x0021" define="EPOCH_S" type="EPOCH_S" writable="true" optional="false">epoch_s</attribute>
136136
<attribute side="server" code="0x0022" define="TEST_VENDOR_ID" type="vendor_id"
137137
writable="true" optional="false" default="0">vendor_id</attribute>
138+
<attribute side="server" code="0x0023" define="LIST_OF_STRUCTS_WITH_OPTIONALS" type="ARRAY" entryType="NullablesAndOptionalsStruct"
139+
writable="false" optional="false">list_nullables_and_optionals_struct</attribute>
138140
<!-- Can't enable the SimpleEnum test until we stop force-lowercasing
139141
attribute types in ZAP -->
140142
<!--<attribute side="server" code="0x0023" define="SIMPLE_ENUM" type="SimpleEnum" writable="true" optional="false">simple_enum</attribute>-->

src/controller/data_model/controller-clusters.zap

+15
Original file line numberDiff line numberDiff line change
@@ -11699,6 +11699,21 @@
1169911699
"maxInterval": 65534,
1170011700
"reportableChange": 0
1170111701
},
11702+
{
11703+
"name": "list_nullables_and_optionals_struct",
11704+
"code": 35,
11705+
"mfgCode": null,
11706+
"side": "server",
11707+
"included": 1,
11708+
"storageOption": "RAM",
11709+
"singleton": 0,
11710+
"bounded": 0,
11711+
"defaultValue": "",
11712+
"reportable": 0,
11713+
"minInterval": 1,
11714+
"maxInterval": 65534,
11715+
"reportableChange": 0
11716+
},
1170211717
{
1170311718
"name": "unsupported",
1170411719
"code": 255,

src/controller/java/templates/CHIPClusters-JNI.zapt

+23-4
Original file line numberDiff line numberDiff line change
@@ -448,7 +448,7 @@ class CHIP{{asUpperCamelCase parent.name}}{{asUpperCamelCase name}}AttributeCall
448448
VerifyOrReturn(err == CHIP_NO_ERROR, ChipLogError(Zcl, "Could not find class chip/devicecontroller/ChipClusters${{asUpperCamelCase parent.name}}Cluster${{asUpperCamelCase name}}Attribute"));
449449
JniClass attributeJniClass(attributeClass);
450450
jmethodID attributeCtor = env->GetMethodID(attributeClass, "<init>"
451-
, "({{#chip_attribute_list_entryTypes}}{{#if (isString type)}}{{#if (isOctetString type)}}[B{{else}}Ljava/lang/String;{{/if}}{{else}}{{asJniSignature type}}{{/if}}{{/chip_attribute_list_entryTypes}})V");
451+
, "({{#chip_attribute_list_entryTypes}}{{#if isOptional}}{{! TODO: Add support for optional types here }}{{else if isNullable}}{{! TODO: Add support for nullable types here }}{{else if isArray}}{{! TODO: Add support for lists here }}{{else if isStruct}}{{! TODO: Add support for structs here }}{{else if (isString type)}}{{#if (isOctetString type)}}[B{{else}}Ljava/lang/String;{{/if}}{{else}}{{asJniSignature type}}{{/if}}{{/chip_attribute_list_entryTypes}})V");
452452
VerifyOrReturn(attributeCtor != nullptr, ChipLogError(Zcl, "Could not find {{asUpperCamelCase name}}Attribute constructor"));
453453
{{/if}}
454454

@@ -457,8 +457,17 @@ class CHIP{{asUpperCamelCase parent.name}}{{asUpperCamelCase name}}AttributeCall
457457
{
458458
auto & entry = iter.GetValue();
459459
{{#if isStruct}}
460+
(void)entry; {{! In case all our struct members are not supported yet }}
460461
{{#chip_attribute_list_entryTypes}}
461-
{{#if (isOctetString type)}}
462+
{{#if isOptional}}
463+
{{! TODO: Add support for optional types here }}
464+
{{else if isNullable}}
465+
{{! TODO: Add support for nullable types here }}
466+
{{else if isArray}}
467+
{{! TODO: Add support for lists here }}
468+
{{else if isStruct}}
469+
{{! TODO: Add support for structs here }}
470+
{{else if (isOctetString type)}}
462471
jbyteArray {{asLowerCamelCase name}} = env->NewByteArray(entry.{{asLowerCamelCase name}}.size());
463472
env->SetByteArrayRegion({{asLowerCamelCase name}}, 0, entry.{{asLowerCamelCase name}}.size(), reinterpret_cast<const jbyte *>(entry.{{asLowerCamelCase name}}.data()));
464473
{{else if (isCharString type)}}
@@ -469,9 +478,19 @@ class CHIP{{asUpperCamelCase parent.name}}{{asUpperCamelCase name}}AttributeCall
469478
{{/if}}
470479
{{/chip_attribute_list_entryTypes}}
471480

472-
jobject attributeObj = env->NewObject(attributeClass, attributeCtor,
481+
jobject attributeObj = env->NewObject(attributeClass, attributeCtor
473482
{{#chip_attribute_list_entryTypes}}
474-
{{asLowerCamelCase name}}{{#not_last}}, {{/not_last}}
483+
{{#if isOptional}}
484+
{{! TODO: Add support for optional types here }}
485+
{{else if isNullable}}
486+
{{! TODO: Add support for nullable types here }}
487+
{{else if isArray}}
488+
{{! TODO: Add support for lists here }}
489+
{{else if isStruct}}
490+
{{! TODO: Add support for structs here }}
491+
{{else}}
492+
, {{asLowerCamelCase name}}
493+
{{/if}}
475494
{{/chip_attribute_list_entryTypes}}
476495
);
477496
VerifyOrReturn(attributeObj != nullptr, ChipLogError(Zcl, "Could not create {{asUpperCamelCase name}}Attribute object"));

src/controller/java/templates/ChipClusters-java.zapt

+28-2
Original file line numberDiff line numberDiff line change
@@ -110,7 +110,15 @@ public class ChipClusters {
110110
{{#if isStruct}}
111111
public static class {{asUpperCamelCase name}}Attribute {
112112
{{#chip_attribute_list_entryTypes}}
113-
{{#if (isOctetString type)}}
113+
{{#if isOptional}}
114+
{{! TODO: Add support for optional types here }}
115+
{{else if isNullable}}
116+
{{! TODO: Add support for nullable types here }}
117+
{{else if isArray}}
118+
{{! TODO: Add support for lists here }}
119+
{{else if isStruct}}
120+
{{! TODO: Add support for structs here }}
121+
{{else if (isOctetString type)}}
114122
public byte[] {{asLowerCamelCase name}};
115123
{{else if (isCharString type)}}
116124
public String {{asLowerCamelCase name}};
@@ -121,7 +129,15 @@ public class ChipClusters {
121129

122130
public {{asUpperCamelCase name}}Attribute(
123131
{{#chip_attribute_list_entryTypes}}
124-
{{#if (isOctetString type)}}
132+
{{#if isOptional}}
133+
{{! TODO: Add support for optional types here }}
134+
{{else if isNullable}}
135+
{{! TODO: Add support for nullable types here }}
136+
{{else if isArray}}
137+
{{! TODO: Add support for lists here }}
138+
{{else if isStruct}}
139+
{{! TODO: Add support for structs here }}
140+
{{else if (isOctetString type)}}
125141
byte[] {{asLowerCamelCase name}}{{#not_last}},{{/not_last}}
126142
{{else if (isCharString type)}}
127143
String {{asLowerCamelCase name}}{{#not_last}},{{/not_last}}
@@ -131,7 +147,17 @@ public class ChipClusters {
131147
{{/chip_attribute_list_entryTypes}}
132148
) {
133149
{{#chip_attribute_list_entryTypes}}
150+
{{#if isOptional}}
151+
{{! TODO: Add support for optional types here }}
152+
{{else if isNullable}}
153+
{{! TODO: Add support for nullable types here }}
154+
{{else if isArray}}
155+
{{! TODO: Add support for lists here }}
156+
{{else if isStruct}}
157+
{{! TODO: Add support for structs here }}
158+
{{else}}
134159
this.{{asLowerCamelCase name}} = {{asLowerCamelCase name}};
160+
{{/if}}
135161
{{/chip_attribute_list_entryTypes}}
136162
}
137163
}

0 commit comments

Comments
 (0)