iosobjective-csocketscfstreamcfreadstream

Unable to write using CFWriteStream


I have created a UDP CFSocket and I'm able to send data without using any file handles. But, when I create CFReadStreamRef, CFWriteStreamRef and use them to send data, it fails. The control does not return. Can anyone help me regarding this? The code is as below:

-(void) CFSocketType2
{


CFSocketRef s = CFSocketCreate(kCFAllocatorDefault, PF_INET,
                               SOCK_DGRAM , IPPROTO_UDP,
                               0,
                               NULL,
                               NULL);

struct sockaddr_in      sin;
struct hostent           *host;

host = gethostbyname("localhost");
memset(&sin, 0, sizeof(sin));
memcpy(&(sin.sin_addr), host->h_addr,host->h_length);
sin.sin_family = AF_INET;
sin.sin_port = htons(5527);

CFDataRef address, data;

UInt8 message[] = "Hello world 123";
address = CFDataCreate(NULL, (UInt8 *)&sin, sizeof(sin));
data = CFDataCreate(NULL, message, sizeof(message));

//Sending data without using file handles
CFSocketConnectToAddress(s, address, 0);
CFSocketSendData(s, NULL, data, 0);


// The problem starts here
CFReadStreamRef readStream = NULL;
CFWriteStreamRef writeStream = NULL;


CFStreamCreatePairWithSocket(kCFAllocatorDefault, CFSocketGetNative(s), &readStream, &writeStream);


if (readStream && writeStream)
{
    CFReadStreamSetProperty(readStream, kCFStreamPropertyShouldCloseNativeSocket, kCFBooleanTrue);
    CFWriteStreamSetProperty(writeStream, kCFStreamPropertyShouldCloseNativeSocket, kCFBooleanTrue);
    if (! CFReadStreamOpen(readStream) || ! CFWriteStreamOpen(writeStream))
    {
        NSLog(@"Could not initialize streams!");
    }
    else
    {
        UInt8 msg [] ="Hello World";
        CFIndex a =  CFWriteStreamWrite(writeStream, msg, sizeof(msg));
        NSLog(@"Return value is %d", a);
    }
}
}

Solution

  • I was working on a UDP socket some time back. The problem in your code is that you are not connecting the server before you can use the the socket.

    The code which I wrote some time back is below. Hope it helps

    -(void) BSDSocketType
    {
    int sockfd;
    struct sockaddr_in servaddr;
    char sendline[] = "hello world";
    
    char addr[] = "127.0.0.1";
    
    
    sockfd=socket(AF_INET,SOCK_DGRAM,0);
    bzero(&servaddr,sizeof(servaddr));
    servaddr.sin_family = AF_INET;
    servaddr.sin_addr.s_addr=inet_addr(addr);
    servaddr.sin_port=htons(5527);
    
    
    
    // All these are foundation classes
    CFReadStreamRef readStraem = NULL;
    CFWriteStreamRef writeStream = NULL;
    
    
    int status =0;
    // Create CFSocket
    status = -3;
    status = fcntl(sockfd, F_SETFL, O_NONBLOCK);
    if (status == -1)
    {
        NSLog(@"Not able to create Non blocking socket");
    }
    int reuseaddr = 1;
    status = setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR, &reuseaddr, sizeof(reuseaddr));
    if (status == -1)
    {
        NSLog(@"Error 2");
    }
    int nosigpipe = 1;
    status = setsockopt(sockfd, SOL_SOCKET, SO_NOSIGPIPE, &nosigpipe, sizeof(nosigpipe));
    if (status == -1)
    {
        NSLog(@"Error");
    }
    
    CFStreamCreatePairWithSocket(NULL, (CFSocketNativeHandle)sockfd, &readStraem, &writeStream);
    if (!readStraem || !writeStream)
    {
        NSLog(@"Error");
    }
    NSLog(@"OK");
    
    
    int n = connect(sockfd, (struct sockaddr *)&servaddr,sizeof(servaddr));
    if ( n < 0)
    {
        printf("Connect error with port %s\n", strerror(errno));
    }
    
    
    CFReadStreamSetProperty(readStraem, kCFStreamPropertyShouldCloseNativeSocket, kCFBooleanFalse);
    CFWriteStreamSetProperty(writeStream, kCFStreamPropertyShouldCloseNativeSocket, kCFBooleanFalse);
    
    CFReadStreamOpen(readStraem);
    CFWriteStreamOpen(writeStream);
    
    NSLog(@"%ld",CFWriteStreamGetStatus(writeStream));
    NSLog(@"%ld",CFReadStreamGetStatus(readStraem));
    
    if(CFWriteStreamCanAcceptBytes(writeStream))
    {
        NSLog(@"Ok");
        UInt8 msg [] ="CF STReamHello World from cftype 2";
        CFIndex a =  CFWriteStreamWrite(writeStream, msg, sizeof(msg));
        NSLog(@"%ld",a);
    }
    else
        NSLog(@"Cannot accept bytes");
    NSLog(@"Ok");
    
    NSInputStream * inputStream = (__bridge NSInputStream *)(readStraem);
    NSOutputStream * outputStream = (__bridge NSOutputStream *)(writeStream);
    
    [inputStream open];
    [outputStream open];
    
    UInt8 msg [] ="NSStream Hello World from cftype 2";
    int a;
    if ([outputStream hasSpaceAvailable])
    {
        a = [outputStream write:msg maxLength:sizeof(msg)];
                NSLog(@"Ok");
    }
    NSLog(@"%d",a);
    

    }