// array. We use this as a stack (FIFO), with index 0 being first.
NSMutableArray* queuedWrites_;
+ // We send queued writes in multiple places, sometimes of a run loop event.
+ // Because of this, we need to ensure that only one client is dequeing and
+ // sending at a time.
+ NSRecursiveLock* writeQueueLock_;
+
// The write stream. Weak.
CFWriteStreamRef writeStream_;
transactionID = 1;
stackFrames_ = [[NSMutableDictionary alloc] init];
self.queuedWrites = [NSMutableArray array];
+ writeQueueLock_ = [NSRecursiveLock new];
}
/**
CFRelease(socket_);
[stackFrames_ release];
self.queuedWrites = nil;
+ [writeQueueLock_ release];
}
/**
if (txnID != lastWrittenTransaction_)
NSLog(@"txn doesn't match last written %@", response);
+ lastReadTransaction_ = [transaction intValue];
NSLog(@"read=%d, write=%d", lastReadTransaction_, lastWrittenTransaction_);
// Dispatch the command response to an appropriate handler.
// Load the debugger to make it look active.
[delegate debuggerConnected];
- [self send:[self createCommand:@"status"]];
+ // TODO: update the status.
}
/**
*/
- (void)sendQueuedWrites
{
+ [writeQueueLock_ lock];
if (lastReadTransaction_ >= lastWrittenTransaction_ && [queuedWrites_ count] > 0)
{
NSString* command = [queuedWrites_ objectAtIndex:0];
// We don't want to block because this is called from the main thread.
// |-performSend:| busy waits when the stream is not ready. Bail out
// before we do that becuase busy waiting is BAD.
- if (!CFWriteStreamCanAcceptBytes(writeStream_))
- return;
-
- [self performSend:command];
- [queuedWrites_ removeObjectAtIndex:0];
+ if (CFWriteStreamCanAcceptBytes(writeStream_))
+ {
+ [self performSend:command];
+ [queuedWrites_ removeObjectAtIndex:0];
+ }
}
+ [writeQueueLock_ unlock];
}
/**