/* * Grouch.app Copyright (C) 2006 Andy Sveikauskas * ------------------------------------------------------------------------ * This program is free software under the GNU General Public License * -- * Asks for rooms and such. */ #import #import #import #import #import #import #import #import #include @interface OscarChatNavSnacHandler : OscarSnacHandler + get; - init; @end @implementation OscarChatNavSnacHandler + get { static id r = nil; if( r ) return r; else return r = [OscarChatNavSnacHandler new]; } - init { [super init]; [self addFamily:[OscarServiceHandler get]]; [self addFamily:[OscarChatNavHandler get]]; return self; } @end @implementation OscarChatNav + chatNavForHost:(NSString*)host andCookie:(id)cookie andQueue:(OscarChatNavQueue*)queue andClient:(OscarClient*)cli { id r = [OscarChatNav new]; if( [r initForHost:host andCookie:cookie andQueue:queue andClient:cli] ) return r; else return nil; } - initForHost:(NSString*)host andCookie:(id)cookie andQueue:(OscarChatNavQueue*)queue andClient:(OscarClient*)cli { [q = queue retain]; [OscarDetachedFlapInitializer go:self host:host creds:cookie snac:[OscarChatNavSnacHandler get] client:cli loop:[NSRunLoop currentRunLoop] fatal:NO]; return self; } - init { [super init]; online = NO; return self; } - (void)dealloc { [q release]; [super dealloc]; } - (void)createChannel:(NSString*)chan withExchange:(int)exchange { if( online ) { OscarBuffer *ot = [OscarBuffer snacWithFamily:0x0d andType:0x08 andFlags:0 andTag:nil]; [ot addInt16:exchange]; [ot addString:@"ok"]; [ot addInt16:0xffff]; // instance [ot addByte:0x01]; [ot addInt16: 0x03]; [ot addTLV:0xd3 withString:chan]; [ot addTLV:0xd6 withString:@"us-ascii"]; [ot addTLV:0xd7 withString:@"en"]; [self write:ot]; [ot release]; } else [q createChannel:chan withExchange:exchange]; } - (void)welcome { online = YES; [q processQueue:self]; } - (void)connectionClosed:sock { OscarClient *cli = [self client]; if( cli ) [[self client] chatNavDied]; [self release]; } @end /************************************************************************/ #define node oscarchatnavqueue_node @implementation OscarChatNavQueue - init { head = tail = NULL; return self; } - (void)dealloc { struct node *n = head; while( n ) { [n->channel release]; head = n->next; free( n ); n = head; } [super dealloc]; } - (void)createChannel:(NSString*)chan withExchange:(int)ex { struct node *n = malloc(sizeof(struct node)); if( !n ) [GrouchException raiseMemoryException]; [n->channel = chan retain]; n->exchange = ex; n->next = NULL; if( tail ) tail = tail->next = n; else head = tail = n; } - (void)processQueue:(id )chatnav { struct node *n = head; while( n ) { [chatnav createChannel:n->channel withExchange:n->exchange]; [n->channel release]; head = n->next; free( n ); n = head; } tail = NULL; } @end