@@ -662,6 +662,37 @@ - (void)testFastEnumeration {
662662 XCTAssertEqual (loop, 10 );
663663}
664664
665+ - (void )testAddCopyOfField {
666+ GPBUnknownFields* ufs = [[[GPBUnknownFields alloc ] init ] autorelease ];
667+ [ufs addFieldNumber: 1 varint: 10 ];
668+ [ufs addFieldNumber: 2 fixed32: 11 ];
669+ [ufs addFieldNumber: 3 fixed64: 12 ];
670+ [ufs addFieldNumber: 4 lengthDelimited: DataFromCStr (" foo" )];
671+ GPBUnknownFields* group = [ufs addGroupWithFieldNumber: 5 ];
672+ [group addFieldNumber: 10 varint: 100 ];
673+ GPBUnknownFields* subGroup = [group addGroupWithFieldNumber: 100 ];
674+ [subGroup addFieldNumber: 50 varint: 50 ];
675+
676+ GPBUnknownFields* ufs2 = [[[GPBUnknownFields alloc ] init ] autorelease ];
677+ for (GPBUnknownField* field in ufs) {
678+ GPBUnknownField* field2 = [ufs2 addCopyOfField: field];
679+ XCTAssertEqualObjects (field, field2);
680+ if (field.type == GPBUnknownFieldTypeGroup) {
681+ // Group does a copy because the `.group` value is mutable.
682+ XCTAssertTrue (field != field2); // Pointer comparison.
683+ XCTAssertTrue (group != field2.group ); // Pointer comparison.
684+ XCTAssertEqualObjects (group, field2.group );
685+ GPBUnknownFields* subGroupAdded = [field2.group firstGroup: 100 ];
686+ XCTAssertTrue (subGroupAdded != subGroup); // Pointer comparison.
687+ XCTAssertEqualObjects (subGroupAdded, subGroup);
688+ } else {
689+ // All other types are immutable, so they use the same object.
690+ XCTAssertTrue (field == field2); // Pointer comparision.
691+ }
692+ }
693+ XCTAssertEqualObjects (ufs, ufs2);
694+ }
695+
665696- (void )testDescriptions {
666697 // Exercise description for completeness.
667698 GPBUnknownFields* ufs = [[[GPBUnknownFields alloc ] init ] autorelease ];
0 commit comments