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

Side by Side Diff: components/browser_watcher/postmortem_minidump_writer.h

Issue 2327043002: A simple minidump writer for postmortem stability reports. (Closed)
Patch Set: Address comments Created 4 years, 3 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 unified diff | Download patch
OLDNEW
(Empty)
1 // Copyright 2016 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #ifndef COMPONENTS_BROWSER_WATCHER_POSTMORTEM_MINIDUMP_WRITER_H_
6 #define COMPONENTS_BROWSER_WATCHER_POSTMORTEM_MINIDUMP_WRITER_H_
7
8 #include <stdint.h>
9
10 #include <map>
11 #include <memory>
12 #include <string>
13 #include <type_traits>
14 #include <vector>
15
16 #include "base/files/file.h"
17 #include "base/macros.h"
18 #include "base/strings/string_piece.h"
19 #include "components/browser_watcher/stability_report.pb.h"
20 #include "third_party/crashpad/crashpad/minidump/minidump_extensions.h"
21 #include "third_party/crashpad/crashpad/util/misc/uuid.h"
22
23 namespace browser_watcher {
24
25 // A class with functionality for writing minimal minidump containers to wrap
26 // postmortem stability reports.
27 // TODO(manzagop): remove this class once CrashPad takes over writing postmortem
28 // minidumps.
29 // TODO(manzagop): revisit where the module information should be transported,
30 // in the protocol buffer or in a module stream.
31 class PostmortemMinidumpWriter {
scottmg 2016/09/13 18:07:43 This seems like it could just be a WriteDump() fun
manzagop (departed) 2016/09/13 21:19:41 Done.
32 public:
33 struct ReportInfo;
34
35 PostmortemMinidumpWriter() = default;
36 ~PostmortemMinidumpWriter() = default;
37
38 // Write to |minidump_file| a minimal minidump that wraps |report|. Returns
39 // true on success, false otherwise.
40 // Note: the caller owns |minidump_file| and is responsible for keeping it
41 // valid for this object's lifetime. |minidump_file| is expected to be empty
42 // and a binary stream.
43 bool WriteDump(base::PlatformFile minidump_file,
44 const StabilityReport& report,
45 const ReportInfo& report_info);
46
47 private:
48 // An offset within a minidump file. Note: using this type to avoid including
49 // windows.h and relying on the RVA type.
50 using FilePosition = uint32_t;
51
52 // The minidump header is always located at the head.
53 static const FilePosition kHeaderPos = 0U;
54
55 void Initialize();
56
57 bool AppendCrashpadInfo(const crashpad::UUID& client_id,
58 const crashpad::UUID& report_id,
59 const std::map<std::string, std::string>& crash_keys);
60
61 bool AppendCrashpadDictionaryEntry(
62 const std::string& key,
63 const std::string& value,
64 std::vector<crashpad::MinidumpSimpleStringDictionaryEntry>* entries);
65
66 // Allocate |size_bytes| within the minidump. On success, |pos| contains the
67 // location of the allocation. Returns true on success, false otherwise.
68 bool Allocate(size_t size_bytes, FilePosition* pos);
69
70 // Seeks |cursor_|. The seek operation is kept separate from the write in
71 // order to make the call explicit. Seek operations can be costly and should
72 // be avoided.
73 bool SeekCursor(FilePosition destination);
74
75 // Write to pre-allocated space.
76 // Note: |pos| must match |cursor_|.
77 template <class DataType>
78 bool Write(FilePosition pos, const DataType& data);
79 bool WriteBytes(FilePosition pos, size_t size_bytes, const char* data);
80
81 // Allocate space for and write the contents of |data|. On success, |pos|
82 // contains the location of the write. Returns true on success, false
83 // otherwise.
84 template <class DataType>
85 bool Append(const DataType& data, FilePosition* pos);
86 template <class DataType>
87 bool AppendVec(const std::vector<DataType>& data, FilePosition* pos);
88 bool AppendUtf8String(base::StringPiece data, FilePosition* pos);
89 bool AppendBytes(base::StringPiece data, FilePosition* pos);
90
91 void RegisterDirectoryEntry(uint32_t stream_type,
92 FilePosition pos,
93 uint32_t size);
94
95 // The next allocatable FilePosition.
96 FilePosition next_available_byte_;
97
98 // Storage for the directory during writes.
99 std::vector<MINIDUMP_DIRECTORY> directory_;
100
101 // The file to write to. Only valid within the scope of a call to WriteDump.
102 base::File* minidump_file_;
Sigurður Ásgeirsson 2016/09/13 17:36:56 Do you need to null-initialize this in a construct
manzagop (departed) 2016/09/13 21:19:41 No you're right. =default is equivalent to {} exce
103
104 DISALLOW_COPY_AND_ASSIGN(PostmortemMinidumpWriter);
105 };
106
107 // Information pertaining to the report and required by CrashPad.
108 struct PostmortemMinidumpWriter::ReportInfo {
109 crashpad::UUID client_id; // The client's identifier.
110 crashpad::UUID report_id; // The report's identifier.
111 std::string product_name; // The product name to be used by the reporter.
112 std::string version_number; // The product's version number.
113 };
114
115 template <class DataType>
116 bool PostmortemMinidumpWriter::Write(FilePosition pos, const DataType& data) {
117 static_assert(std::is_trivially_copyable<DataType>::value,
118 "restricted to trivially copyable");
119 return WriteBytes(pos, sizeof(data), reinterpret_cast<const char*>(&data));
120 }
121
122 template <class DataType>
123 bool PostmortemMinidumpWriter::Append(const DataType& data, FilePosition* pos) {
124 static_assert(std::is_trivially_copyable<DataType>::value,
125 "restricted to trivially copyable");
126 DCHECK(pos);
127 if (!Allocate(sizeof(data), pos))
128 return false;
129 return Write(*pos, data);
130 }
131
132 template <class DataType>
133 bool PostmortemMinidumpWriter::AppendVec(const std::vector<DataType>& data,
134 FilePosition* pos) {
135 static_assert(std::is_trivially_copyable<DataType>::value,
136 "restricted to trivially copyable");
137 DCHECK(!data.empty());
138 DCHECK(pos);
139
140 size_t size_bytes = sizeof(DataType) * data.size();
141 if (!Allocate(size_bytes, pos))
142 return false;
143 return WriteBytes(*pos, size_bytes,
144 reinterpret_cast<const char*>(&data.at(0)));
145 }
146
147 } // namespace browser_watcher
148
149 #endif // COMPONENTS_BROWSER_WATCHER_POSTMORTEM_MINIDUMP_WRITER_H_
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698