Thu, 22 Jan 2015 13:21:57 +0100
Incorporate requested changes from Mozilla in review:
https://bugzilla.mozilla.org/show_bug.cgi?id=1123480#c6
1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set sw=2 ts=2 autoindent cindent expandtab: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this file,
5 * You can obtain one at http://mozilla.org/MPL/2.0/. */
7 #ifndef __NUWA_H_
8 #define __NUWA_H_
10 #include <setjmp.h>
11 #include <unistd.h>
13 #include "mozilla/Types.h"
15 /**
16 * Nuwa is a goddess who created mankind according to her figure in the
17 * ancient Chinese mythology.
18 */
20 // Max number of top level protocol that can be handled by Nuwa process.
21 #ifndef NUWA_TOPLEVEL_MAX
22 #define NUWA_TOPLEVEL_MAX 8
23 #endif
25 struct NuwaProtoFdInfo {
26 int protoId;
27 int originFd;
28 int newFds[2];
29 };
31 #define NUWA_NEWFD_PARENT 0
32 #define NUWA_NEWFD_CHILD 1
34 extern "C" {
36 /**
37 * The following 3 methods are used to synchronously spawn the Nuwa process.
38 * The typical usage is:
39 *
40 * The IPC thread The main thread
41 * 1. Receives the request.
42 * 2. NuwaSpawnPrepare().
43 * 3. Request main thread to
44 * spawn. --------------------------------------+
45 * 4. NuwaSpawnWait(). V
46 * 5. NuwaSpawn() to clone all
47 * the threads in the Nuwa
48 * process (including main
49 * & IPC threads).
50 * 6. NuwaSpawn() finishes and
51 * +-------------------------------------- signals NuwaSpawnWait().
52 * V
53 * 7. NuwaSpawnWait() returns.
54 */
56 /**
57 * Prepare for spawning a new process. The calling thread (typically the IPC
58 * thread) will block further requests to spawn a new process.
59 */
60 MFBT_API void NuwaSpawnPrepare();
62 /**
63 * Called on the thread that receives the request. Used to wait until
64 * NuwaSpawn() finishes and maintain the stack of the calling thread.
65 */
66 MFBT_API void NuwaSpawnWait();
68 /**
69 * Spawn a new content process, called in the Nuwa process. This has to run on
70 * the main thread.
71 *
72 * @return The process ID of the new process.
73 */
74 MFBT_API pid_t NuwaSpawn();
76 /**
77 * The following methods are for marking threads created in the Nuwa process so
78 * they can be frozen and then recreated in the spawned process. All threads
79 * except the main thread must be marked by one of the following 4 methods;
80 * otherwise, we have a thread that is created but unknown to us. The Nuwa
81 * process will never become ready and this needs to be fixed.
82 */
84 /**
85 * Mark the current thread as supporting Nuwa. The thread will implicitly freeze
86 * by calling a blocking method such as pthread_mutex_lock() or epoll_wait().
87 *
88 * @param recreate The custom function that will be called in the spawned
89 * process, after the thread is recreated. Can be nullptr if no
90 * custom function to be called after the thread is recreated.
91 * @param arg The argument passed to the custom function. Can be nullptr.
92 */
93 MFBT_API void NuwaMarkCurrentThread(void (*recreate)(void *), void *arg);
95 /**
96 * Mark the current thread as not supporting Nuwa. The calling thread will not
97 * be automatically cloned from the Nuwa process to spawned process. If this
98 * thread needs to be created in the spawned process, use NuwaAddConstructor()
99 * or NuwaAddFinalConstructor() to do it.
100 */
101 MFBT_API void NuwaSkipCurrentThread();
103 /**
104 * Force the current thread to freeze explicitly at the current point.
105 */
106 MFBT_API void NuwaFreezeCurrentThread();
108 /**
109 * Helper functions for the NuwaCheckpointCurrentThread() macro.
110 */
111 MFBT_API jmp_buf* NuwaCheckpointCurrentThread1();
113 MFBT_API bool NuwaCheckpointCurrentThread2(int setjmpCond);
115 /**
116 * Set the point to recover after thread recreation. The calling thread is not
117 * blocked. This is used for the thread that cannot freeze (i.e. the IPC
118 * thread).
119 */
120 #define NuwaCheckpointCurrentThread() \
121 NuwaCheckpointCurrentThread2(setjmp(*NuwaCheckpointCurrentThread1()))
123 /**
124 * The following methods are called in the initialization stage of the Nuwa
125 * process.
126 */
128 /**
129 * Prepare for making the Nuwa process.
130 */
131 MFBT_API void PrepareNuwaProcess();
133 /**
134 * Make the current process a Nuwa process. Start to freeze the threads.
135 */
136 MFBT_API void MakeNuwaProcess();
138 /**
139 * Register a method to be invoked after a new process is spawned. The method
140 * will be invoked on the main thread.
141 *
142 * @param construct The method to be invoked.
143 * @param arg The argument passed to the method.
144 */
145 MFBT_API void NuwaAddConstructor(void (*construct)(void *), void *arg);
147 /**
148 * Register a method to be invoked after a new process is spawned and threads
149 * are recreated. The method will be invoked on the main thread.
150 *
151 * @param construct The method to be invoked.
152 * @param arg The argument passed to the method.
153 */
154 MFBT_API void NuwaAddFinalConstructor(void (*construct)(void *), void *arg);
156 /**
157 * The methods to query the Nuwa-related states.
158 */
160 /**
161 * @return If the current process is the Nuwa process.
162 */
163 MFBT_API bool IsNuwaProcess();
165 /**
166 * @return If the Nuwa process is ready for spawning new processes.
167 */
168 MFBT_API bool IsNuwaReady();
169 };
171 #endif /* __NUWA_H_ */