| OLD | NEW |
| 1 // Copyright 2014 The Crashpad Authors. All rights reserved. | 1 // Copyright 2014 The Crashpad Authors. All rights reserved. |
| 2 // | 2 // |
| 3 // Licensed under the Apache License, Version 2.0 (the "License"); | 3 // Licensed under the Apache License, Version 2.0 (the "License"); |
| 4 // you may not use this file except in compliance with the License. | 4 // you may not use this file except in compliance with the License. |
| 5 // You may obtain a copy of the License at | 5 // You may obtain a copy of the License at |
| 6 // | 6 // |
| 7 // http://www.apache.org/licenses/LICENSE-2.0 | 7 // http://www.apache.org/licenses/LICENSE-2.0 |
| 8 // | 8 // |
| 9 // Unless required by applicable law or agreed to in writing, software | 9 // Unless required by applicable law or agreed to in writing, software |
| 10 // distributed under the License is distributed on an "AS IS" BASIS, | 10 // distributed under the License is distributed on an "AS IS" BASIS, |
| 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| 12 // See the License for the specific language governing permissions and | 12 // See the License for the specific language governing permissions and |
| 13 // limitations under the License. | 13 // limitations under the License. |
| 14 | 14 |
| 15 #include "minidump/minidump_system_info_writer.h" | 15 #include "minidump/minidump_system_info_writer.h" |
| 16 | 16 |
| 17 #include <string.h> | 17 #include <string.h> |
| 18 | 18 |
| 19 #include "base/logging.h" | 19 #include "base/logging.h" |
| 20 #include "minidump/minidump_string_writer.h" | 20 #include "minidump/minidump_string_writer.h" |
| 21 #include "snapshot/system_snapshot.h" | 21 #include "snapshot/system_snapshot.h" |
| 22 #include "util/file/file_writer.h" | 22 #include "util/file/file_writer.h" |
| 23 #include "util/misc/arraysize_unsafe.h" |
| 23 #include "util/misc/implicit_cast.h" | 24 #include "util/misc/implicit_cast.h" |
| 24 | 25 |
| 25 namespace crashpad { | 26 namespace crashpad { |
| 26 | 27 |
| 27 namespace { | 28 namespace { |
| 28 | 29 |
| 29 uint64_t AMD64FeaturesFromSystemSnapshot( | 30 uint64_t AMD64FeaturesFromSystemSnapshot( |
| 30 const SystemSnapshot* system_snapshot) { | 31 const SystemSnapshot* system_snapshot) { |
| 31 #define ADD_FEATURE(minidump_bit) (UINT64_C(1) << (minidump_bit)) | 32 #define ADD_FEATURE(minidump_bit) (UINT64_C(1) << (minidump_bit)) |
| 32 | 33 |
| (...skipping 24 matching lines...) Expand all Loading... |
| 57 MAP_FEATURE(cpuid_features, F_PAE, PF_PAE_ENABLED); | 58 MAP_FEATURE(cpuid_features, F_PAE, PF_PAE_ENABLED); |
| 58 MAP_FEATURE(cpuid_features, F_MMX, PF_MMX_INSTRUCTIONS_AVAILABLE); | 59 MAP_FEATURE(cpuid_features, F_MMX, PF_MMX_INSTRUCTIONS_AVAILABLE); |
| 59 MAP_FEATURE(cpuid_features, F_SSE, PF_XMMI_INSTRUCTIONS_AVAILABLE); | 60 MAP_FEATURE(cpuid_features, F_SSE, PF_XMMI_INSTRUCTIONS_AVAILABLE); |
| 60 MAP_FEATURE(cpuid_features, F_SSE2, PF_XMMI64_INSTRUCTIONS_AVAILABLE); | 61 MAP_FEATURE(cpuid_features, F_SSE2, PF_XMMI64_INSTRUCTIONS_AVAILABLE); |
| 61 MAP_FEATURE(cpuid_features, F_SSE3, PF_SSE3_INSTRUCTIONS_AVAILABLE); | 62 MAP_FEATURE(cpuid_features, F_SSE3, PF_SSE3_INSTRUCTIONS_AVAILABLE); |
| 62 MAP_FEATURE(cpuid_features, F_CX16, PF_COMPARE_EXCHANGE128); | 63 MAP_FEATURE(cpuid_features, F_CX16, PF_COMPARE_EXCHANGE128); |
| 63 MAP_FEATURE(cpuid_features, F_XSAVE, PF_XSAVE_ENABLED); | 64 MAP_FEATURE(cpuid_features, F_XSAVE, PF_XSAVE_ENABLED); |
| 64 MAP_FEATURE(cpuid_features, F_RDRAND, PF_RDRAND_INSTRUCTION_AVAILABLE); | 65 MAP_FEATURE(cpuid_features, F_RDRAND, PF_RDRAND_INSTRUCTION_AVAILABLE); |
| 65 | 66 |
| 66 #define FX_XD 20 | 67 #define FX_XD 20 |
| 68 #define FX_RDTSCP 27 |
| 67 #define FX_3DNOW 31 | 69 #define FX_3DNOW 31 |
| 68 | 70 |
| 69 uint64_t extended_features = system_snapshot->CPUX86ExtendedFeatures(); | 71 uint64_t extended_features = system_snapshot->CPUX86ExtendedFeatures(); |
| 70 | 72 |
| 73 MAP_FEATURE(extended_features, FX_RDTSCP, PF_RDTSCP_INSTRUCTION_AVAILABLE); |
| 71 MAP_FEATURE(extended_features, FX_3DNOW, PF_3DNOW_INSTRUCTIONS_AVAILABLE); | 74 MAP_FEATURE(extended_features, FX_3DNOW, PF_3DNOW_INSTRUCTIONS_AVAILABLE); |
| 72 | 75 |
| 73 #define F7_FSGSBASE 0 | 76 #define F7_FSGSBASE 0 |
| 74 | 77 |
| 75 uint32_t leaf7_features = system_snapshot->CPUX86Leaf7Features(); | 78 uint32_t leaf7_features = system_snapshot->CPUX86Leaf7Features(); |
| 76 | 79 |
| 77 MAP_FEATURE(leaf7_features, F7_FSGSBASE, PF_RDWRFSGSBASE_AVAILABLE); | 80 MAP_FEATURE(leaf7_features, F7_FSGSBASE, PF_RDWRFSGSBASE_AVAILABLE); |
| 78 | 81 |
| 79 // This feature bit should be set if NX (XD, DEP) is enabled, not just if | 82 // This feature bit should be set if NX (XD, DEP) is enabled, not just if it’s |
| 80 // it’s available on the CPU as indicated by the XF_XD bit. | 83 // available on the CPU as indicated by the FX_XD bit. |
| 81 if (system_snapshot->NXEnabled()) { | 84 if (system_snapshot->NXEnabled()) { |
| 82 minidump_features |= ADD_FEATURE(PF_NX_ENABLED); | 85 minidump_features |= ADD_FEATURE(PF_NX_ENABLED); |
| 83 } | 86 } |
| 84 | 87 |
| 85 if (system_snapshot->CPUX86SupportsDAZ()) { | 88 if (system_snapshot->CPUX86SupportsDAZ()) { |
| 86 minidump_features |= ADD_FEATURE(PF_SSE_DAZ_MODE_AVAILABLE); | 89 minidump_features |= ADD_FEATURE(PF_SSE_DAZ_MODE_AVAILABLE); |
| 87 } | 90 } |
| 88 | 91 |
| 89 // PF_SECOND_LEVEL_ADDRESS_TRANSLATION can’t be determined without | 92 // PF_SECOND_LEVEL_ADDRESS_TRANSLATION can’t be determined without consulting |
| 90 // consulting model-specific registers, a privileged operation. The exact | 93 // model-specific registers, a privileged operation. The exact use of |
| 91 // use of PF_VIRT_FIRMWARE_ENABLED is unknown. PF_FASTFAIL_AVAILABLE is | 94 // PF_VIRT_FIRMWARE_ENABLED is unknown. PF_FASTFAIL_AVAILABLE is irrelevant |
| 92 // irrelevant outside of Windows. | 95 // outside of Windows. |
| 93 | 96 |
| 94 #undef MAP_FEATURE | 97 #undef MAP_FEATURE |
| 95 #undef ADD_FEATURE | 98 #undef ADD_FEATURE |
| 96 | 99 |
| 97 return minidump_features; | 100 return minidump_features; |
| 98 } | 101 } |
| 99 | 102 |
| 100 } // namespace | 103 } // namespace |
| 101 | 104 |
| 102 MinidumpSystemInfoWriter::MinidumpSystemInfoWriter() | 105 MinidumpSystemInfoWriter::MinidumpSystemInfoWriter() |
| (...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 187 } | 190 } |
| 188 | 191 |
| 189 void MinidumpSystemInfoWriter::SetCPUX86Vendor(uint32_t ebx, | 192 void MinidumpSystemInfoWriter::SetCPUX86Vendor(uint32_t ebx, |
| 190 uint32_t edx, | 193 uint32_t edx, |
| 191 uint32_t ecx) { | 194 uint32_t ecx) { |
| 192 DCHECK_EQ(state(), kStateMutable); | 195 DCHECK_EQ(state(), kStateMutable); |
| 193 DCHECK(system_info_.ProcessorArchitecture == kMinidumpCPUArchitectureX86 || | 196 DCHECK(system_info_.ProcessorArchitecture == kMinidumpCPUArchitectureX86 || |
| 194 system_info_.ProcessorArchitecture == | 197 system_info_.ProcessorArchitecture == |
| 195 kMinidumpCPUArchitectureX86Win64); | 198 kMinidumpCPUArchitectureX86Win64); |
| 196 | 199 |
| 197 static_assert(arraysize(system_info_.Cpu.X86CpuInfo.VendorId) == 3, | 200 static_assert(ARRAYSIZE_UNSAFE(system_info_.Cpu.X86CpuInfo.VendorId) == 3, |
| 198 "VendorId must have 3 elements"); | 201 "VendorId must have 3 elements"); |
| 199 | 202 |
| 200 system_info_.Cpu.X86CpuInfo.VendorId[0] = ebx; | 203 system_info_.Cpu.X86CpuInfo.VendorId[0] = ebx; |
| 201 system_info_.Cpu.X86CpuInfo.VendorId[1] = edx; | 204 system_info_.Cpu.X86CpuInfo.VendorId[1] = edx; |
| 202 system_info_.Cpu.X86CpuInfo.VendorId[2] = ecx; | 205 system_info_.Cpu.X86CpuInfo.VendorId[2] = ecx; |
| 203 } | 206 } |
| 204 | 207 |
| 205 void MinidumpSystemInfoWriter::SetCPUX86VendorString( | 208 void MinidumpSystemInfoWriter::SetCPUX86VendorString( |
| 206 const std::string& vendor) { | 209 const std::string& vendor) { |
| 207 DCHECK_EQ(state(), kStateMutable); | 210 DCHECK_EQ(state(), kStateMutable); |
| (...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 245 system_info_.Cpu.X86CpuInfo.AMDExtendedCpuFeatures = extended_features; | 248 system_info_.Cpu.X86CpuInfo.AMDExtendedCpuFeatures = extended_features; |
| 246 } | 249 } |
| 247 | 250 |
| 248 void MinidumpSystemInfoWriter::SetCPUOtherFeatures(uint64_t features_0, | 251 void MinidumpSystemInfoWriter::SetCPUOtherFeatures(uint64_t features_0, |
| 249 uint64_t features_1) { | 252 uint64_t features_1) { |
| 250 DCHECK_EQ(state(), kStateMutable); | 253 DCHECK_EQ(state(), kStateMutable); |
| 251 DCHECK(system_info_.ProcessorArchitecture != kMinidumpCPUArchitectureX86 && | 254 DCHECK(system_info_.ProcessorArchitecture != kMinidumpCPUArchitectureX86 && |
| 252 system_info_.ProcessorArchitecture != | 255 system_info_.ProcessorArchitecture != |
| 253 kMinidumpCPUArchitectureX86Win64); | 256 kMinidumpCPUArchitectureX86Win64); |
| 254 | 257 |
| 255 static_assert(arraysize(system_info_.Cpu.OtherCpuInfo.ProcessorFeatures) == 2, | 258 static_assert( |
| 256 "ProcessorFeatures must have 2 elements"); | 259 ARRAYSIZE_UNSAFE(system_info_.Cpu.OtherCpuInfo.ProcessorFeatures) == 2, |
| 260 "ProcessorFeatures must have 2 elements"); |
| 257 | 261 |
| 258 system_info_.Cpu.OtherCpuInfo.ProcessorFeatures[0] = features_0; | 262 system_info_.Cpu.OtherCpuInfo.ProcessorFeatures[0] = features_0; |
| 259 system_info_.Cpu.OtherCpuInfo.ProcessorFeatures[1] = features_1; | 263 system_info_.Cpu.OtherCpuInfo.ProcessorFeatures[1] = features_1; |
| 260 } | 264 } |
| 261 | 265 |
| 262 bool MinidumpSystemInfoWriter::Freeze() { | 266 bool MinidumpSystemInfoWriter::Freeze() { |
| 263 DCHECK_EQ(state(), kStateMutable); | 267 DCHECK_EQ(state(), kStateMutable); |
| 264 CHECK(csd_version_); | 268 CHECK(csd_version_); |
| 265 | 269 |
| 266 if (!MinidumpStreamWriter::Freeze()) { | 270 if (!MinidumpStreamWriter::Freeze()) { |
| (...skipping 23 matching lines...) Expand all Loading... |
| 290 DCHECK_EQ(state(), kStateWritable); | 294 DCHECK_EQ(state(), kStateWritable); |
| 291 | 295 |
| 292 return file_writer->Write(&system_info_, sizeof(system_info_)); | 296 return file_writer->Write(&system_info_, sizeof(system_info_)); |
| 293 } | 297 } |
| 294 | 298 |
| 295 MinidumpStreamType MinidumpSystemInfoWriter::StreamType() const { | 299 MinidumpStreamType MinidumpSystemInfoWriter::StreamType() const { |
| 296 return kMinidumpStreamTypeSystemInfo; | 300 return kMinidumpStreamTypeSystemInfo; |
| 297 } | 301 } |
| 298 | 302 |
| 299 } // namespace crashpad | 303 } // namespace crashpad |
| OLD | NEW |