Add test case for Objective-C 2.0 properties bug
authorWincent Colaiuta <win@wincent.com>
Sat, 11 Aug 2007 11:39:50 +0000 (13:39 +0200)
committerWincent Colaiuta <win@wincent.com>
Sat, 11 Aug 2007 11:39:50 +0000 (13:39 +0200)
In a previous commit (f2d45e3) I noted what appears to be a bug in either the
Objective-C 2.0 properties implementation (spurious compiler warnings) or in
its documentation.

I've prepared this test case demonstrating the problem. In the course of doing
so I discovered that the problem has a workaround that is considerably easier
than I originally thought, and the bug doesn't actually make it impossible to
use the public-readonly/private-readwrite property pattern. I will apply the
new workaround in a subsequent commit.

Signed-off-by: Wincent Colaiuta <win@wincent.com>
other/readonly_readwrite_properties_bug/readonly_readwrite_properties_bug.m [new file with mode: 0644]
other/readonly_readwrite_properties_bug/readonly_readwrite_properties_bug.xcodeproj/project.pbxproj [new file with mode: 0644]
other/readonly_readwrite_properties_bug/readonly_readwrite_properties_bug_Prefix.pch [new file with mode: 0644]

diff --git a/other/readonly_readwrite_properties_bug/readonly_readwrite_properties_bug.m b/other/readonly_readwrite_properties_bug/readonly_readwrite_properties_bug.m
new file mode 100644 (file)
index 0000000..e792c53
--- /dev/null
@@ -0,0 +1,52 @@
+#import <Foundation/Foundation.h>
+
+// ********** START TEST CASE (<rdar://problem/5403996>) **********
+
+// "public" interface: where bar is declared readonly, copy
+@interface Foo : NSObject {
+    NSString *bar;
+}
+@property(readonly, copy) NSString *bar;
+@end
+
+// "private" interface: where bar is redeclared readwrite
+@interface Foo ()
+@property(readwrite) NSString *bar;
+/*
+
+ The preceding property redeclaration generates the following warnings:
+
+ warning: no 'assign', 'retain', or 'copy' attribute is specified - 'assign' is assumed
+ warning: 'assign' attribute (default) not appropriate for non-gc object property 'bar'
+ warning: property 'bar' attribute in 'Foo' class continuation does not match class 'Foo' property
+
+ In order to make the warnings go away the copy attribute must be explicitly carried over to the redeclaration:
+
+ @property(readwrite, copy) NSString *bar;
+
+ So here we either have a compiler bug or a documentation bug, because the documentation states:
+
+ "You can re-declare properties in a subclass, and you can repeat properties' attributes in whole or in part"
+ "The same holds true for properties declared in a category"
+ "the property's attributes must only be repeated in whole or part"
+
+ Which would imply that explicitly repeating the "copy" attribute should not be necessary.
+
+ */
+@end
+
+// implementation
+@implementation Foo
+@synthesize bar;
+@end
+
+// ********** END TEST CASE **********
+
+int main (int argc, const char * argv[]) {
+    NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
+
+    // insert code here...
+    NSLog(@"Hello, World!");
+    [pool drain];
+    return 0;
+}
diff --git a/other/readonly_readwrite_properties_bug/readonly_readwrite_properties_bug.xcodeproj/project.pbxproj b/other/readonly_readwrite_properties_bug/readonly_readwrite_properties_bug.xcodeproj/project.pbxproj
new file mode 100644 (file)
index 0000000..e0e35c7
--- /dev/null
@@ -0,0 +1,214 @@
+// !$*UTF8*$!
+{
+       archiveVersion = 1;
+       classes = {
+       };
+       objectVersion = 43;
+       objects = {
+
+/* Begin PBXBuildFile section */
+               8DD76F9A0486AA7600D96B5E /* readonly_readwrite_properties_bug.m in Sources */ = {isa = PBXBuildFile; fileRef = 08FB7796FE84155DC02AAC07 /* readonly_readwrite_properties_bug.m */; settings = {ATTRIBUTES = (); }; };
+               8DD76F9C0486AA7600D96B5E /* Foundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 08FB779EFE84155DC02AAC07 /* Foundation.framework */; };
+/* End PBXBuildFile section */
+
+/* Begin PBXCopyFilesBuildPhase section */
+               8DD76F9E0486AA7600D96B5E /* CopyFiles */ = {
+                       isa = PBXCopyFilesBuildPhase;
+                       buildActionMask = 8;
+                       dstPath = /usr/share/man/man1/;
+                       dstSubfolderSpec = 0;
+                       files = (
+                       );
+                       runOnlyForDeploymentPostprocessing = 1;
+               };
+/* End PBXCopyFilesBuildPhase section */
+
+/* Begin PBXFileReference section */
+               08FB7796FE84155DC02AAC07 /* readonly_readwrite_properties_bug.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = readonly_readwrite_properties_bug.m; sourceTree = "<group>"; };
+               08FB779EFE84155DC02AAC07 /* Foundation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Foundation.framework; path = /System/Library/Frameworks/Foundation.framework; sourceTree = "<absolute>"; };
+               32A70AAB03705E1F00C91783 /* readonly_readwrite_properties_bug_Prefix.pch */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = readonly_readwrite_properties_bug_Prefix.pch; sourceTree = "<group>"; };
+               8DD76FA10486AA7600D96B5E /* readonly_readwrite_properties_bug */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = readonly_readwrite_properties_bug; sourceTree = BUILT_PRODUCTS_DIR; };
+/* End PBXFileReference section */
+
+/* Begin PBXFrameworksBuildPhase section */
+               8DD76F9B0486AA7600D96B5E /* Frameworks */ = {
+                       isa = PBXFrameworksBuildPhase;
+                       buildActionMask = 2147483647;
+                       files = (
+                               8DD76F9C0486AA7600D96B5E /* Foundation.framework in Frameworks */,
+                       );
+                       runOnlyForDeploymentPostprocessing = 0;
+               };
+/* End PBXFrameworksBuildPhase section */
+
+/* Begin PBXGroup section */
+               08FB7794FE84155DC02AAC07 /* readonly_readwrite_properties_bug */ = {
+                       isa = PBXGroup;
+                       children = (
+                               08FB7795FE84155DC02AAC07 /* Source */,
+                               C6859EA2029092E104C91782 /* Documentation */,
+                               08FB779DFE84155DC02AAC07 /* External Frameworks and Libraries */,
+                               1AB674ADFE9D54B511CA2CBB /* Products */,
+                       );
+                       name = readonly_readwrite_properties_bug;
+                       sourceTree = "<group>";
+               };
+               08FB7795FE84155DC02AAC07 /* Source */ = {
+                       isa = PBXGroup;
+                       children = (
+                               32A70AAB03705E1F00C91783 /* readonly_readwrite_properties_bug_Prefix.pch */,
+                               08FB7796FE84155DC02AAC07 /* readonly_readwrite_properties_bug.m */,
+                       );
+                       name = Source;
+                       sourceTree = "<group>";
+               };
+               08FB779DFE84155DC02AAC07 /* External Frameworks and Libraries */ = {
+                       isa = PBXGroup;
+                       children = (
+                               08FB779EFE84155DC02AAC07 /* Foundation.framework */,
+                       );
+                       name = "External Frameworks and Libraries";
+                       sourceTree = "<group>";
+               };
+               1AB674ADFE9D54B511CA2CBB /* Products */ = {
+                       isa = PBXGroup;
+                       children = (
+                               8DD76FA10486AA7600D96B5E /* readonly_readwrite_properties_bug */,
+                       );
+                       name = Products;
+                       sourceTree = "<group>";
+               };
+               C6859EA2029092E104C91782 /* Documentation */ = {
+                       isa = PBXGroup;
+                       children = (
+                       );
+                       name = Documentation;
+                       sourceTree = "<group>";
+               };
+/* End PBXGroup section */
+
+/* Begin PBXNativeTarget section */
+               8DD76F960486AA7600D96B5E /* readonly_readwrite_properties_bug */ = {
+                       isa = PBXNativeTarget;
+                       buildConfigurationList = 1DEB927408733DD40010E9CD /* Build configuration list for PBXNativeTarget "readonly_readwrite_properties_bug" */;
+                       buildPhases = (
+                               8DD76F990486AA7600D96B5E /* Sources */,
+                               8DD76F9B0486AA7600D96B5E /* Frameworks */,
+                               8DD76F9E0486AA7600D96B5E /* CopyFiles */,
+                       );
+                       buildRules = (
+                       );
+                       dependencies = (
+                       );
+                       name = readonly_readwrite_properties_bug;
+                       productInstallPath = "$(HOME)/bin";
+                       productName = readonly_readwrite_properties_bug;
+                       productReference = 8DD76FA10486AA7600D96B5E /* readonly_readwrite_properties_bug */;
+                       productType = "com.apple.product-type.tool";
+               };
+/* End PBXNativeTarget section */
+
+/* Begin PBXProject section */
+               08FB7793FE84155DC02AAC07 /* Project object */ = {
+                       isa = PBXProject;
+                       buildConfigurationList = 1DEB927808733DD40010E9CD /* Build configuration list for PBXProject "readonly_readwrite_properties_bug" */;
+                       compatibilityVersion = "Xcode 3.0";
+                       hasScannedForEncodings = 1;
+                       mainGroup = 08FB7794FE84155DC02AAC07 /* readonly_readwrite_properties_bug */;
+                       projectDirPath = "";
+                       projectRoot = "";
+                       targets = (
+                               8DD76F960486AA7600D96B5E /* readonly_readwrite_properties_bug */,
+                       );
+               };
+/* End PBXProject section */
+
+/* Begin PBXSourcesBuildPhase section */
+               8DD76F990486AA7600D96B5E /* Sources */ = {
+                       isa = PBXSourcesBuildPhase;
+                       buildActionMask = 2147483647;
+                       files = (
+                               8DD76F9A0486AA7600D96B5E /* readonly_readwrite_properties_bug.m in Sources */,
+                       );
+                       runOnlyForDeploymentPostprocessing = 0;
+               };
+/* End PBXSourcesBuildPhase section */
+
+/* Begin XCBuildConfiguration section */
+               1DEB927508733DD40010E9CD /* Debug */ = {
+                       isa = XCBuildConfiguration;
+                       buildSettings = {
+                               COPY_PHASE_STRIP = NO;
+                               GCC_DYNAMIC_NO_PIC = NO;
+                               GCC_ENABLE_FIX_AND_CONTINUE = YES;
+                               GCC_MODEL_TUNING = G5;
+                               GCC_OPTIMIZATION_LEVEL = 0;
+                               GCC_PRECOMPILE_PREFIX_HEADER = YES;
+                               GCC_PREFIX_HEADER = readonly_readwrite_properties_bug_Prefix.pch;
+                               INSTALL_PATH = /usr/local/bin;
+                               PRODUCT_NAME = readonly_readwrite_properties_bug;
+                               ZERO_LINK = YES;
+                       };
+                       name = Debug;
+               };
+               1DEB927608733DD40010E9CD /* Release */ = {
+                       isa = XCBuildConfiguration;
+                       buildSettings = {
+                               DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
+                               GCC_MODEL_TUNING = G5;
+                               GCC_PRECOMPILE_PREFIX_HEADER = YES;
+                               GCC_PREFIX_HEADER = readonly_readwrite_properties_bug_Prefix.pch;
+                               INSTALL_PATH = /usr/local/bin;
+                               PRODUCT_NAME = readonly_readwrite_properties_bug;
+                       };
+                       name = Release;
+               };
+               1DEB927908733DD40010E9CD /* Debug */ = {
+                       isa = XCBuildConfiguration;
+                       buildSettings = {
+                               GCC_WARN_ABOUT_RETURN_TYPE = YES;
+                               GCC_WARN_UNUSED_VARIABLE = YES;
+                               PREBINDING = NO;
+                               SDKROOTS = "$(DEVELOPER_SDK_DIR)/MacOSX10.5.sdk";
+                       };
+                       name = Debug;
+               };
+               1DEB927A08733DD40010E9CD /* Release */ = {
+                       isa = XCBuildConfiguration;
+                       buildSettings = {
+                               ARCHS = (
+                                       ppc,
+                                       i386,
+                               );
+                               GCC_WARN_ABOUT_RETURN_TYPE = YES;
+                               GCC_WARN_UNUSED_VARIABLE = YES;
+                               PREBINDING = NO;
+                               SDKROOTS = "$(DEVELOPER_SDK_DIR)/MacOSX10.5.sdk";
+                       };
+                       name = Release;
+               };
+/* End XCBuildConfiguration section */
+
+/* Begin XCConfigurationList section */
+               1DEB927408733DD40010E9CD /* Build configuration list for PBXNativeTarget "readonly_readwrite_properties_bug" */ = {
+                       isa = XCConfigurationList;
+                       buildConfigurations = (
+                               1DEB927508733DD40010E9CD /* Debug */,
+                               1DEB927608733DD40010E9CD /* Release */,
+                       );
+                       defaultConfigurationIsVisible = 0;
+                       defaultConfigurationName = Release;
+               };
+               1DEB927808733DD40010E9CD /* Build configuration list for PBXProject "readonly_readwrite_properties_bug" */ = {
+                       isa = XCConfigurationList;
+                       buildConfigurations = (
+                               1DEB927908733DD40010E9CD /* Debug */,
+                               1DEB927A08733DD40010E9CD /* Release */,
+                       );
+                       defaultConfigurationIsVisible = 0;
+                       defaultConfigurationName = Release;
+               };
+/* End XCConfigurationList section */
+       };
+       rootObject = 08FB7793FE84155DC02AAC07 /* Project object */;
+}
diff --git a/other/readonly_readwrite_properties_bug/readonly_readwrite_properties_bug_Prefix.pch b/other/readonly_readwrite_properties_bug/readonly_readwrite_properties_bug_Prefix.pch
new file mode 100644 (file)
index 0000000..ee30f84
--- /dev/null
@@ -0,0 +1,7 @@
+//
+// Prefix header for all source files of the 'readonly_readwrite_properties_bug' target in the 'readonly_readwrite_properties_bug' project.
+//
+
+#ifdef __OBJC__
+    #import <Foundation/Foundation.h>
+#endif