// // CommunicationProtocol.m // DUREX Vendor Control // // Created by Imanol Barba on 5/23/14. // Copyright (c) 2014 Emmoco. All rights reserved. // #import "CommunicationProtocol.h" @interface CommunicationProtocol () @end @implementation CommunicationProtocol + (id)sharedProtocol { static CommunicationProtocol *shared = nil; static dispatch_once_t onceToken; dispatch_once(&onceToken, ^{ shared = [[self alloc] init]; }); return shared; } -(Boolean) waitForMessageAvailable: (Boolean) status { uint8_t retries = 0; while([self messageAvailable] != status) { [NSThread sleepForTimeInterval:5]; if([self messageAvailable] != status) { if(retries++ == MAX_RETRIES) { return FALSE; } } } return TRUE; } -(NSString*) readMessage { __block uint8_t numPackets, numBytes; __block NSMutableString *message; [message setString:@""]; if([self waitForMessageAvailable:TRUE]) { [[EMConnectionManager sharedManager] readResource:@"numPackets" onSuccess:^(id readValue) { numPackets = (uint8_t) [readValue unsignedCharValue]; } onFail:^(NSError *error) { NSLog(@"[CommunicationProtocol.m]: %@",error); numPackets = 0; }]; if(numPackets) { for(int i = 0; i < numPackets; i++) { [[EMConnectionManager sharedManager] readResource:@"numBytes" onSuccess:^(id readValue) { numBytes = (uint8_t) [readValue unsignedCharValue]; } onFail:^(NSError *error) { NSLog(@"[CommunicationProtocol.m]: %@",error); numBytes = 0; }]; if(numBytes) { [[EMConnectionManager sharedManager] readResource:@"data" onSuccess:^(id readValue) { [message appendString:[readValue stringValue]]; } onFail:^(NSError *error) { NSLog(@"[CommunicationProtocol.m]: %@",error); }]; } } } } [[EMConnectionManager sharedManager] writeValue:@"FALSE" toResource:@"messageAvailable" onSuccess:^ { } onFail:^(NSError *error) { NSLog(@"[CommunicationProtocol.m]: %@",error); } ]; return message; } -(Boolean) writeMessage: (NSString*) message { unsigned long remainingBytes = [message length]; uint8_t numBytes, current_index = 0; __block Boolean status = FALSE; [[EMConnectionManager sharedManager] writeValue:[NSNumber numberWithUnsignedChar:(unsigned char)([message length]/MAX_STRING_LENGTH)+1] toResource:@"numPackets" onSuccess:^ { status = TRUE; } onFail:^(NSError *error) { NSLog(@"[CommunicationProtocol.m]: %@",error); status = FALSE; } ]; if(status != FALSE) { while(remainingBytes) { if(![self waitForMessageAvailable:FALSE]) { status = FALSE; break; } if(remainingBytes > MAX_STRING_LENGTH) { numBytes = MAX_STRING_LENGTH; remainingBytes -= MAX_STRING_LENGTH; } else { numBytes = remainingBytes; remainingBytes = 0; } [[EMConnectionManager sharedManager] writeValue:[NSNumber numberWithUnsignedChar:(unsigned char)numBytes] toResource:@"numBytes" onSuccess:^ { status = TRUE; } onFail:^(NSError *error) { NSLog(@"[CommunicationProtocol.m]: %@",error); status = FALSE; } ]; if(status != FALSE) { NSString *data = [message substringWithRange:NSMakeRange(current_index, numBytes)]; current_index += numBytes; [[EMConnectionManager sharedManager] writeValue:data toResource:@"data" onSuccess:^ { status = TRUE; } onFail:^(NSError *error) { NSLog(@"[CommunicationProtocol.m]: %@",error); status = FALSE; } ]; if(status != FALSE) { [[EMConnectionManager sharedManager] writeValue:@"TRUE" toResource:@"messageAvailable" onSuccess:^ { status = TRUE; } onFail:^(NSError *error) { NSLog(@"[CommunicationProtocol.m]: %@",error); status = FALSE; } ]; } } } } return status; } -(Boolean) establishConnection { if([self writeMessage:@"Hello"]) { NSString *answer = [self readMessage]; if([answer isEqualToString:@"Hello"]) { return TRUE; } } return FALSE; } @end