Reputation: 5542
I know you might find this an odd question, but I'm just learning GCD and I want to fully understand all its aspects. So here it is:
Is there ever any reason to dispatch a task SYNC on the CURRENT QUEUE?
For example:
dispatch_queue_t concurrentQueue = dispatch_get_global_queue(...);
dispatch_async(concurrentQueue, ^{
//this is work task 0
//first do something here, then suddenly:
dispatch_sync(concurrentQueue, ^{
//work task 1
});
//continue work task 0
});
I understand one thing: if instead of concurrentQueue
I use a serial queue, then I get a deadlock on that serial queue, because work task 1
cannot start until the work task 0
is finished (because of the serial queue that guarantees order of execution), and in the same time work task 0
cannot continue its execution because it waits for the SYNC dispath function to return (please correct me if I'm wrong, that would make me a total noob).
So coming back to the original idea, is there any difference whatsoever between the code above and the same code where instead of calling the dispatch_sync
function I simply write work task 1
code directly?
Upvotes: 7
Views: 1857
Reputation: 6870
Assume this queue for all examples:
dispatch_queue_t queue = dispatch_queue_create(“com.somecompany.queue”, nil);
Situation 1 - OK
dispatch_async(queue, ^{
[self goDoSomethingLongAndInvolved];
dispatch_async(queue, ^{
NSLog(@"Situation 1");
});
});
Situation 2 - Not OK! Deadlock!
dispatch_sync(queue, ^{
[self goDoSomethingLongAndInvolved];
dispatch_sync(queue, ^{
NSLog(@"Situation 2”); // NOT REACHED! DEADLOCK!
});
});
Situation 3 - Not OK! Deadlock!
dispatch_async(queue, ^{
[self goDoSomethingLongAndInvolved];
dispatch_sync(queue, ^{
NSLog(@"Situation 3"); // NOT REACHED! DEADLOCK!
});
});
Situation 4 - OK
dispatch_sync(queue, ^{
[self goDoSomethingLongAndInvolved];
dispatch_async(queue, ^{
NSLog(@"Situation 4");
});
});
Basically dispatch_sync does not like to be on the inside.
Only dispatch_asyncs can go inside.
Upvotes: 3
Reputation: 29886
No. I can't think of a reason to ever dispatch_sync
on the same concurrent queue you're already on. If you do that, GCD will just immediately invoke your block, in-line, on the same thread, as if you had called it directly. (I checked.) And as you pointed out, doing that on a serial queue will deadlock you.
Upvotes: 7