michael@0: // Copyright (c) 2011 The Chromium Authors. All rights reserved. michael@0: // Use of this source code is governed by a BSD-style license that can be michael@0: // found in the LICENSE file. michael@0: michael@0: #ifndef SANDBOX_SRC_HANDLE_TABLE_H_ michael@0: #define SANDBOX_SRC_HANDLE_TABLE_H_ michael@0: michael@0: #include michael@0: #include michael@0: michael@0: #include "base/basictypes.h" michael@0: #include "base/strings/string16.h" michael@0: #include "sandbox/win/src/nt_internals.h" michael@0: michael@0: namespace sandbox { michael@0: michael@0: // HandleTable retrieves the global handle table and provides helper classes michael@0: // for iterating through the table and retrieving handle info. michael@0: class HandleTable { michael@0: public: michael@0: static const char16* HandleTable::kTypeProcess; michael@0: static const char16* HandleTable::kTypeThread; michael@0: static const char16* HandleTable::kTypeFile; michael@0: static const char16* HandleTable::kTypeDirectory; michael@0: static const char16* HandleTable::kTypeKey; michael@0: static const char16* HandleTable::kTypeWindowStation; michael@0: static const char16* HandleTable::kTypeDesktop; michael@0: static const char16* HandleTable::kTypeService; michael@0: static const char16* HandleTable::kTypeMutex; michael@0: static const char16* HandleTable::kTypeSemaphore; michael@0: static const char16* HandleTable::kTypeEvent; michael@0: static const char16* HandleTable::kTypeTimer; michael@0: static const char16* HandleTable::kTypeNamedPipe; michael@0: static const char16* HandleTable::kTypeJobObject; michael@0: static const char16* HandleTable::kTypeFileMap; michael@0: static const char16* HandleTable::kTypeAlpcPort; michael@0: michael@0: class Iterator; michael@0: michael@0: // Used by the iterator to provide simple caching accessors to handle data. michael@0: class HandleEntry { michael@0: public: michael@0: bool operator==(const HandleEntry& rhs) const { michael@0: return handle_entry_ == rhs.handle_entry_; michael@0: } michael@0: michael@0: bool operator!=(const HandleEntry& rhs) const { michael@0: return handle_entry_ != rhs.handle_entry_; michael@0: } michael@0: michael@0: const SYSTEM_HANDLE_INFORMATION* handle_entry() const { michael@0: return handle_entry_; michael@0: } michael@0: michael@0: const OBJECT_TYPE_INFORMATION* TypeInfo(); michael@0: michael@0: const string16& Name(); michael@0: michael@0: const string16& Type(); michael@0: michael@0: bool IsType(const string16& type_string); michael@0: michael@0: private: michael@0: friend class Iterator; michael@0: friend class HandleTable; michael@0: michael@0: enum UpdateType { michael@0: UPDATE_INFO_ONLY, michael@0: UPDATE_INFO_AND_NAME, michael@0: UPDATE_INFO_AND_TYPE_NAME, michael@0: }; michael@0: michael@0: explicit HandleEntry(const SYSTEM_HANDLE_INFORMATION* handle_info_entry); michael@0: michael@0: bool needs_info_update() { return handle_entry_ != last_entry_; } michael@0: michael@0: void UpdateInfo(UpdateType flag); michael@0: michael@0: OBJECT_TYPE_INFORMATION* type_info_internal() { michael@0: return reinterpret_cast( michael@0: &(type_info_buffer_[0])); michael@0: } michael@0: michael@0: const SYSTEM_HANDLE_INFORMATION* handle_entry_; michael@0: const SYSTEM_HANDLE_INFORMATION* last_entry_; michael@0: std::vector type_info_buffer_; michael@0: string16 handle_name_; michael@0: string16 type_name_; michael@0: michael@0: DISALLOW_COPY_AND_ASSIGN(HandleEntry); michael@0: }; michael@0: michael@0: class Iterator { michael@0: public: michael@0: Iterator(const HandleTable& table, const SYSTEM_HANDLE_INFORMATION* start, michael@0: const SYSTEM_HANDLE_INFORMATION* stop); michael@0: michael@0: Iterator(const Iterator& it); michael@0: michael@0: Iterator& operator++() { michael@0: if (++(current_.handle_entry_) == end_) michael@0: current_.handle_entry_ = table_.end(); michael@0: return *this; michael@0: } michael@0: michael@0: bool operator==(const Iterator& rhs) const { michael@0: return current_ == rhs.current_; michael@0: } michael@0: michael@0: bool operator!=(const Iterator& rhs) const { michael@0: return current_ != rhs.current_; michael@0: } michael@0: michael@0: HandleEntry& operator*() { return current_; } michael@0: michael@0: operator const SYSTEM_HANDLE_INFORMATION*() { michael@0: return current_.handle_entry_; michael@0: } michael@0: michael@0: HandleEntry* operator->() { return ¤t_; } michael@0: michael@0: private: michael@0: const HandleTable& table_; michael@0: HandleEntry current_; michael@0: const SYSTEM_HANDLE_INFORMATION* end_; michael@0: }; michael@0: michael@0: HandleTable(); michael@0: michael@0: Iterator begin() const { michael@0: return Iterator(*this, handle_info()->Information, michael@0: &handle_info()->Information[handle_info()->NumberOfHandles]); michael@0: } michael@0: michael@0: const SYSTEM_HANDLE_INFORMATION_EX* handle_info() const { michael@0: return reinterpret_cast( michael@0: &(handle_info_buffer_[0])); michael@0: } michael@0: michael@0: // Returns an iterator to the handles for only the supplied process ID. michael@0: Iterator HandlesForProcess(ULONG process_id) const; michael@0: const SYSTEM_HANDLE_INFORMATION* end() const { michael@0: return &handle_info()->Information[handle_info()->NumberOfHandles]; michael@0: } michael@0: michael@0: private: michael@0: SYSTEM_HANDLE_INFORMATION_EX* handle_info_internal() { michael@0: return reinterpret_cast( michael@0: &(handle_info_buffer_[0])); michael@0: } michael@0: michael@0: std::vector handle_info_buffer_; michael@0: michael@0: DISALLOW_COPY_AND_ASSIGN(HandleTable); michael@0: }; michael@0: michael@0: } // namespace sandbox michael@0: michael@0: #endif // SANDBOX_SRC_HANDLE_TABLE_H_