aboutsummaryrefslogtreecommitdiffstatshomepage
diff options
context:
space:
mode:
-rw-r--r--include/pdb/symbol.hpp44
-rw-r--r--src/symbol.cpp57
2 files changed, 62 insertions, 39 deletions
diff --git a/include/pdb/symbol.hpp b/include/pdb/symbol.hpp
index 6c36092..2e24a5a 100644
--- a/include/pdb/symbol.hpp
+++ b/include/pdb/symbol.hpp
@@ -13,10 +13,9 @@
#include <DbgHelp.h>
#include <Windows.h>
+#include <array>
#include <climits>
#include <cstddef>
-#include <cstring>
-#include <stdexcept>
#include <string>
namespace pdb {
@@ -38,32 +37,18 @@ class SymbolInfo {
public:
typedef SYMBOL_INFO Impl;
- SymbolInfo() : impl{*reinterpret_cast<Impl*>(buffer)} {
- impl.SizeOfStruct = sizeof(Impl);
- impl.MaxNameLen = MAX_SYM_NAME;
- }
-
- explicit SymbolInfo(const Impl& impl) : SymbolInfo{} {
- if (impl.SizeOfStruct != sizeof(impl))
- throw std::runtime_error{"invalid SYMBOL_INFO.SizeOfStruct"};
- const auto raw_size = calc_size(impl);
- if (raw_size > sizeof(buffer))
- throw std::runtime_error{"SYMBOL_INFO is too large"};
- std::memcpy(buffer, &impl, raw_size);
- }
+ SymbolInfo();
+ explicit SymbolInfo(const Impl& impl);
explicit operator Impl&() { return impl; }
-
explicit operator const Impl&() const { return impl; }
Address get_displacement() const { return displacement; }
-
void set_displacement(Address new_value) { displacement = new_value; }
std::string get_name() const { return {impl.Name, impl.NameLen}; }
Address get_offline_base() const { return impl.ModBase; }
-
Address get_offline_address() const { return impl.Address; }
symbol::Tag get_tag() const { return impl.Tag; }
@@ -80,15 +65,7 @@ public:
private:
static constexpr std::size_t max_buffer_size = sizeof(Impl) + MAX_SYM_NAME - 1;
- static std::size_t calc_size(const Impl& impl) {
- try {
- return SafeInt<std::size_t>{impl.SizeOfStruct} + impl.NameLen - 1;
- } catch (const SafeIntException&) {
- throw std::runtime_error{"invalid SYMBOL_INFO size"};
- }
- }
-
- unsigned char buffer[max_buffer_size] = {0};
+ std::array<unsigned char, max_buffer_size> buffer;
Address displacement = 0;
protected:
@@ -110,21 +87,10 @@ class LineInfo {
public:
typedef IMAGEHLP_LINE64 Impl;
- explicit LineInfo(const Impl& impl)
- : file_path{impl.FileName}, line_number{cast_line_number(impl.LineNumber)} {}
+ explicit LineInfo(const Impl& impl);
const std::string file_path;
const unsigned long line_number;
-
-private:
- static unsigned long cast_line_number(DWORD impl) {
- unsigned long dest = 0;
-
- if (!SafeCast(impl, dest))
- throw std::runtime_error{"invalid line number"};
-
- return dest;
- }
};
} // namespace pdb
diff --git a/src/symbol.cpp b/src/symbol.cpp
new file mode 100644
index 0000000..98ec427
--- /dev/null
+++ b/src/symbol.cpp
@@ -0,0 +1,57 @@
+// Copyright (c) 2020 Egor Tensin <Egor.Tensin@gmail.com>
+// This file is part of the "PDB repository" project.
+// For details, see https://github.com/egor-tensin/pdb-repo.
+// Distributed under the MIT License.
+
+#include "pdb/all.hpp"
+
+#include <SafeInt.hpp>
+
+#include <DbgHelp.h>
+#include <Windows.h>
+
+#include <cstddef>
+#include <cstring>
+#include <stdexcept>
+
+namespace pdb {
+namespace {
+
+std::size_t calc_size(const SymbolInfo::Impl& impl) {
+ try {
+ return SafeInt<std::size_t>{impl.SizeOfStruct} + impl.NameLen - 1;
+ } catch (const SafeIntException&) {
+ throw std::runtime_error{"invalid SYMBOL_INFO size"};
+ }
+}
+
+unsigned long cast_line_number(DWORD impl) {
+ unsigned long dest = 0;
+
+ if (!SafeCast(impl, dest))
+ throw std::runtime_error{"invalid line number"};
+
+ return dest;
+}
+
+} // namespace
+
+SymbolInfo::SymbolInfo() : buffer{}, impl{*reinterpret_cast<Impl*>(buffer.data())} {
+ buffer.fill(0);
+ impl.SizeOfStruct = sizeof(Impl);
+ impl.MaxNameLen = MAX_SYM_NAME;
+}
+
+SymbolInfo::SymbolInfo(const Impl& impl) : SymbolInfo{} {
+ if (impl.SizeOfStruct != sizeof(impl))
+ throw std::runtime_error{"invalid SYMBOL_INFO.SizeOfStruct"};
+ const auto impl_size = calc_size(impl);
+ if (impl_size > buffer.size())
+ throw std::runtime_error{"SYMBOL_INFO is too large"};
+ std::memcpy(buffer.data(), &impl, impl_size);
+}
+
+LineInfo::LineInfo(const Impl& impl)
+ : file_path{impl.FileName}, line_number{cast_line_number(impl.LineNumber)} {}
+
+} // namespace pdb