Ken Rockot | dba46db | 2018-07-04 18:41:04 | [diff] [blame] | 1 | # Mojo Core Embedder API |
| 2 | This document is a subset of the [Mojo documentation](/mojo/README.md). |
| 3 | |
| 4 | [TOC] |
| 5 | |
| 6 | ## Overview |
| 7 | |
| 8 | The Mojo Core Embedder API enables process to initialize and use Mojo for IPC, |
| 9 | using an implementation of Mojo Core that is statically linked into the |
| 10 | application. See the note about dynamic linking |
| 11 | [here](/mojo/README.md#Mojo-Core) for more information about an alternative |
| 12 | approach to Mojo Core initialization. |
| 13 | |
| 14 | **NOTE:** Unless you are introducing a new binary entry point into the system |
| 15 | (*e.g.,* a new executable with a new `main()` definition), you probably don't |
| 16 | need to know anything about the Embedder API. Most processes defined in the |
| 17 | Chrome repo today already fully initialize Mojo Core so that all other public |
| 18 | Mojo APIs just work out of the box. |
| 19 | |
| 20 | ## Basic Initialization |
| 21 | |
| 22 | As an embedder, initializing Mojo Core requires a single call to |
| 23 | `mojo::core::Init`: |
| 24 | |
| 25 | ``` |
| 26 | #include "mojo/core/embedder/embedder.h" |
| 27 | |
| 28 | int main(int argc, char** argv) { |
| 29 | mojo::core::Init(); |
| 30 | |
| 31 | // Now you can create message pipes, write messages, etc |
| 32 | |
| 33 | return 0; |
| 34 | } |
| 35 | ``` |
| 36 | |
| 37 | This enables local API calls to work, so message pipes *etc* can be created and |
| 38 | used. In some cases (particuarly many unit testing scenarios) this is |
| 39 | sufficient, but to support any actual multiprocess communication (e.g. sending |
| 40 | or accepting Mojo invitations), a second IPC initialization step is required. |
| 41 | |
| 42 | ## IPC Initialization |
| 43 | |
| 44 | Internal Mojo IPC implementation requires a background `TaskRunner` on which it |
| 45 | can watch for inbound I/O from other processes. This is configured using a |
| 46 | `ScopedIPCSupport` object, which keeps IPC support alive through the extent of |
| 47 | its lifetime. |
| 48 | |
| 49 | Typically an application will create a dedicated background thread and give its |
| 50 | `TaskRunner` to Mojo. Note that in Chromium, we use the existing "IO thread" in |
| 51 | the browser process and content child processes. In general, any thread used |
Carlos Caballero | 9a576de | 2019-07-31 09:12:56 | [diff] [blame] | 52 | for Mojo IPC support must be running a `base::MessagePumpType::IO` loop. |
Ken Rockot | dba46db | 2018-07-04 18:41:04 | [diff] [blame] | 53 | |
| 54 | ``` |
| 55 | #include "base/threading/thread.h" |
| 56 | #include "mojo/core/embedder/embedder.h" |
| 57 | #include "mojo/core/embedder/scoped_ipc_support.h" |
| 58 | |
| 59 | int main(int argc, char** argv) { |
| 60 | mojo::core::Init(); |
| 61 | |
| 62 | base::Thread ipc_thread("ipc!"); |
| 63 | ipc_thread.StartWithOptions( |
Carlos Caballero | 9a576de | 2019-07-31 09:12:56 | [diff] [blame] | 64 | base::Thread::Options(base::MessagePumpType::IO, 0)); |
Ken Rockot | dba46db | 2018-07-04 18:41:04 | [diff] [blame] | 65 | |
| 66 | // As long as this object is alive, all Mojo API surface relevant to IPC |
| 67 | // connections is usable, and message pipes which span a process boundary will |
| 68 | // continue to function. |
| 69 | mojo::core::ScopedIPCSupport ipc_support( |
| 70 | ipc_thread.task_runner(), |
| 71 | mojo::core::ScopedIPCSupport::ShutdownPolicy::CLEAN); |
| 72 | |
| 73 | return 0; |
| 74 | } |
| 75 | ``` |
| 76 | |
| 77 | This process is now fully prepared to use Mojo IPC! |
| 78 | |
| 79 | Note that all existing process types in Chromium already perform this setup |
| 80 | very early during startup. |
| 81 | |
| 82 | ## Connecting Two Processes |
| 83 | |
| 84 | Once IPC is initialized, you can bootstrap connections to other processes by |
| 85 | using the public |
| 86 | [Invitations API](/mojo/public/cpp/system/README.md#Invitations). |