blob: 97d8bae7b19376d4d3718d8171d9c1b3c4b3e6d1 [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
#import <Cocoa/Cocoa.h>
#import "TSocketServer.h"
#import "TNSFileHandleTransport.h"
#import "TProtocol.h"
#import "TTransportException.h"
@implementation TSocketServer
- (id) initWithPort: (int) port
protocolFactory: (id <TProtocolFactory>) protocolFactory
processor: (id <TProcessor>) processor;
{
self = [super init];
mInputProtocolFactory = [protocolFactory retain];
mOutputProtocolFactory = [protocolFactory retain];
mProcessor = [processor retain];
// create a socket
mServerSocket = [[NSSocketPort alloc] initWithTCPPort: port];
// FIXME - move this separate start method and add method to close
// and cleanup any open ports
if (mServerSocket == nil) {
NSLog(@"Unable to listen on TCP port %d", port);
} else {
NSLog(@"Listening on TCP port %d", port);
// wrap it in a file handle so we can get messages from it
mSocketFileHandle = [[NSFileHandle alloc] initWithFileDescriptor: [mServerSocket socket]
closeOnDealloc: YES];
// register for notifications of accepted incoming connections
[[NSNotificationCenter defaultCenter] addObserver: self
selector: @selector(connectionAccepted:)
name: NSFileHandleConnectionAcceptedNotification
object: mSocketFileHandle];
// tell socket to listen
[mSocketFileHandle acceptConnectionInBackgroundAndNotify];
}
return self;
}
- (void) dealloc {
[mInputProtocolFactory release];
[mOutputProtocolFactory release];
[mProcessor release];
[mSocketFileHandle release];
[mServerSocket release];
[super dealloc];
}
- (void) connectionAccepted: (NSNotification *) aNotification
{
NSFileHandle * socket = [[aNotification userInfo] objectForKey: NSFileHandleNotificationFileHandleItem];
// now that we have a client connected, spin off a thread to handle activity
[NSThread detachNewThreadSelector: @selector(handleClientConnection:)
toTarget: self
withObject: socket];
[[aNotification object] acceptConnectionInBackgroundAndNotify];
}
- (void) handleClientConnection: (NSFileHandle *) clientSocket
{
NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
TNSFileHandleTransport * transport = [[TNSFileHandleTransport alloc] initWithFileHandle: clientSocket];
id <TProtocol> inProtocol = [mInputProtocolFactory newProtocolOnTransport: transport];
id <TProtocol> outProtocol = [mOutputProtocolFactory newProtocolOnTransport: transport];
@try {
while ([mProcessor processOnInputProtocol: inProtocol outputProtocol: outProtocol]);
}
@catch (TTransportException * te) {
NSLog(@"%@", te);
}
[pool release];
}
@end