[GTK][EFL] Make *_PROCESS_CMD_PREFIX conditional on DEVELOPER_MODE
[WebKit-https.git] / Source / WebKit2 / UIProcess / Launcher / gtk / ProcessLauncherGtk.cpp
1 /*
2  * Copyright (C) 2010 Apple Inc. All rights reserved.
3  * Portions Copyright (c) 2010 Motorola Mobility, Inc.  All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  *
14  * THIS SOFTWARE IS PROVIDED BY MOTOROLA INC. AND ITS CONTRIBUTORS ``AS IS''
15  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
16  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
17  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL MOTOROLA INC. OR ITS CONTRIBUTORS
18  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
24  * THE POSSIBILITY OF SUCH DAMAGE.
25  */
26
27 #include "config.h"
28 #include "ProcessLauncher.h"
29
30 #include "Connection.h"
31 #include "ProcessExecutablePath.h"
32 #include <WebCore/AuthenticationChallenge.h>
33 #include <WebCore/FileSystem.h>
34 #include <WebCore/NetworkingContext.h>
35 #include <WebCore/ResourceHandle.h>
36 #include <errno.h>
37 #include <fcntl.h>
38 #include <glib.h>
39 #include <locale.h>
40 #include <wtf/RunLoop.h>
41 #include <wtf/UniStdExtras.h>
42 #include <wtf/glib/GLibUtilities.h>
43 #include <wtf/glib/GUniquePtr.h>
44 #include <wtf/text/CString.h>
45 #include <wtf/text/WTFString.h>
46
47 using namespace WebCore;
48
49 namespace WebKit {
50
51 static void childSetupFunction(gpointer userData)
52 {
53     int socket = GPOINTER_TO_INT(userData);
54     close(socket);
55 }
56
57 void ProcessLauncher::launchProcess()
58 {
59     GPid pid = 0;
60
61     IPC::Connection::SocketPair socketPair = IPC::Connection::createPlatformConnection(IPC::Connection::ConnectionOptions::SetCloexecOnServer);
62
63     String executablePath, pluginPath;
64     CString realExecutablePath, realPluginPath;
65     switch (m_launchOptions.processType) {
66     case ProcessLauncher::ProcessType::Web:
67         executablePath = executablePathOfWebProcess();
68         break;
69 #if ENABLE(NETSCAPE_PLUGIN_API)
70     case ProcessLauncher::ProcessType::Plugin64:
71     case ProcessLauncher::ProcessType::Plugin32:
72         executablePath = executablePathOfPluginProcess();
73 #if ENABLE(PLUGIN_PROCESS_GTK2)
74         if (m_launchOptions.extraInitializationData.contains("requires-gtk2"))
75             executablePath.append('2');
76 #endif
77         pluginPath = m_launchOptions.extraInitializationData.get("plugin-path");
78         realPluginPath = fileSystemRepresentation(pluginPath);
79         break;
80 #endif
81     case ProcessLauncher::ProcessType::Network:
82         executablePath = executablePathOfNetworkProcess();
83         break;
84 #if ENABLE(DATABASE_PROCESS)
85     case ProcessLauncher::ProcessType::Database:
86         executablePath = executablePathOfDatabaseProcess();
87         break;
88 #endif
89     default:
90         ASSERT_NOT_REACHED();
91         return;
92     }
93
94     realExecutablePath = fileSystemRepresentation(executablePath);
95     GUniquePtr<gchar> socket(g_strdup_printf("%d", socketPair.client));
96
97     unsigned nargs = 4; // size of the argv array for g_spawn_async()
98
99 #if ENABLE(DEVELOPER_MODE)
100     Vector<CString> prefixArgs;
101     if (!m_launchOptions.processCmdPrefix.isNull()) {
102         Vector<String> splitArgs;
103         m_launchOptions.processCmdPrefix.split(' ', splitArgs);
104         for (auto it = splitArgs.begin(); it != splitArgs.end(); it++)
105             prefixArgs.append(it->utf8());
106         nargs += prefixArgs.size();
107     }
108 #endif
109
110     char** argv = g_newa(char*, nargs);
111     unsigned i = 0;
112 #if ENABLE(DEVELOPER_MODE)
113     // If there's a prefix command, put it before the rest of the args.
114     for (auto it = prefixArgs.begin(); it != prefixArgs.end(); it++)
115         argv[i++] = const_cast<char*>(it->data());
116 #endif
117     argv[i++] = const_cast<char*>(realExecutablePath.data());
118     argv[i++] = socket.get();
119     argv[i++] = const_cast<char*>(realPluginPath.data());
120     argv[i++] = 0;
121
122     GUniqueOutPtr<GError> error;
123     if (!g_spawn_async(0, argv, 0, G_SPAWN_LEAVE_DESCRIPTORS_OPEN, childSetupFunction, GINT_TO_POINTER(socketPair.server), &pid, &error.outPtr())) {
124         g_printerr("Unable to fork a new WebProcess: %s.\n", error->message);
125         ASSERT_NOT_REACHED();
126     }
127
128     // Don't expose the parent socket to potential future children.
129     if (!setCloseOnExec(socketPair.client))
130         RELEASE_ASSERT_NOT_REACHED();
131
132     close(socketPair.client);
133     m_processIdentifier = pid;
134
135     // We've finished launching the process, message back to the main run loop.
136     RefPtr<ProcessLauncher> protector(this);
137     IPC::Connection::Identifier serverSocket = socketPair.server;
138     RunLoop::main().dispatch([protector, pid, serverSocket] {
139         protector->didFinishLaunchingProcess(pid, serverSocket);
140     });
141 }
142
143 void ProcessLauncher::terminateProcess()
144 {
145     if (m_isLaunching) {
146         invalidate();
147         return;
148     }
149
150     if (!m_processIdentifier)
151         return;
152
153     kill(m_processIdentifier, SIGKILL);
154     m_processIdentifier = 0;
155 }
156
157 void ProcessLauncher::platformInvalidate()
158 {
159 }
160
161 } // namespace WebKit