Planeshift

crash_generation_client.h

Go to the documentation of this file.
00001 // Copyright (c) 2008, Google Inc.
00002 // All rights reserved.
00003 //
00004 // Redistribution and use in source and binary forms, with or without
00005 // modification, are permitted provided that the following conditions are
00006 // met:
00007 //
00008 //     * Redistributions of source code must retain the above copyright
00009 // notice, this list of conditions and the following disclaimer.
00010 //     * Redistributions in binary form must reproduce the above
00011 // copyright notice, this list of conditions and the following disclaimer
00012 // in the documentation and/or other materials provided with the
00013 // distribution.
00014 //     * Neither the name of Google Inc. nor the names of its
00015 // contributors may be used to endorse or promote products derived from
00016 // this software without specific prior written permission.
00017 //
00018 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
00019 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
00020 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
00021 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
00022 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
00023 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
00024 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
00025 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
00026 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
00027 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
00028 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00029 
00030 #ifndef CLIENT_WINDOWS_CRASH_GENERATION_CRASH_GENERATION_CLIENT_H_
00031 #define CLIENT_WINDOWS_CRASH_GENERATION_CRASH_GENERATION_CLIENT_H_
00032 
00033 #include <windows.h>
00034 #include <dbghelp.h>
00035 #include <string>
00036 #include <utility>
00037 #include "client/windows/common/ipc_protocol.h"
00038 #include "common/scoped_ptr.h"
00039 
00040 namespace google_breakpad {
00041 
00042 struct CustomClientInfo;
00043 
00044 // Abstraction of client-side implementation of out of process
00045 // crash generation.
00046 //
00047 // The process that desires to have out-of-process crash dump
00048 // generation service can use this class in the following way:
00049 //
00050 // * Create an instance.
00051 // * Call Register method so that the client tries to register
00052 //   with the server process and check the return value. If
00053 //   registration is not successful, out-of-process crash dump
00054 //   generation will not be available
00055 // * Request dump generation by calling either of the two
00056 //   overloaded RequestDump methods - one in case of exceptions
00057 //   and the other in case of assertion failures
00058 //
00059 // Note that it is the responsibility of the client code of
00060 // this class to set the unhandled exception filter with the
00061 // system by calling the SetUnhandledExceptionFilter function
00062 // and the client code should explicitly request dump generation.
00063 class CrashGenerationClient {
00064  public:
00065   CrashGenerationClient(const wchar_t* pipe_name,
00066                         MINIDUMP_TYPE dump_type,
00067                         const CustomClientInfo* custom_info);
00068 
00069   CrashGenerationClient(HANDLE pipe_handle,
00070                         MINIDUMP_TYPE dump_type,
00071                         const CustomClientInfo* custom_info);
00072 
00073   ~CrashGenerationClient();
00074 
00075   // Registers the client process with the crash server.
00076   //
00077   // Returns true if the registration is successful; false otherwise.
00078   bool Register();
00079 
00080   // Requests the crash server to upload a previous dump with the
00081   // given crash id.
00082   bool RequestUpload(DWORD crash_id);
00083 
00084   bool RequestDump(EXCEPTION_POINTERS* ex_info,
00085                    MDRawAssertionInfo* assert_info);
00086 
00087   // Requests the crash server to generate a dump with the given
00088   // exception information.
00089   //
00090   // Returns true if the dump was successful; false otherwise. Note that
00091   // if the registration step was not performed or it was not successful,
00092   // false will be returned.
00093   bool RequestDump(EXCEPTION_POINTERS* ex_info);
00094 
00095   // Requests the crash server to generate a dump with the given
00096   // assertion information.
00097   //
00098   // Returns true if the dump was successful; false otherwise. Note that
00099   // if the registration step was not performed or it was not successful,
00100   // false will be returned.
00101   bool RequestDump(MDRawAssertionInfo* assert_info);
00102 
00103   // If the crash generation client is running in a sandbox that prevents it
00104   // from opening the named pipe directly, the server process may open the
00105   // handle and duplicate it into the client process with this helper method.
00106   // Returns INVALID_HANDLE_VALUE on failure. The process must have been opened
00107   // with the PROCESS_DUP_HANDLE access right.
00108   static HANDLE DuplicatePipeToClientProcess(const wchar_t* pipe_name,
00109                                              HANDLE hProcess);
00110 
00111  private:
00112   // Connects to the appropriate pipe and sets the pipe handle state.
00113   //
00114   // Returns the pipe handle if everything goes well; otherwise Returns NULL.
00115   HANDLE ConnectToServer();
00116 
00117   // Performs a handshake with the server over the given pipe which should be
00118   // already connected to the server.
00119   //
00120   // Returns true if handshake with the server was successful; false otherwise.
00121   bool RegisterClient(HANDLE pipe);
00122 
00123   // Validates the given server response.
00124   bool ValidateResponse(const ProtocolMessage& msg) const;
00125 
00126   // Returns true if the registration step succeeded; false otherwise.
00127   bool IsRegistered() const;
00128 
00129   // Connects to the given named pipe with given parameters.
00130   //
00131   // Returns true if the connection is successful; false otherwise.
00132   HANDLE ConnectToPipe(const wchar_t* pipe_name,
00133                        DWORD pipe_access,
00134                        DWORD flags_attrs);
00135 
00136   // Signals the crash event and wait for the server to generate crash.
00137   bool SignalCrashEventAndWait();
00138 
00139   // Pipe name to use to talk to server.
00140   std::wstring pipe_name_;
00141 
00142   // Pipe handle duplicated from server process. Only valid before
00143   // Register is called.
00144   HANDLE pipe_handle_;
00145 
00146   // Custom client information
00147   CustomClientInfo custom_info_;
00148 
00149   // Type of dump to generate.
00150   MINIDUMP_TYPE dump_type_;
00151 
00152   // Event to signal in case of a crash.
00153   HANDLE crash_event_;
00154 
00155   // Handle to wait on after signaling a crash for the server
00156   // to finish generating crash dump.
00157   HANDLE crash_generated_;
00158 
00159   // Handle to a mutex that will become signaled with WAIT_ABANDONED
00160   // if the server process goes down.
00161   HANDLE server_alive_;
00162 
00163   // Server process id.
00164   DWORD server_process_id_;
00165 
00166   // Id of the thread that caused the crash.
00167   DWORD thread_id_;
00168 
00169   // Exception pointers for an exception crash.
00170   EXCEPTION_POINTERS* exception_pointers_;
00171 
00172   // Assertion info for an invalid parameter or pure call crash.
00173   MDRawAssertionInfo assert_info_;
00174 
00175   // Disable copy ctor and operator=.
00176   CrashGenerationClient(const CrashGenerationClient& crash_client);
00177   CrashGenerationClient& operator=(const CrashGenerationClient& crash_client);
00178 };
00179 
00180 }  // namespace google_breakpad
00181 
00182 #endif  // CLIENT_WINDOWS_CRASH_GENERATION_CRASH_GENERATION_CLIENT_H_