Posix error 14 (bad address) on open read stream in Cocoa. Tips?
I am following the sample code in the CFNetwork Programming Guide, specifically the section on Blocking Prevention while Working with Threads . my code is almost identical to theirs (below), but when i connect to my server i get posix error 14 (bad address is bad IP (other than it)? Bad memory address for any call I made? what?!.
I have no idea how to debug this. I am really very new to the whole CFNetworking business and have never been a particularly expert on networking (which I really loved about Java: simple networks!: D)
In any case, the log follows with the code below. Any hints would be greatly appreciated.
Log:
[6824:20b] [DEBUG] Compat version: 30000011
[6824:20b] [DEBUG] resovled host.
[6824:20b] [DEBUG] writestream opened.
[6824:20b] [DEBUG] readstream client assigned.
[6824:20b] [DEBUG] readstream opened.
[6824:20b] [DEBUG] *** Read stream reported kCFStreamEventErrorOccurred
[6824:20b] [DEBUG] *** POSIX error: 14 - Bad address
[6824:20b] Error closing readstream
[6824:20b] [DEBUG] Writing int: 0x09000000 (0x00000009)
code:
+ (BOOL) connectToServerNamed:(NSString*)name atPort:(int)port {
CFHostRef theHost = CFHostCreateWithName (NULL, (CFStringRef)name);
CFStreamError error;
if (CFHostStartInfoResolution (theHost, kCFHostReachability, &error))
{
NSLog (@"[DEBUG] resovled host.");
CFStreamCreatePairWithSocketToCFHost (NULL, theHost, port, &readStream, &writeStream);
if (CFWriteStreamOpen(writeStream))
{
NSLog (@"[DEBUG] writestream opened.");
CFStreamClientContext myContext = { 0, self, NULL, NULL, NULL };
CFOptionFlags registeredEvents = kCFStreamEventHasBytesAvailable |
kCFStreamEventErrorOccurred | kCFStreamEventEndEncountered;
if (CFReadStreamSetClient (readStream, registeredEvents, readCallBack, &myContext))
{
NSLog (@"[DEBUG] readstream client assigned.");
CFReadStreamScheduleWithRunLoop(readStream, CFRunLoopGetCurrent(),
kCFRunLoopCommonModes);
if (CFReadStreamOpen(readStream))
{
NSLog (@"[DEBUG] readstream opened.");
CFRunLoopRun();
// Lots of error condition handling snipped.
[...]
return YES;
}
void readCallBack (CFReadStreamRef stream, CFStreamEventType event, void *myPtr)
{
switch (event)
{
case kCFStreamEventHasBytesAvailable:
{
CFIndex bytesRead = CFReadStreamRead(stream, buffer, kNetworkyBitsBufferSize); // won't block
if (bytesRead > 0) // <= 0 leads to additional events
{
if (listener)
{
UInt8 *tmpBuffer = malloc (sizeof (UInt8) * bytesRead);
memcpy (buffer, tmpBuffer, bytesRead);
NSLog(@"[DEBUG] reveived %d bytes", bytesRead);
[listener networkDataArrived:tmpBuffer count:bytesRead];
}
NSLog(@"[DEBUG] reveived %d bytes; no listener", bytesRead);
}
}
break;
case kCFStreamEventErrorOccurred:
NSLog(@"[DEBUG] *** Read stream reported kCFStreamEventErrorOccurred");
CFStreamError error = CFReadStreamGetError(stream);
logError(error);
[NetworkyBits shutDownRead];
break;
case kCFStreamEventEndEncountered:
NSLog(@"[DEBUG] *** Read stream reported kCFStreamEventEndEncountered");
[NetworkyBits shutDownRead];
break;
}
}
void logError (CFStreamError error)
{
if (error.domain == kCFStreamErrorDomainPOSIX) // Interpret error.error as a UNIX errno.
{
NSLog (@"[DEBUG] *** POSIX error: %d - %s", (int) error.error, strerror(error.error));
}
else if (error.domain == kCFStreamErrorDomainMacOSStatus)
{
NSLog (@"[DEBUG] *** MacOS error: %d", (int) error.error);
}
else
{
NSLog (@"[DEBUG] *** Stream error domain: %d, error: %d", (int) error.error);
}
}
source to share
Olie where
buffer
which you point to
CFReadStreamRead()
come? EFAULT is a bad buffer address ... are you sure you actually initialized this buffer to point to something effective? This is obviously global or sometime ... which in itself is a pretty bad idea. You must highlight it in your function or it must be ivar (if you are using Obj-C).
source to share
I'm not familiar with Cocoa or Objective-C, but I can tell that the POSIX 14 error code is called EFAULT , which means that you made a system call with an invalid pointer value. It is almost certainly a user-defined pointer to a buffer for a read or write system call. Check all buffer pointers and make sure they are not NULL. Check the return value from malloc()
- you may not be able to allocate the buffer.
source to share