Threads within a thread block run on on the same SM at the same time.
As a result, threads within a thread block can communicate with each other using the SM’s shared memory.
There are no scheduling guarantees between thread groups. That is to say, thread blocks can execute in any order.
As a result, threads in different thread blocks must not have any dependencies between the two.