Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(179)

Unified Diff: client/crashpad_client_mac.cc

Issue 1001993002: CrashpadClient::StartHandler(): accept database, url, and annotations arguments (Closed) Base URL: https://chromium.googlesource.com/crashpad/crashpad@master
Patch Set: 80 Created 5 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « client/crashpad_client.h ('k') | handler/mac/main.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: client/crashpad_client_mac.cc
diff --git a/client/crashpad_client_mac.cc b/client/crashpad_client_mac.cc
index 2858ac4802a704269bdaeb86fedeb3f5e354e21a..2ac274d0f00cadeb2294e6e70baacff90df1dd24 100644
--- a/client/crashpad_client_mac.cc
+++ b/client/crashpad_client_mac.cc
@@ -27,6 +27,19 @@
#include "util/mach/mach_extensions.h"
#include "util/posix/close_multiple.h"
+namespace {
+
+std::string FormatArgumentString(const std::string& name,
+ const std::string& value) {
+ return base::StringPrintf("--%s=%s", name.c_str(), value.c_str());
+}
+
+std::string FormatArgumentInt(const std::string& name, int value) {
+ return base::StringPrintf("--%s=%d", name.c_str(), value);
+}
+
+} // namespace
+
namespace crashpad {
CrashpadClient::CrashpadClient()
@@ -38,28 +51,49 @@ CrashpadClient::~CrashpadClient() {
bool CrashpadClient::StartHandler(
const base::FilePath& handler,
- const std::vector<std::string>& handler_arguments) {
+ const base::FilePath& database,
+ const std::string& url,
+ const std::map<std::string, std::string>& annotations,
+ const std::vector<std::string>& arguments) {
DCHECK_EQ(exception_port_, kMachPortNull);
// Set up the arguments for execve() first. These aren’t needed until execve()
// is called, but it’s dangerous to do this in a child process after fork().
ChildPortHandshake child_port_handshake;
int handshake_fd = child_port_handshake.ReadPipeFD();
- std::string handshake_fd_arg =
- base::StringPrintf("--handshake-fd=%d", handshake_fd);
-
- const std::string& handler_s = handler.value();
- const char* const handler_c = handler_s.c_str();
-
- // Use handler as argv[0], followed by handler_arguments, handshake_fd_arg,
- // and a nullptr terminator.
- std::vector<const char*> argv(1, handler_c);
- argv.reserve(1 + handler_arguments.size() + 1 + 1);
- for (const std::string& handler_argument : handler_arguments) {
- argv.push_back(handler_argument.c_str());
+
+ // Use handler as argv[0], followed by arguments directed by this method’s
+ // parameters and a --handshake-fd argument. |arguments| are added first so
+ // that if it erroneously contains an argument such as --url, the actual |url|
+ // argument passed to this method will supersede it. In normal command-line
+ // processing, the last parameter wins in the case of a conflict.
+ std::vector<std::string> argv(1, handler.value());
+ argv.reserve(1 + arguments.size() + 2 + annotations.size() + 1);
+ for (const std::string& argument : arguments) {
+ argv.push_back(argument);
+ }
+ if (!database.value().empty()) {
+ argv.push_back(FormatArgumentString("database", database.value()));
+ }
+ if (!url.empty()) {
+ argv.push_back(FormatArgumentString("url", url));
+ }
+ for (const auto& kv : annotations) {
+ argv.push_back(
+ FormatArgumentString("annotation", kv.first + '=' + kv.second));
+ }
+ argv.push_back(FormatArgumentInt("handshake-fd", handshake_fd));
+
+ // argv_c contains const char* pointers and is terminated by nullptr. argv
+ // is required because the pointers in argv_c need to point somewhere, and
+ // they can’t point to temporaries such as those returned by
+ // FormatArgumentString().
+ std::vector<const char*> argv_c;
+ argv_c.reserve(argv.size() + 1);
+ for (const std::string& argument : argv) {
+ argv_c.push_back(argument.c_str());
}
- argv.push_back(handshake_fd_arg.c_str());
- argv.push_back(nullptr);
+ argv_c.push_back(nullptr);
// Double-fork(). The three processes involved are parent, child, and
// grandchild. The grandchild will become the handler process. The child exits
@@ -112,12 +146,12 @@ bool CrashpadClient::StartHandler(
CloseMultipleNowOrOnExec(STDERR_FILENO + 1, handshake_fd);
- // &argv[0] is a pointer to a pointer to const char data, but because of how
- // C (not C++) works, execvp() wants a pointer to a const pointer to char
- // data. It modifies neither the data nor the pointers, so the const_cast is
- // safe.
- execvp(handler_c, const_cast<char* const*>(&argv[0]));
- PLOG(FATAL) << "execvp " << handler_s;
+ // &argv_c[0] is a pointer to a pointer to const char data, but because of
+ // how C (not C++) works, execvp() wants a pointer to a const pointer to
+ // char data. It modifies neither the data nor the pointers, so the
+ // const_cast is safe.
+ execvp(handler.value().c_str(), const_cast<char* const*>(&argv_c[0]));
+ PLOG(FATAL) << "execvp " << handler.value();
}
// Parent process.
« no previous file with comments | « client/crashpad_client.h ('k') | handler/mac/main.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698