How to make code work in ARC?


Hi All:

I have the book really enlightening?

I am still a newbie trying to learn iOS programming and ARC.

So far, I have been able to convert all of the previous chapters code to ARC. I hit some difficulty here.

I used the compile flag: -fno-objc-arc in “build phases > compile sources” to force the ARC compiler to compile the file as a none ARC files for:
CocoaServer: HTTPServer.m and TCPServer.m
Notified: NotifiedAppDelegate.m
I confirmed that the books code - with the small absolute to relative modification discussed in earlier posts - executes - will at least the iphone simulator says “Data sent to server”.

Then in the NotifiedAppDelegate.m file, with the compile flag still set, I commented out all the [* release] lines. Yes, the code is now leaky, but hey this is an experiment to learn.
There are no [* autorelease] lines to comment out.

I confirmed the same result “Data sent to server” for both 4.3 and 5.0 in the simulator.

When I tried to convert the sole [* retain] line in the function below, I encountered a connection failed when executing. The 2 lines I tried are commented out below it.

  • (void)netServiceBrowser:(NSNetServiceBrowser *)aNetServiceBrowser
    didFindService:(NSNetService *)aNetService
    // Looking for an HTTP service, but only one with the name CocoaHTTPServer
    if (!desktopServer && [[aNetService name] isEqualToString:@“CocoaHTTPServer”]) {
    desktopServer = [aNetService retain];
    // desktopServer = (NSNetService *) aNetService;
    // desktopServer = aNetService;
    [desktopServer resolveWithTimeout:30];
    [desktopServer setDelegate:self];
    [statusLabel setText:@“Resolving CocoaHTTPServer…”];
    } else {
    NSLog(@“ignoring %@”, aNetService);

I investigated the _bridge_retain and __bridge_retain also, but I do not know yet if that will be useful.

Any suggestions on how to make this code work in ARC, would be most helpful.

I suspect that CocoaServer: HTTPServer.m and TCPServer.m may have the same problems for its retains.

Thank you for your time.

Happy Coding!

Jeff Pape


Not ideal, but the way I got this to work was to create an NSNetService property called tempService

@interface NotifiedAppDelegate : UIResponder <UIApplicationDelegate, NSNetServiceBrowserDelegate, NSNetServiceDelegate, NSURLConnectionDelegate> { NSNetService *desktopServer; NSNetService *tempService; NSNetServiceBrowser *browser; }

Which is assigned aNetService where you were trying to assign it to desktopService.

- (void)netServiceBrowser:(NSNetServiceBrowser *)aNetServiceBrowser didFindService:(NSNetService *)aNetService moreComing:(BOOL)moreComing { // Looking for an HTTP servce, but only one with the name CocoaHTTPServer if (!desktopServer && [[aNetService name] isEqualToString:@"CocoaHTTPServer"]) { [aNetService resolveWithTimeout:30]; [aNetService setDelegate:self]; tempService = aNetService; [_statusLabel setText:@"Resolving CocoaHTTPServer..."]; } else { NSLog(@"ignoring %@", aNetService); } }

You can then set it to nil when in the delegate function to allow it to be released.

[code]- (void)netServiceDidResolveAddress:(NSNetService *)sender
[_statusLabel setText:@“Resolved service…”];
desktopServer = sender;
tempService = nil;

[self postInformationToServer];


I’m not sure if there is a better way to tell an object to retain under ARC without assigning it to a property.


I’m doing this in Xcode 4.2.1 with ARC, updated the TCPServer and HTTPServer files to ARC with the help of Xcode. Got CocoaServer to advertise without issue, Notified does run and connect but will “time out” when trying to POST to server. (void)postInformationToServer in Notified runs (“Sending data to server …”), but the HTTPConnection delegate in CocoaServer doesn’t pick it up, (void)HTTPConnection:(HTTPConnection *)conn didReceiveRequest:(HTTPServerRequest *)mess doesn’t run.

I’m testing this on the simulator (OSX Lion), is this a problem with the simulator, or did I botch up something in one of the Apple Server source files?

I did update the code with what’s in the errata, and used the retain hack in assigning aNetService (in netServiceBrowser:didFindService:moreComing:)

The downloaded book source code does run correctly for both chapter 28 and 29.