RunLoop 的 CommonModes ,其实不是一个真正的 modes,而是一个伪 mode.. ,每个 _CFRunLoopRef 的数据结构大致是这样的:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
 struct __CFRunLoop {
CFRuntimeBase _base;
pthread_mutex_t _lock; /* locked for accessing mode list */
__CFPort _wakeUpPort; // used for CFRunLoopWakeUp
Boolean _unused;
volatile _per_run_data *_perRunData; // reset for runs of the run loop
pthread_t _pthread; //runloop对应的线程
uint32_t _winthread;
CFMutableSetRef _commonModes;//存储的是字符串,记录所有标记为common的mode
CFMutableSetRef _commonModeItems;//存储所有commonMode的item(source、timer、observer)
CFRunLoopModeRef _currentMode;//当前运行的mode
CFMutableSetRef _modes;//存储的是CFRunLoopModeRef,
struct _block_item *_blocks_head;
struct _block_item *_blocks_tail;
CFAbsoluteTime _runTime;
CFAbsoluteTime _sleepTime;
CFTypeRef _counterpart;
};

可以看到,里面有个 _commonModes 的集合,里面存储着被标记为 common 的 Modes 的字符串,主线程的 RunLoop 中,DefaultMode 和 TrackingMode 是被标记为 _commonMode 的。结构体中而且还一个 _commonModeItems 的集合,这个集合里,存储着所有 commonMode 的 item,比如 source、timer、observer。
每当 RunLoop 中的内容发生变化时,都会将 _commonModeItems 中的内容,自动同步到被标记为 _commonMode 的 mode 中,比如:
当我们将一个 timer 加入 commonMode,那么他们会被存储到 _commonModeItems 中,然后 RunLoop 会遍历 _commonModes 中的 mode ,然后将 timer 加入到这些 mode 中。