Remove another pile of unused stuff Change-Id: I926511deb046064b1c857e15a331bc73b53c97dc Reviewed-on: https://gn-review.googlesource.com/1622 Commit-Queue: Scott Graham <scottmg@chromium.org> Reviewed-by: Brett Wilson <brettw@chromium.org>
diff --git a/base/OWNERS b/base/OWNERS deleted file mode 100644 index 21d1970..0000000 --- a/base/OWNERS +++ /dev/null
@@ -1,52 +0,0 @@ -# About src/base: -# -# Chromium is a very mature project, most things that are generally useful are -# already here, and that things not here aren't generally useful. -# -# Base is pulled into many projects. For example, various ChromeOS daemons. So -# the bar for adding stuff is that it must have demonstrated wide -# applicability. Prefer to add things closer to where they're used (i.e. "not -# base"), and pull into base only when needed. In a project our size, -# sometimes even duplication is OK and inevitable. -# -# Adding a new logging macro DPVELOG_NE is not more clear than just -# writing the stuff you want to log in a regular logging statement, even -# if it makes your calling code longer. Just add it to your own code. -# -# If the code in question does not need to be used inside base, but will have -# multiple consumers across the codebase, consider placing it in a new directory -# under components/ instead. - -danakj@chromium.org -dcheng@chromium.org -gab@chromium.org -mark@chromium.org -thakis@chromium.org -thestig@chromium.org - -# For Bind/Callback: -per-file bind*=tzik@chromium.org -per-file callback*=tzik@chromium.org - -# For Android-specific changes: -per-file *android*=file://base/android/OWNERS -per-file BUILD.gn=file://base/android/OWNERS - -# For Fuchsia-specific changes: -per-file *_fuchsia*=file://build/fuchsia/OWNERS - -# For FeatureList API: -per-file feature_list*=asvitkine@chromium.org -per-file feature_list*=isherman@chromium.org - -# Restricted since rand_util.h also backs the cryptographically secure RNG. -per-file rand_util*=set noparent -per-file rand_util*=file://ipc/SECURITY_OWNERS - -# For TCMalloc tests: -per-file security_unittest.cc=jln@chromium.org - -# For Value: -per-file values*=jdoerrie@chromium.org - -# COMPONENT: Internals>Core
diff --git a/base/auto_reset.h b/base/auto_reset.h deleted file mode 100644 index 8515fe9..0000000 --- a/base/auto_reset.h +++ /dev/null
@@ -1,43 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_AUTO_RESET_H_ -#define BASE_AUTO_RESET_H_ - -#include <utility> - -#include "base/macros.h" - -// base::AutoReset<> is useful for setting a variable to a new value only within -// a particular scope. An base::AutoReset<> object resets a variable to its -// original value upon destruction, making it an alternative to writing -// "var = false;" or "var = old_val;" at all of a block's exit points. -// -// This should be obvious, but note that an base::AutoReset<> instance should -// have a shorter lifetime than its scoped_variable, to prevent invalid memory -// writes when the base::AutoReset<> object is destroyed. - -namespace base { - -template<typename T> -class AutoReset { - public: - AutoReset(T* scoped_variable, T new_value) - : scoped_variable_(scoped_variable), - original_value_(std::move(*scoped_variable)) { - *scoped_variable_ = std::move(new_value); - } - - ~AutoReset() { *scoped_variable_ = std::move(original_value_); } - - private: - T* scoped_variable_; - T original_value_; - - DISALLOW_COPY_AND_ASSIGN(AutoReset); -}; - -} // namespace base - -#endif // BASE_AUTO_RESET_H_
diff --git a/base/containers/OWNERS b/base/containers/OWNERS deleted file mode 100644 index cc39b28..0000000 --- a/base/containers/OWNERS +++ /dev/null
@@ -1,3 +0,0 @@ -danakj@chromium.org -dcheng@chromium.org -vmpstr@chromium.org
diff --git a/base/containers/README.md b/base/containers/README.md deleted file mode 100644 index 092a264..0000000 --- a/base/containers/README.md +++ /dev/null
@@ -1,295 +0,0 @@ -# base/containers library - -## What goes here - -This directory contains some STL-like containers. - -Things should be moved here that are generally applicable across the code base. -Don't add things here just because you need them in one place and think others -may someday want something similar. You can put specialized containers in -your component's directory and we can promote them here later if we feel there -is broad applicability. - -### Design and naming - -Containers should adhere as closely to STL as possible. Functions and behaviors -not present in STL should only be added when they are related to the specific -data structure implemented by the container. - -For STL-like containers our policy is that they should use STL-like naming even -when it may conflict with the style guide. So functions and class names should -be lower case with underscores. Non-STL-like classes and functions should use -Google naming. Be sure to use the base namespace. - -## Map and set selection - -### Usage advice - - * Generally avoid **std::unordered\_set** and **std::unordered\_map**. In the - common case, query performance is unlikely to be sufficiently higher than - std::map to make a difference, insert performance is slightly worse, and - the memory overhead is high. This makes sense mostly for large tables where - you expect a lot of lookups. - - * Most maps and sets in Chrome are small and contain objects that can be - moved efficiently. In this case, consider **base::flat\_map** and - **base::flat\_set**. You need to be aware of the maximum expected size of - the container since individual inserts and deletes are O(n), giving O(n^2) - construction time for the entire map. But because it avoids mallocs in most - cases, inserts are better or comparable to other containers even for - several dozen items, and efficiently-moved types are unlikely to have - performance problems for most cases until you have hundreds of items. If - your container can be constructed in one shot, the constructor from vector - gives O(n log n) construction times and it should be strictly better than - a std::map. - - * **base::small\_map** has better runtime memory usage without the poor - mutation performance of large containers that base::flat\_map has. But this - advantage is partially offset by additional code size. Prefer in cases - where you make many objects so that the code/heap tradeoff is good. - - * Use **std::map** and **std::set** if you can't decide. Even if they're not - great, they're unlikely to be bad or surprising. - -### Map and set details - -Sizes are on 64-bit platforms. Stable iterators aren't invalidated when the -container is mutated. - -| Container | Empty size | Per-item overhead | Stable iterators? | -|:---------------------------------------- |:--------------------- |:----------------- |:----------------- | -| std::map, std::set | 16 bytes | 32 bytes | Yes | -| std::unordered\_map, std::unordered\_set | 128 bytes | 16-24 bytes | No | -| base::flat\_map and base::flat\_set | 24 bytes | 0 (see notes) | No | -| base::small\_map | 24 bytes (see notes) | 32 bytes | No | - -**Takeaways:** std::unordered\_map and std::unordered\_map have high -overhead for small container sizes, prefer these only for larger workloads. - -Code size comparisons for a block of code (see appendix) on Windows using -strings as keys. - -| Container | Code size | -|:------------------- |:---------- | -| std::unordered\_map | 1646 bytes | -| std::map | 1759 bytes | -| base::flat\_map | 1872 bytes | -| base::small\_map | 2410 bytes | - -**Takeaways:** base::small\_map generates more code because of the inlining of -both brute-force and red-black tree searching. This makes it less attractive -for random one-off uses. But if your code is called frequently, the runtime -memory benefits will be more important. The code sizes of the other maps are -close enough it's not worth worrying about. - -### std::map and std::set - -A red-black tree. Each inserted item requires the memory allocation of a node -on the heap. Each node contains a left pointer, a right pointer, a parent -pointer, and a "color" for the red-black tree (32-bytes per item on 64-bits). - -### std::unordered\_map and std::unordered\_set - -A hash table. Implemented on Windows as a std::vector + std::list and in libc++ -as the equivalent of a std::vector + a std::forward\_list. Both implementations -allocate an 8-entry hash table (containing iterators into the list) on -initialization, and grow to 64 entries once 8 items are inserted. Above 64 -items, the size doubles every time the load factor exceeds 1. - -The empty size is sizeof(std::unordered\_map) = 64 + -the initial hash table size which is 8 pointers. The per-item overhead in the -table above counts the list node (2 pointers on Windows, 1 pointer in libc++), -plus amortizes the hash table assuming a 0.5 load factor on average. - -In a microbenchmark on Windows, inserts of 1M integers into a -std::unordered\_set took 1.07x the time of std::set, and queries took 0.67x the -time of std::set. For a typical 4-entry set (the statistical mode of map sizes -in the browser), query performance is identical to std::set and base::flat\_set. -On ARM, unordered\_set performance can be worse because integer division to -compute the bucket is slow, and a few "less than" operations can be faster than -computing a hash depending on the key type. The takeaway is that you should not -default to using unordered maps because "they're faster." - -### base::flat\_map and base::flat\_set - -A sorted std::vector. Seached via binary search, inserts in the middle require -moving elements to make room. Good cache locality. For large objects and large -set sizes, std::vector's doubling-when-full strategy can waste memory. - -Supports efficient construction from a vector of items which avoids the O(n^2) -insertion time of each element separately. - -The per-item overhead will depend on the underlying std::vector's reallocation -strategy and the memory access pattern. Assuming items are being linearly added, -one would expect it to be 3/4 full, so per-item overhead will be 0.25 * -sizeof(T). - - -flat\_set/flat\_map support a notion of transparent comparisons. Therefore you -can, for example, lookup base::StringPiece in a set of std::strings without -constructing a temporary std::string. This functionality is based on C++14 -extensions to std::set/std::map interface. - -You can find more information about transparent comparisons here: -http://en.cppreference.com/w/cpp/utility/functional/less_void - -Example, smart pointer set: - -```cpp -// Declare a type alias using base::UniquePtrComparator. -template <typename T> -using UniquePtrSet = base::flat_set<std::unique_ptr<T>, - base::UniquePtrComparator>; - -// ... -// Collect data. -std::vector<std::unique_ptr<int>> ptr_vec; -ptr_vec.reserve(5); -std::generate_n(std::back_inserter(ptr_vec), 5, []{ - return std::make_unique<int>(0); -}); - -// Construct a set. -UniquePtrSet<int> ptr_set(std::move(ptr_vec), base::KEEP_FIRST_OF_DUPES); - -// Use raw pointers to lookup keys. -int* ptr = ptr_set.begin()->get(); -EXPECT_TRUE(ptr_set.find(ptr) == ptr_set.begin()); -``` - -Example flat_map<std\::string, int>: - -```cpp -base::flat_map<std::string, int> str_to_int({{"a", 1}, {"c", 2},{"b", 2}}, - base::KEEP_FIRST_OF_DUPES); - -// Does not construct temporary strings. -str_to_int.find("c")->second = 3; -str_to_int.erase("c"); -EXPECT_EQ(str_to_int.end(), str_to_int.find("c")->second); - -// NOTE: This does construct a temporary string. This happens since if the -// item is not in the container, then it needs to be constructed, which is -// something that transparent comparators don't have to guarantee. -str_to_int["c"] = 3; -``` - -### base::small\_map - -A small inline buffer that is brute-force searched that overflows into a full -std::map or std::unordered\_map. This gives the memory benefit of -base::flat\_map for small data sizes without the degenerate insertion -performance for large container sizes. - -Since instantiations require both code for a std::map and a brute-force search -of the inline container, plus a fancy iterator to cover both cases, code size -is larger. - -The initial size in the above table is assuming a very small inline table. The -actual size will be sizeof(int) + min(sizeof(std::map), sizeof(T) * -inline\_size). - -# Deque - -### Usage advice - -Chromium code should always use `base::circular_deque` or `base::queue` in -preference to `std::deque` or `std::queue` due to memory usage and platform -variation. - -The `base::circular_deque` implementation (and the `base::queue` which uses it) -provide performance consistent across platforms that better matches most -programmer's expectations on performance (it doesn't waste as much space as -libc++ and doesn't do as many heap allocations as MSVC). It also generates less -code tham `std::queue`: using it across the code base saves several hundred -kilobytes. - -Since `base::deque` does not have stable iterators and it will move the objects -it contains, it may not be appropriate for all uses. If you need these, -consider using a `std::list` which will provide constant time insert and erase. - -### std::deque and std::queue - -The implementation of `std::deque` varies considerably which makes it hard to -reason about. All implementations use a sequence of data blocks referenced by -an array of pointers. The standard guarantees random access, amortized -constant operations at the ends, and linear mutations in the middle. - -In Microsoft's implementation, each block is the smaller of 16 bytes or the -size of the contained element. This means in practice that every expansion of -the deque of non-trivial classes requires a heap allocation. libc++ (on Android -and Mac) uses 4K blocks which elimiates the problem of many heap allocations, -but generally wastes a large amount of space (an Android analysis revealed more -than 2.5MB wasted space from deque alone, resulting in some optimizations). -libstdc++ uses an intermediate-size 512 byte buffer. - -Microsoft's implementation never shrinks the deque capacity, so the capacity -will always be the maximum number of elements ever contained. libstdc++ -deallocates blocks as they are freed. libc++ keeps up to two empty blocks. - -### base::circular_deque and base::queue - -A deque implemented as a circular buffer in an array. The underlying array will -grow like a `std::vector` while the beginning and end of the deque will move -around. The items will wrap around the underlying buffer so the storage will -not be contiguous, but fast random access iterators are still possible. - -When the underlying buffer is filled, it will be reallocated and the constents -moved (like a `std::vector`). The underlying buffer will be shrunk if there is -too much wasted space (_unlike_ a `std::vector`). As a result, iterators are -not stable across mutations. - -# Stack - -`std::stack` is like `std::queue` in that it is a wrapper around an underlying -container. The default container is `std::deque` so everything from the deque -section applies. - -Chromium provides `base/containers/stack.h` which defines `base::stack` that -should be used in preference to std::stack. This changes the underlying -container to `base::circular_deque`. The result will be very similar to -manually specifying a `std::vector` for the underlying implementation except -that the storage will shrink when it gets too empty (vector will never -reallocate to a smaller size). - -Watch out: with some stack usage patterns it's easy to depend on unstable -behavior: - -```cpp -base::stack<Foo> stack; -for (...) { - Foo& current = stack.top(); - DoStuff(); // May call stack.push(), say if writing a parser. - current.done = true; // Current may reference deleted item! -} -``` - -## Appendix - -### Code for map code size comparison - -This just calls insert and query a number of times, with printfs that prevent -things from being dead-code eliminated. - -```cpp -TEST(Foo, Bar) { - base::small_map<std::map<std::string, Flubber>> foo; - foo.insert(std::make_pair("foo", Flubber(8, "bar"))); - foo.insert(std::make_pair("bar", Flubber(8, "bar"))); - foo.insert(std::make_pair("foo1", Flubber(8, "bar"))); - foo.insert(std::make_pair("bar1", Flubber(8, "bar"))); - foo.insert(std::make_pair("foo", Flubber(8, "bar"))); - foo.insert(std::make_pair("bar", Flubber(8, "bar"))); - auto found = foo.find("asdf"); - printf("Found is %d\n", (int)(found == foo.end())); - found = foo.find("foo"); - printf("Found is %d\n", (int)(found == foo.end())); - found = foo.find("bar"); - printf("Found is %d\n", (int)(found == foo.end())); - found = foo.find("asdfhf"); - printf("Found is %d\n", (int)(found == foo.end())); - found = foo.find("bar1"); - printf("Found is %d\n", (int)(found == foo.end())); -} -``` -
diff --git a/base/containers/adapters.h b/base/containers/adapters.h deleted file mode 100644 index fa671b4..0000000 --- a/base/containers/adapters.h +++ /dev/null
@@ -1,73 +0,0 @@ -// Copyright 2014 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_CONTAINERS_ADAPTERS_H_ -#define BASE_CONTAINERS_ADAPTERS_H_ - -#include <stddef.h> - -#include <iterator> - -#include "base/macros.h" - -namespace base { - -namespace internal { - -// Internal adapter class for implementing base::Reversed. -template <typename T> -class ReversedAdapter { - public: - using Iterator = decltype(static_cast<T*>(nullptr)->rbegin()); - - explicit ReversedAdapter(T& t) : t_(t) {} - ReversedAdapter(const ReversedAdapter& ra) : t_(ra.t_) {} - - // TODO(mdempsky): Once we can use C++14 library features, use std::rbegin - // and std::rend instead, so we can remove the specialization below. - Iterator begin() const { return t_.rbegin(); } - Iterator end() const { return t_.rend(); } - - private: - T& t_; - - DISALLOW_ASSIGN(ReversedAdapter); -}; - -template <typename T, size_t N> -class ReversedAdapter<T[N]> { - public: - using Iterator = std::reverse_iterator<T*>; - - explicit ReversedAdapter(T (&t)[N]) : t_(t) {} - ReversedAdapter(const ReversedAdapter& ra) : t_(ra.t_) {} - - Iterator begin() const { return Iterator(&t_[N]); } - Iterator end() const { return Iterator(&t_[0]); } - - private: - T (&t_)[N]; - - DISALLOW_ASSIGN(ReversedAdapter); -}; - -} // namespace internal - -// Reversed returns a container adapter usable in a range-based "for" statement -// for iterating a reversible container in reverse order. -// -// Example: -// -// std::vector<int> v = ...; -// for (int i : base::Reversed(v)) { -// // iterates through v from back to front -// } -template <typename T> -internal::ReversedAdapter<T> Reversed(T& t) { - return internal::ReversedAdapter<T>(t); -} - -} // namespace base - -#endif // BASE_CONTAINERS_ADAPTERS_H_
diff --git a/base/containers/flat_set.h b/base/containers/flat_set.h deleted file mode 100644 index bf14c36..0000000 --- a/base/containers/flat_set.h +++ /dev/null
@@ -1,140 +0,0 @@ -// Copyright 2017 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_CONTAINERS_FLAT_SET_H_ -#define BASE_CONTAINERS_FLAT_SET_H_ - -#include <functional> - -#include "base/containers/flat_tree.h" -#include "base/template_util.h" - -namespace base { - -// flat_set is a container with a std::set-like interface that stores its -// contents in a sorted vector. -// -// Please see //base/containers/README.md for an overview of which container -// to select. -// -// PROS -// -// - Good memory locality. -// - Low overhead, especially for smaller sets. -// - Performance is good for more workloads than you might expect (see -// overview link above). -// - Supports C++14 set interface. -// -// CONS -// -// - Inserts and removals are O(n). -// -// IMPORTANT NOTES -// -// - Iterators are invalidated across mutations. -// - If possible, construct a flat_set in one operation by inserting into -// a std::vector and moving that vector into the flat_set constructor. -// - For multiple removals use base::EraseIf() which is O(n) rather than -// O(n * removed_items). -// -// QUICK REFERENCE -// -// Most of the core functionality is inherited from flat_tree. Please see -// flat_tree.h for more details for most of these functions. As a quick -// reference, the functions available are: -// -// Constructors (inputs need not be sorted): -// flat_set(InputIterator first, InputIterator last, -// FlatContainerDupes = KEEP_FIRST_OF_DUPES, -// const Compare& compare = Compare()); -// flat_set(const flat_set&); -// flat_set(flat_set&&); -// flat_set(std::vector<Key>, -// FlatContainerDupes = KEEP_FIRST_OF_DUPES, -// const Compare& compare = Compare()); // Re-use storage. -// flat_set(std::initializer_list<value_type> ilist, -// FlatContainerDupes = KEEP_FIRST_OF_DUPES, -// const Compare& comp = Compare()); -// -// Assignment functions: -// flat_set& operator=(const flat_set&); -// flat_set& operator=(flat_set&&); -// flat_set& operator=(initializer_list<Key>); -// -// Memory management functions: -// void reserve(size_t); -// size_t capacity() const; -// void shrink_to_fit(); -// -// Size management functions: -// void clear(); -// size_t size() const; -// size_t max_size() const; -// bool empty() const; -// -// Iterator functions: -// iterator begin(); -// const_iterator begin() const; -// const_iterator cbegin() const; -// iterator end(); -// const_iterator end() const; -// const_iterator cend() const; -// reverse_iterator rbegin(); -// const reverse_iterator rbegin() const; -// const_reverse_iterator crbegin() const; -// reverse_iterator rend(); -// const_reverse_iterator rend() const; -// const_reverse_iterator crend() const; -// -// Insert and accessor functions: -// pair<iterator, bool> insert(const key_type&); -// pair<iterator, bool> insert(key_type&&); -// void insert(InputIterator first, InputIterator last, -// FlatContainerDupes = KEEP_FIRST_OF_DUPES); -// iterator insert(const_iterator hint, const key_type&); -// iterator insert(const_iterator hint, key_type&&); -// pair<iterator, bool> emplace(Args&&...); -// iterator emplace_hint(const_iterator, Args&&...); -// -// Erase functions: -// iterator erase(iterator); -// iterator erase(const_iterator); -// iterator erase(const_iterator first, const_iterator& last); -// template <typename K> size_t erase(const K& key); -// -// Comparators (see std::set documentation). -// key_compare key_comp() const; -// value_compare value_comp() const; -// -// Search functions: -// template <typename K> size_t count(const K&) const; -// template <typename K> iterator find(const K&); -// template <typename K> const_iterator find(const K&) const; -// template <typename K> pair<iterator, iterator> equal_range(K&); -// template <typename K> iterator lower_bound(const K&); -// template <typename K> const_iterator lower_bound(const K&) const; -// template <typename K> iterator upper_bound(const K&); -// template <typename K> const_iterator upper_bound(const K&) const; -// -// General functions: -// void swap(flat_set&&); -// -// Non-member operators: -// bool operator==(const flat_set&, const flat_set); -// bool operator!=(const flat_set&, const flat_set); -// bool operator<(const flat_set&, const flat_set); -// bool operator>(const flat_set&, const flat_set); -// bool operator>=(const flat_set&, const flat_set); -// bool operator<=(const flat_set&, const flat_set); -// -template <class Key, class Compare = std::less<>> -using flat_set = typename ::base::internal::flat_tree< - Key, - Key, - ::base::internal::GetKeyFromValueIdentity<Key>, - Compare>; - -} // namespace base - -#endif // BASE_CONTAINERS_FLAT_SET_H_
diff --git a/base/containers/id_map.h b/base/containers/id_map.h deleted file mode 100644 index 4c816da..0000000 --- a/base/containers/id_map.h +++ /dev/null
@@ -1,290 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_CONTAINERS_ID_MAP_H_ -#define BASE_CONTAINERS_ID_MAP_H_ - -#include <stddef.h> -#include <stdint.h> - -#include <memory> -#include <set> -#include <type_traits> -#include <unordered_map> -#include <utility> - -#include "base/containers/flat_set.h" -#include "base/logging.h" -#include "base/macros.h" -#include "base/sequence_checker.h" - -namespace base { - -// This object maintains a list of IDs that can be quickly converted to -// pointers to objects. It is implemented as a hash table, optimized for -// relatively small data sets (in the common case, there will be exactly one -// item in the list). -// -// Items can be inserted into the container with arbitrary ID, but the caller -// must ensure they are unique. Inserting IDs and relying on automatically -// generated ones is not allowed because they can collide. - -// The map's value type (the V param) can be any dereferenceable type, such as a -// raw pointer or smart pointer -template <typename V, typename K = int32_t> -class IDMap final { - public: - using KeyType = K; - - private: - using T = typename std::remove_reference<decltype(*V())>::type; - - using HashTable = std::unordered_map<KeyType, V>; - - public: - IDMap() : iteration_depth_(0), next_id_(1), check_on_null_data_(false) { - // A number of consumers of IDMap create it on one thread but always - // access it from a different, but consistent, thread (or sequence) - // post-construction. The first call to CalledOnValidSequence() will re-bind - // it. - DETACH_FROM_SEQUENCE(sequence_checker_); - } - - ~IDMap() { - // Many IDMap's are static, and hence will be destroyed on the main - // thread. However, all the accesses may take place on another thread (or - // sequence), such as the IO thread. Detaching again to clean this up. - DETACH_FROM_SEQUENCE(sequence_checker_); - } - - // Sets whether Add and Replace should DCHECK if passed in NULL data. - // Default is false. - void set_check_on_null_data(bool value) { check_on_null_data_ = value; } - - // Adds a view with an automatically generated unique ID. See AddWithID. - KeyType Add(V data) { return AddInternal(std::move(data)); } - - // Adds a new data member with the specified ID. The ID must not be in - // the list. The caller either must generate all unique IDs itself and use - // this function, or allow this object to generate IDs and call Add. These - // two methods may not be mixed, or duplicate IDs may be generated. - void AddWithID(V data, KeyType id) { AddWithIDInternal(std::move(data), id); } - - void Remove(KeyType id) { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - typename HashTable::iterator i = data_.find(id); - if (i == data_.end() || IsRemoved(id)) { - NOTREACHED() << "Attempting to remove an item not in the list"; - return; - } - - if (iteration_depth_ == 0) { - data_.erase(i); - } else { - removed_ids_.insert(id); - } - } - - // Replaces the value for |id| with |new_data| and returns the existing value. - // Should only be called with an already added id. - V Replace(KeyType id, V new_data) { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - DCHECK(!check_on_null_data_ || new_data); - typename HashTable::iterator i = data_.find(id); - DCHECK(i != data_.end()); - DCHECK(!IsRemoved(id)); - - using std::swap; - swap(i->second, new_data); - return new_data; - } - - void Clear() { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - if (iteration_depth_ == 0) { - data_.clear(); - } else { - removed_ids_.reserve(data_.size()); - removed_ids_.insert(KeyIterator(data_.begin()), KeyIterator(data_.end())); - } - } - - bool IsEmpty() const { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - return size() == 0u; - } - - T* Lookup(KeyType id) const { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - typename HashTable::const_iterator i = data_.find(id); - if (i == data_.end() || !i->second || IsRemoved(id)) - return nullptr; - return &*i->second; - } - - size_t size() const { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - return data_.size() - removed_ids_.size(); - } - -#if defined(UNIT_TEST) - int iteration_depth() const { - return iteration_depth_; - } -#endif // defined(UNIT_TEST) - - // It is safe to remove elements from the map during iteration. All iterators - // will remain valid. - template<class ReturnType> - class Iterator { - public: - Iterator(IDMap<V, K>* map) : map_(map), iter_(map_->data_.begin()) { - Init(); - } - - Iterator(const Iterator& iter) - : map_(iter.map_), - iter_(iter.iter_) { - Init(); - } - - const Iterator& operator=(const Iterator& iter) { - map_ = iter.map; - iter_ = iter.iter; - Init(); - return *this; - } - - ~Iterator() { - DCHECK_CALLED_ON_VALID_SEQUENCE(map_->sequence_checker_); - - // We're going to decrement iteration depth. Make sure it's greater than - // zero so that it doesn't become negative. - DCHECK_LT(0, map_->iteration_depth_); - - if (--map_->iteration_depth_ == 0) - map_->Compact(); - } - - bool IsAtEnd() const { - DCHECK_CALLED_ON_VALID_SEQUENCE(map_->sequence_checker_); - return iter_ == map_->data_.end(); - } - - KeyType GetCurrentKey() const { - DCHECK_CALLED_ON_VALID_SEQUENCE(map_->sequence_checker_); - return iter_->first; - } - - ReturnType* GetCurrentValue() const { - DCHECK_CALLED_ON_VALID_SEQUENCE(map_->sequence_checker_); - if (!iter_->second || map_->IsRemoved(iter_->first)) - return nullptr; - return &*iter_->second; - } - - void Advance() { - DCHECK_CALLED_ON_VALID_SEQUENCE(map_->sequence_checker_); - ++iter_; - SkipRemovedEntries(); - } - - private: - void Init() { - DCHECK_CALLED_ON_VALID_SEQUENCE(map_->sequence_checker_); - ++map_->iteration_depth_; - SkipRemovedEntries(); - } - - void SkipRemovedEntries() { - while (iter_ != map_->data_.end() && map_->IsRemoved(iter_->first)) - ++iter_; - } - - IDMap<V, K>* map_; - typename HashTable::const_iterator iter_; - }; - - typedef Iterator<T> iterator; - typedef Iterator<const T> const_iterator; - - private: - // Transforms a map iterator to an iterator on the keys of the map. - // Used by Clear() to populate |removed_ids_| in bulk. - struct KeyIterator : std::iterator<std::forward_iterator_tag, KeyType> { - using inner_iterator = typename HashTable::iterator; - inner_iterator iter_; - - KeyIterator(inner_iterator iter) : iter_(iter) {} - KeyType operator*() const { return iter_->first; } - KeyIterator& operator++() { - ++iter_; - return *this; - } - KeyIterator operator++(int) { return KeyIterator(iter_++); } - bool operator==(const KeyIterator& other) const { - return iter_ == other.iter_; - } - bool operator!=(const KeyIterator& other) const { - return iter_ != other.iter_; - } - }; - - KeyType AddInternal(V data) { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - DCHECK(!check_on_null_data_ || data); - KeyType this_id = next_id_; - DCHECK(data_.find(this_id) == data_.end()) << "Inserting duplicate item"; - data_[this_id] = std::move(data); - next_id_++; - return this_id; - } - - void AddWithIDInternal(V data, KeyType id) { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - DCHECK(!check_on_null_data_ || data); - if (IsRemoved(id)) { - removed_ids_.erase(id); - } else { - DCHECK(data_.find(id) == data_.end()) << "Inserting duplicate item"; - } - data_[id] = std::move(data); - } - - bool IsRemoved(KeyType key) const { - return removed_ids_.find(key) != removed_ids_.end(); - } - - void Compact() { - DCHECK_EQ(0, iteration_depth_); - for (const auto& i : removed_ids_) - data_.erase(i); - removed_ids_.clear(); - } - - // Keep track of how many iterators are currently iterating on us to safely - // handle removing items during iteration. - int iteration_depth_; - - // Keep set of IDs that should be removed after the outermost iteration has - // finished. This way we manage to not invalidate the iterator when an element - // is removed. - base::flat_set<KeyType> removed_ids_; - - // The next ID that we will return from Add() - KeyType next_id_; - - HashTable data_; - - // See description above setter. - bool check_on_null_data_; - - SEQUENCE_CHECKER(sequence_checker_); - - DISALLOW_COPY_AND_ASSIGN(IDMap); -}; - -} // namespace base - -#endif // BASE_CONTAINERS_ID_MAP_H_
diff --git a/base/containers/linked_list.h b/base/containers/linked_list.h deleted file mode 100644 index a913bad..0000000 --- a/base/containers/linked_list.h +++ /dev/null
@@ -1,190 +0,0 @@ -// Copyright (c) 2009 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_CONTAINERS_LINKED_LIST_H_ -#define BASE_CONTAINERS_LINKED_LIST_H_ - -#include "base/macros.h" - -// Simple LinkedList type. (See the Q&A section to understand how this -// differs from std::list). -// -// To use, start by declaring the class which will be contained in the linked -// list, as extending LinkNode (this gives it next/previous pointers). -// -// class MyNodeType : public LinkNode<MyNodeType> { -// ... -// }; -// -// Next, to keep track of the list's head/tail, use a LinkedList instance: -// -// LinkedList<MyNodeType> list; -// -// To add elements to the list, use any of LinkedList::Append, -// LinkNode::InsertBefore, or LinkNode::InsertAfter: -// -// LinkNode<MyNodeType>* n1 = ...; -// LinkNode<MyNodeType>* n2 = ...; -// LinkNode<MyNodeType>* n3 = ...; -// -// list.Append(n1); -// list.Append(n3); -// n3->InsertBefore(n3); -// -// Lastly, to iterate through the linked list forwards: -// -// for (LinkNode<MyNodeType>* node = list.head(); -// node != list.end(); -// node = node->next()) { -// MyNodeType* value = node->value(); -// ... -// } -// -// Or to iterate the linked list backwards: -// -// for (LinkNode<MyNodeType>* node = list.tail(); -// node != list.end(); -// node = node->previous()) { -// MyNodeType* value = node->value(); -// ... -// } -// -// Questions and Answers: -// -// Q. Should I use std::list or base::LinkedList? -// -// A. The main reason to use base::LinkedList over std::list is -// performance. If you don't care about the performance differences -// then use an STL container, as it makes for better code readability. -// -// Comparing the performance of base::LinkedList<T> to std::list<T*>: -// -// * Erasing an element of type T* from base::LinkedList<T> is -// an O(1) operation. Whereas for std::list<T*> it is O(n). -// That is because with std::list<T*> you must obtain an -// iterator to the T* element before you can call erase(iterator). -// -// * Insertion operations with base::LinkedList<T> never require -// heap allocations. -// -// Q. How does base::LinkedList implementation differ from std::list? -// -// A. Doubly-linked lists are made up of nodes that contain "next" and -// "previous" pointers that reference other nodes in the list. -// -// With base::LinkedList<T>, the type being inserted already reserves -// space for the "next" and "previous" pointers (base::LinkNode<T>*). -// Whereas with std::list<T> the type can be anything, so the implementation -// needs to glue on the "next" and "previous" pointers using -// some internal node type. - -namespace base { - -template <typename T> -class LinkNode { - public: - LinkNode() : previous_(nullptr), next_(nullptr) {} - LinkNode(LinkNode<T>* previous, LinkNode<T>* next) - : previous_(previous), next_(next) {} - - LinkNode(LinkNode<T>&& rhs) { - next_ = rhs.next_; - rhs.next_ = nullptr; - previous_ = rhs.previous_; - rhs.previous_ = nullptr; - - // If the node belongs to a list, next_ and previous_ are both non-null. - // Otherwise, they are both null. - if (next_) { - next_->previous_ = this; - previous_->next_ = this; - } - } - - // Insert |this| into the linked list, before |e|. - void InsertBefore(LinkNode<T>* e) { - this->next_ = e; - this->previous_ = e->previous_; - e->previous_->next_ = this; - e->previous_ = this; - } - - // Insert |this| into the linked list, after |e|. - void InsertAfter(LinkNode<T>* e) { - this->next_ = e->next_; - this->previous_ = e; - e->next_->previous_ = this; - e->next_ = this; - } - - // Remove |this| from the linked list. - void RemoveFromList() { - this->previous_->next_ = this->next_; - this->next_->previous_ = this->previous_; - // next() and previous() return non-null if and only this node is not in any - // list. - this->next_ = nullptr; - this->previous_ = nullptr; - } - - LinkNode<T>* previous() const { - return previous_; - } - - LinkNode<T>* next() const { - return next_; - } - - // Cast from the node-type to the value type. - const T* value() const { - return static_cast<const T*>(this); - } - - T* value() { - return static_cast<T*>(this); - } - - private: - LinkNode<T>* previous_; - LinkNode<T>* next_; - - DISALLOW_COPY_AND_ASSIGN(LinkNode); -}; - -template <typename T> -class LinkedList { - public: - // The "root" node is self-referential, and forms the basis of a circular - // list (root_.next() will point back to the start of the list, - // and root_->previous() wraps around to the end of the list). - LinkedList() : root_(&root_, &root_) {} - - // Appends |e| to the end of the linked list. - void Append(LinkNode<T>* e) { - e->InsertBefore(&root_); - } - - LinkNode<T>* head() const { - return root_.next(); - } - - LinkNode<T>* tail() const { - return root_.previous(); - } - - const LinkNode<T>* end() const { - return &root_; - } - - bool empty() const { return head() == end(); } - - private: - LinkNode<T> root_; - - DISALLOW_COPY_AND_ASSIGN(LinkedList); -}; - -} // namespace base - -#endif // BASE_CONTAINERS_LINKED_LIST_H_
diff --git a/base/containers/mru_cache.h b/base/containers/mru_cache.h deleted file mode 100644 index 4a9f44e..0000000 --- a/base/containers/mru_cache.h +++ /dev/null
@@ -1,268 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -// This file contains a template for a Most Recently Used cache that allows -// constant-time access to items using a key, but easy identification of the -// least-recently-used items for removal. Each key can only be associated with -// one payload item at a time. -// -// The key object will be stored twice, so it should support efficient copying. -// -// NOTE: While all operations are O(1), this code is written for -// legibility rather than optimality. If future profiling identifies this as -// a bottleneck, there is room for smaller values of 1 in the O(1). :] - -#ifndef BASE_CONTAINERS_MRU_CACHE_H_ -#define BASE_CONTAINERS_MRU_CACHE_H_ - -#include <stddef.h> - -#include <algorithm> -#include <functional> -#include <list> -#include <map> -#include <unordered_map> -#include <utility> - -#include "base/logging.h" -#include "base/macros.h" - -namespace base { -namespace trace_event { -namespace internal { - -template <class MruCacheType> -size_t DoEstimateMemoryUsageForMruCache(const MruCacheType&); - -} // namespace internal -} // namespace trace_event - -// MRUCacheBase ---------------------------------------------------------------- - -// This template is used to standardize map type containers that can be used -// by MRUCacheBase. This level of indirection is necessary because of the way -// that template template params and default template params interact. -template <class KeyType, class ValueType, class CompareType> -struct MRUCacheStandardMap { - typedef std::map<KeyType, ValueType, CompareType> Type; -}; - -// Base class for the MRU cache specializations defined below. -template <class KeyType, - class PayloadType, - class HashOrCompareType, - template <typename, typename, typename> class MapType = - MRUCacheStandardMap> -class MRUCacheBase { - public: - // The payload of the list. This maintains a copy of the key so we can - // efficiently delete things given an element of the list. - typedef std::pair<KeyType, PayloadType> value_type; - - private: - typedef std::list<value_type> PayloadList; - typedef typename MapType<KeyType, - typename PayloadList::iterator, - HashOrCompareType>::Type KeyIndex; - - public: - typedef typename PayloadList::size_type size_type; - - typedef typename PayloadList::iterator iterator; - typedef typename PayloadList::const_iterator const_iterator; - typedef typename PayloadList::reverse_iterator reverse_iterator; - typedef typename PayloadList::const_reverse_iterator const_reverse_iterator; - - enum { NO_AUTO_EVICT = 0 }; - - // The max_size is the size at which the cache will prune its members to when - // a new item is inserted. If the caller wants to manager this itself (for - // example, maybe it has special work to do when something is evicted), it - // can pass NO_AUTO_EVICT to not restrict the cache size. - explicit MRUCacheBase(size_type max_size) : max_size_(max_size) {} - - virtual ~MRUCacheBase() = default; - - size_type max_size() const { return max_size_; } - - // Inserts a payload item with the given key. If an existing item has - // the same key, it is removed prior to insertion. An iterator indicating the - // inserted item will be returned (this will always be the front of the list). - // - // The payload will be forwarded. - template <typename Payload> - iterator Put(const KeyType& key, Payload&& payload) { - // Remove any existing payload with that key. - typename KeyIndex::iterator index_iter = index_.find(key); - if (index_iter != index_.end()) { - // Erase the reference to it. The index reference will be replaced in the - // code below. - Erase(index_iter->second); - } else if (max_size_ != NO_AUTO_EVICT) { - // New item is being inserted which might make it larger than the maximum - // size: kick the oldest thing out if necessary. - ShrinkToSize(max_size_ - 1); - } - - ordering_.emplace_front(key, std::forward<Payload>(payload)); - index_.emplace(key, ordering_.begin()); - return ordering_.begin(); - } - - // Retrieves the contents of the given key, or end() if not found. This method - // has the side effect of moving the requested item to the front of the - // recency list. - iterator Get(const KeyType& key) { - typename KeyIndex::iterator index_iter = index_.find(key); - if (index_iter == index_.end()) - return end(); - typename PayloadList::iterator iter = index_iter->second; - - // Move the touched item to the front of the recency ordering. - ordering_.splice(ordering_.begin(), ordering_, iter); - return ordering_.begin(); - } - - // Retrieves the payload associated with a given key and returns it via - // result without affecting the ordering (unlike Get). - iterator Peek(const KeyType& key) { - typename KeyIndex::const_iterator index_iter = index_.find(key); - if (index_iter == index_.end()) - return end(); - return index_iter->second; - } - - const_iterator Peek(const KeyType& key) const { - typename KeyIndex::const_iterator index_iter = index_.find(key); - if (index_iter == index_.end()) - return end(); - return index_iter->second; - } - - // Exchanges the contents of |this| by the contents of the |other|. - void Swap(MRUCacheBase& other) { - ordering_.swap(other.ordering_); - index_.swap(other.index_); - std::swap(max_size_, other.max_size_); - } - - // Erases the item referenced by the given iterator. An iterator to the item - // following it will be returned. The iterator must be valid. - iterator Erase(iterator pos) { - index_.erase(pos->first); - return ordering_.erase(pos); - } - - // MRUCache entries are often processed in reverse order, so we add this - // convenience function (not typically defined by STL containers). - reverse_iterator Erase(reverse_iterator pos) { - // We have to actually give it the incremented iterator to delete, since - // the forward iterator that base() returns is actually one past the item - // being iterated over. - return reverse_iterator(Erase((++pos).base())); - } - - // Shrinks the cache so it only holds |new_size| items. If |new_size| is - // bigger or equal to the current number of items, this will do nothing. - void ShrinkToSize(size_type new_size) { - for (size_type i = size(); i > new_size; i--) - Erase(rbegin()); - } - - // Deletes everything from the cache. - void Clear() { - index_.clear(); - ordering_.clear(); - } - - // Returns the number of elements in the cache. - size_type size() const { - // We don't use ordering_.size() for the return value because - // (as a linked list) it can be O(n). - DCHECK(index_.size() == ordering_.size()); - return index_.size(); - } - - // Allows iteration over the list. Forward iteration starts with the most - // recent item and works backwards. - // - // Note that since these iterators are actually iterators over a list, you - // can keep them as you insert or delete things (as long as you don't delete - // the one you are pointing to) and they will still be valid. - iterator begin() { return ordering_.begin(); } - const_iterator begin() const { return ordering_.begin(); } - iterator end() { return ordering_.end(); } - const_iterator end() const { return ordering_.end(); } - - reverse_iterator rbegin() { return ordering_.rbegin(); } - const_reverse_iterator rbegin() const { return ordering_.rbegin(); } - reverse_iterator rend() { return ordering_.rend(); } - const_reverse_iterator rend() const { return ordering_.rend(); } - - bool empty() const { return ordering_.empty(); } - - private: - template <class MruCacheType> - friend size_t trace_event::internal::DoEstimateMemoryUsageForMruCache( - const MruCacheType&); - - PayloadList ordering_; - KeyIndex index_; - - size_type max_size_; - - DISALLOW_COPY_AND_ASSIGN(MRUCacheBase); -}; - -// MRUCache -------------------------------------------------------------------- - -// A container that does not do anything to free its data. Use this when storing -// value types (as opposed to pointers) in the list. -template <class KeyType, - class PayloadType, - class CompareType = std::less<KeyType>> -class MRUCache : public MRUCacheBase<KeyType, PayloadType, CompareType> { - private: - using ParentType = MRUCacheBase<KeyType, PayloadType, CompareType>; - - public: - // See MRUCacheBase, noting the possibility of using NO_AUTO_EVICT. - explicit MRUCache(typename ParentType::size_type max_size) - : ParentType(max_size) {} - virtual ~MRUCache() = default; - - private: - DISALLOW_COPY_AND_ASSIGN(MRUCache); -}; - -// HashingMRUCache ------------------------------------------------------------ - -template <class KeyType, class ValueType, class HashType> -struct MRUCacheHashMap { - typedef std::unordered_map<KeyType, ValueType, HashType> Type; -}; - -// This class is similar to MRUCache, except that it uses std::unordered_map as -// the map type instead of std::map. Note that your KeyType must be hashable to -// use this cache or you need to provide a hashing class. -template <class KeyType, class PayloadType, class HashType = std::hash<KeyType>> -class HashingMRUCache - : public MRUCacheBase<KeyType, PayloadType, HashType, MRUCacheHashMap> { - private: - using ParentType = - MRUCacheBase<KeyType, PayloadType, HashType, MRUCacheHashMap>; - - public: - // See MRUCacheBase, noting the possibility of using NO_AUTO_EVICT. - explicit HashingMRUCache(typename ParentType::size_type max_size) - : ParentType(max_size) {} - virtual ~HashingMRUCache() = default; - - private: - DISALLOW_COPY_AND_ASSIGN(HashingMRUCache); -}; - -} // namespace base - -#endif // BASE_CONTAINERS_MRU_CACHE_H_
diff --git a/base/containers/ring_buffer.h b/base/containers/ring_buffer.h deleted file mode 100644 index 4e48907..0000000 --- a/base/containers/ring_buffer.h +++ /dev/null
@@ -1,119 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_CONTAINERS_RING_BUFFER_H_ -#define BASE_CONTAINERS_RING_BUFFER_H_ - -#include <stddef.h> - -#include "base/logging.h" -#include "base/macros.h" - -namespace base { - -// base::RingBuffer uses a fixed-size array, unlike base::circular_deque and -// std::deque, and so, one can access only the last |kSize| elements. Also, you -// can add elements to the front and read/modify random elements, but cannot -// remove elements from the back. Therefore, it does not have a |Size| method, -// only |BufferSize|, which is a constant, and |CurrentIndex|, which is the -// number of elements added so far. -// -// If the above is sufficient for your use case, base::RingBuffer should be more -// efficient than base::circular_deque. -template <typename T, size_t kSize> -class RingBuffer { - public: - RingBuffer() : current_index_(0) {} - - size_t BufferSize() const { return kSize; } - - size_t CurrentIndex() const { return current_index_; } - - // tests if a value was saved to this index - bool IsFilledIndex(size_t n) const { return BufferIndex(n) < current_index_; } - - // n = 0 returns the oldest value and - // n = bufferSize() - 1 returns the most recent value. - const T& ReadBuffer(size_t n) const { - DCHECK(IsFilledIndex(n)); - return buffer_[BufferIndex(n)]; - } - - T* MutableReadBuffer(size_t n) { - DCHECK(IsFilledIndex(n)); - return &buffer_[BufferIndex(n)]; - } - - void SaveToBuffer(const T& value) { - buffer_[BufferIndex(0)] = value; - current_index_++; - } - - void Clear() { current_index_ = 0; } - - // Iterator has const access to the RingBuffer it got retrieved from. - class Iterator { - public: - size_t index() const { return index_; } - - const T* operator->() const { return &buffer_.ReadBuffer(index_); } - const T* operator*() const { return &buffer_.ReadBuffer(index_); } - - Iterator& operator++() { - index_++; - if (index_ == kSize) - out_of_range_ = true; - return *this; - } - - Iterator& operator--() { - if (index_ == 0) - out_of_range_ = true; - index_--; - return *this; - } - - operator bool() const { - return buffer_.IsFilledIndex(index_) && !out_of_range_; - } - - private: - Iterator(const RingBuffer<T, kSize>& buffer, size_t index) - : buffer_(buffer), index_(index), out_of_range_(false) {} - - const RingBuffer<T, kSize>& buffer_; - size_t index_; - bool out_of_range_; - - friend class RingBuffer<T, kSize>; - }; - - // Returns an Iterator pointing to the oldest value in the buffer. - // Example usage (iterate from oldest to newest value): - // for (RingBuffer<T, kSize>::Iterator it = ring_buffer.Begin(); it; ++it) {} - Iterator Begin() const { - if (current_index_ < kSize) - return Iterator(*this, kSize - current_index_); - return Iterator(*this, 0); - } - - // Returns an Iterator pointing to the newest value in the buffer. - // Example usage (iterate backwards from newest to oldest value): - // for (RingBuffer<T, kSize>::Iterator it = ring_buffer.End(); it; --it) {} - Iterator End() const { return Iterator(*this, kSize - 1); } - - private: - inline size_t BufferIndex(size_t n) const { - return (current_index_ + n) % kSize; - } - - T buffer_[kSize]; - size_t current_index_; - - DISALLOW_COPY_AND_ASSIGN(RingBuffer); -}; - -} // namespace base - -#endif // BASE_CONTAINERS_RING_BUFFER_H_
diff --git a/base/containers/small_map.h b/base/containers/small_map.h deleted file mode 100644 index a235f11..0000000 --- a/base/containers/small_map.h +++ /dev/null
@@ -1,659 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_CONTAINERS_SMALL_MAP_H_ -#define BASE_CONTAINERS_SMALL_MAP_H_ - -#include <stddef.h> - -#include <map> -#include <new> -#include <string> -#include <utility> - -#include "base/logging.h" - -namespace base { - -// small_map is a container with a std::map-like interface. It starts out -// backed by a unsorted array but switches to some other container type if it -// grows beyond this fixed size. -// -// Please see //base/containers/README.md for an overview of which container -// to select. -// -// PROS -// -// - Good memory locality and low overhead for smaller maps. -// - Handles large maps without the degenerate performance of flat_map. -// -// CONS -// -// - Larger code size than the alternatives. -// -// IMPORTANT NOTES -// -// - Iterators are invalidated across mutations. -// -// DETAILS -// -// base::small_map will pick up the comparator from the underlying map type. In -// std::map only a "less" operator is defined, which requires us to do two -// comparisons per element when doing the brute-force search in the simple -// array. std::unordered_map has a key_equal function which will be used. -// -// We define default overrides for the common map types to avoid this -// double-compare, but you should be aware of this if you use your own -// operator< for your map and supply yor own version of == to the small_map. -// You can use regular operator== by just doing: -// -// base::small_map<std::map<MyKey, MyValue>, 4, std::equal_to<KyKey>> -// -// -// USAGE -// ----- -// -// NormalMap: The map type to fall back to. This also defines the key -// and value types for the small_map. -// kArraySize: The size of the initial array of results. This will be -// allocated with the small_map object rather than separately on -// the heap. Once the map grows beyond this size, the map type -// will be used instead. -// EqualKey: A functor which tests two keys for equality. If the wrapped -// map type has a "key_equal" member (hash_map does), then that will -// be used by default. If the wrapped map type has a strict weak -// ordering "key_compare" (std::map does), that will be used to -// implement equality by default. -// MapInit: A functor that takes a NormalMap* and uses it to initialize the map. -// This functor will be called at most once per small_map, when the map -// exceeds the threshold of kArraySize and we are about to copy values -// from the array to the map. The functor *must* initialize the -// NormalMap* argument with placement new, since after it runs we -// assume that the NormalMap has been initialized. -// -// example: -// base::small_map<std::map<string, int>> days; -// days["sunday" ] = 0; -// days["monday" ] = 1; -// days["tuesday" ] = 2; -// days["wednesday"] = 3; -// days["thursday" ] = 4; -// days["friday" ] = 5; -// days["saturday" ] = 6; - -namespace internal { - -template <typename NormalMap> -class small_map_default_init { - public: - void operator()(NormalMap* map) const { new (map) NormalMap(); } -}; - -// has_key_equal<M>::value is true iff there exists a type M::key_equal. This is -// used to dispatch to one of the select_equal_key<> metafunctions below. -template <typename M> -struct has_key_equal { - typedef char sml; // "small" is sometimes #defined so we use an abbreviation. - typedef struct { char dummy[2]; } big; - // Two functions, one accepts types that have a key_equal member, and one that - // accepts anything. They each return a value of a different size, so we can - // determine at compile-time which function would have been called. - template <typename U> static big test(typename U::key_equal*); - template <typename> static sml test(...); - // Determines if M::key_equal exists by looking at the size of the return - // type of the compiler-chosen test() function. - static const bool value = (sizeof(test<M>(0)) == sizeof(big)); -}; -template <typename M> const bool has_key_equal<M>::value; - -// Base template used for map types that do NOT have an M::key_equal member, -// e.g., std::map<>. These maps have a strict weak ordering comparator rather -// than an equality functor, so equality will be implemented in terms of that -// comparator. -// -// There's a partial specialization of this template below for map types that do -// have an M::key_equal member. -template <typename M, bool has_key_equal_value> -struct select_equal_key { - struct equal_key { - bool operator()(const typename M::key_type& left, - const typename M::key_type& right) { - // Implements equality in terms of a strict weak ordering comparator. - typename M::key_compare comp; - return !comp(left, right) && !comp(right, left); - } - }; -}; - -// Provide overrides to use operator== for key compare for the "normal" map and -// hash map types. If you override the default comparator or allocator for a -// map or hash_map, or use another type of map, this won't get used. -// -// If we switch to using std::unordered_map for base::hash_map, then the -// hash_map specialization can be removed. -template <typename KeyType, typename ValueType> -struct select_equal_key<std::map<KeyType, ValueType>, false> { - struct equal_key { - bool operator()(const KeyType& left, const KeyType& right) { - return left == right; - } - }; -}; -template <typename KeyType, typename ValueType> -struct select_equal_key<base::hash_map<KeyType, ValueType>, false> { - struct equal_key { - bool operator()(const KeyType& left, const KeyType& right) { - return left == right; - } - }; -}; - -// Partial template specialization handles case where M::key_equal exists, e.g., -// hash_map<>. -template <typename M> -struct select_equal_key<M, true> { - typedef typename M::key_equal equal_key; -}; - -} // namespace internal - -template <typename NormalMap, - int kArraySize = 4, - typename EqualKey = typename internal::select_equal_key< - NormalMap, - internal::has_key_equal<NormalMap>::value>::equal_key, - typename MapInit = internal::small_map_default_init<NormalMap>> -class small_map { - // We cannot rely on the compiler to reject array of size 0. In - // particular, gcc 2.95.3 does it but later versions allow 0-length - // arrays. Therefore, we explicitly reject non-positive kArraySize - // here. - static_assert(kArraySize > 0, "default initial size should be positive"); - - public: - typedef typename NormalMap::key_type key_type; - typedef typename NormalMap::mapped_type data_type; - typedef typename NormalMap::mapped_type mapped_type; - typedef typename NormalMap::value_type value_type; - typedef EqualKey key_equal; - - small_map() : size_(0), functor_(MapInit()) {} - - explicit small_map(const MapInit& functor) : size_(0), functor_(functor) {} - - // Allow copy-constructor and assignment, since STL allows them too. - small_map(const small_map& src) { - // size_ and functor_ are initted in InitFrom() - InitFrom(src); - } - void operator=(const small_map& src) { - if (&src == this) return; - - // This is not optimal. If src and dest are both using the small - // array, we could skip the teardown and reconstruct. One problem - // to be resolved is that the value_type itself is pair<const K, - // V>, and const K is not assignable. - Destroy(); - InitFrom(src); - } - ~small_map() { Destroy(); } - - class const_iterator; - - class iterator { - public: - typedef typename NormalMap::iterator::iterator_category iterator_category; - typedef typename NormalMap::iterator::value_type value_type; - typedef typename NormalMap::iterator::difference_type difference_type; - typedef typename NormalMap::iterator::pointer pointer; - typedef typename NormalMap::iterator::reference reference; - - inline iterator(): array_iter_(NULL) {} - - inline iterator& operator++() { - if (array_iter_ != NULL) { - ++array_iter_; - } else { - ++hash_iter_; - } - return *this; - } - inline iterator operator++(int /*unused*/) { - iterator result(*this); - ++(*this); - return result; - } - inline iterator& operator--() { - if (array_iter_ != NULL) { - --array_iter_; - } else { - --hash_iter_; - } - return *this; - } - inline iterator operator--(int /*unused*/) { - iterator result(*this); - --(*this); - return result; - } - inline value_type* operator->() const { - if (array_iter_ != NULL) { - return array_iter_; - } else { - return hash_iter_.operator->(); - } - } - - inline value_type& operator*() const { - if (array_iter_ != NULL) { - return *array_iter_; - } else { - return *hash_iter_; - } - } - - inline bool operator==(const iterator& other) const { - if (array_iter_ != NULL) { - return array_iter_ == other.array_iter_; - } else { - return other.array_iter_ == NULL && hash_iter_ == other.hash_iter_; - } - } - - inline bool operator!=(const iterator& other) const { - return !(*this == other); - } - - bool operator==(const const_iterator& other) const; - bool operator!=(const const_iterator& other) const; - - private: - friend class small_map; - friend class const_iterator; - inline explicit iterator(value_type* init) : array_iter_(init) {} - inline explicit iterator(const typename NormalMap::iterator& init) - : array_iter_(NULL), hash_iter_(init) {} - - value_type* array_iter_; - typename NormalMap::iterator hash_iter_; - }; - - class const_iterator { - public: - typedef typename NormalMap::const_iterator::iterator_category - iterator_category; - typedef typename NormalMap::const_iterator::value_type value_type; - typedef typename NormalMap::const_iterator::difference_type difference_type; - typedef typename NormalMap::const_iterator::pointer pointer; - typedef typename NormalMap::const_iterator::reference reference; - - inline const_iterator(): array_iter_(NULL) {} - // Non-explicit ctor lets us convert regular iterators to const iterators - inline const_iterator(const iterator& other) - : array_iter_(other.array_iter_), hash_iter_(other.hash_iter_) {} - - inline const_iterator& operator++() { - if (array_iter_ != NULL) { - ++array_iter_; - } else { - ++hash_iter_; - } - return *this; - } - inline const_iterator operator++(int /*unused*/) { - const_iterator result(*this); - ++(*this); - return result; - } - - inline const_iterator& operator--() { - if (array_iter_ != NULL) { - --array_iter_; - } else { - --hash_iter_; - } - return *this; - } - inline const_iterator operator--(int /*unused*/) { - const_iterator result(*this); - --(*this); - return result; - } - - inline const value_type* operator->() const { - if (array_iter_ != NULL) { - return array_iter_; - } else { - return hash_iter_.operator->(); - } - } - - inline const value_type& operator*() const { - if (array_iter_ != NULL) { - return *array_iter_; - } else { - return *hash_iter_; - } - } - - inline bool operator==(const const_iterator& other) const { - if (array_iter_ != NULL) { - return array_iter_ == other.array_iter_; - } else { - return other.array_iter_ == NULL && hash_iter_ == other.hash_iter_; - } - } - - inline bool operator!=(const const_iterator& other) const { - return !(*this == other); - } - - private: - friend class small_map; - inline explicit const_iterator(const value_type* init) - : array_iter_(init) {} - inline explicit const_iterator( - const typename NormalMap::const_iterator& init) - : array_iter_(NULL), hash_iter_(init) {} - - const value_type* array_iter_; - typename NormalMap::const_iterator hash_iter_; - }; - - iterator find(const key_type& key) { - key_equal compare; - if (size_ >= 0) { - for (int i = 0; i < size_; i++) { - if (compare(array_[i].first, key)) { - return iterator(array_ + i); - } - } - return iterator(array_ + size_); - } else { - return iterator(map()->find(key)); - } - } - - const_iterator find(const key_type& key) const { - key_equal compare; - if (size_ >= 0) { - for (int i = 0; i < size_; i++) { - if (compare(array_[i].first, key)) { - return const_iterator(array_ + i); - } - } - return const_iterator(array_ + size_); - } else { - return const_iterator(map()->find(key)); - } - } - - // Invalidates iterators. - data_type& operator[](const key_type& key) { - key_equal compare; - - if (size_ >= 0) { - // operator[] searches backwards, favoring recently-added - // elements. - for (int i = size_-1; i >= 0; --i) { - if (compare(array_[i].first, key)) { - return array_[i].second; - } - } - if (size_ == kArraySize) { - ConvertToRealMap(); - return map_[key]; - } else { - new (&array_[size_]) value_type(key, data_type()); - return array_[size_++].second; - } - } else { - return map_[key]; - } - } - - // Invalidates iterators. - std::pair<iterator, bool> insert(const value_type& x) { - key_equal compare; - - if (size_ >= 0) { - for (int i = 0; i < size_; i++) { - if (compare(array_[i].first, x.first)) { - return std::make_pair(iterator(array_ + i), false); - } - } - if (size_ == kArraySize) { - ConvertToRealMap(); // Invalidates all iterators! - std::pair<typename NormalMap::iterator, bool> ret = map_.insert(x); - return std::make_pair(iterator(ret.first), ret.second); - } else { - new (&array_[size_]) value_type(x); - return std::make_pair(iterator(array_ + size_++), true); - } - } else { - std::pair<typename NormalMap::iterator, bool> ret = map_.insert(x); - return std::make_pair(iterator(ret.first), ret.second); - } - } - - // Invalidates iterators. - template <class InputIterator> - void insert(InputIterator f, InputIterator l) { - while (f != l) { - insert(*f); - ++f; - } - } - - // Invalidates iterators. - template <typename... Args> - std::pair<iterator, bool> emplace(Args&&... args) { - key_equal compare; - - if (size_ >= 0) { - value_type x(std::forward<Args>(args)...); - for (int i = 0; i < size_; i++) { - if (compare(array_[i].first, x.first)) { - return std::make_pair(iterator(array_ + i), false); - } - } - if (size_ == kArraySize) { - ConvertToRealMap(); // Invalidates all iterators! - std::pair<typename NormalMap::iterator, bool> ret = - map_.emplace(std::move(x)); - return std::make_pair(iterator(ret.first), ret.second); - } else { - new (&array_[size_]) value_type(std::move(x)); - return std::make_pair(iterator(array_ + size_++), true); - } - } else { - std::pair<typename NormalMap::iterator, bool> ret = - map_.emplace(std::forward<Args>(args)...); - return std::make_pair(iterator(ret.first), ret.second); - } - } - - iterator begin() { - if (size_ >= 0) { - return iterator(array_); - } else { - return iterator(map_.begin()); - } - } - const_iterator begin() const { - if (size_ >= 0) { - return const_iterator(array_); - } else { - return const_iterator(map_.begin()); - } - } - - iterator end() { - if (size_ >= 0) { - return iterator(array_ + size_); - } else { - return iterator(map_.end()); - } - } - const_iterator end() const { - if (size_ >= 0) { - return const_iterator(array_ + size_); - } else { - return const_iterator(map_.end()); - } - } - - void clear() { - if (size_ >= 0) { - for (int i = 0; i < size_; i++) { - array_[i].~value_type(); - } - } else { - map_.~NormalMap(); - } - size_ = 0; - } - - // Invalidates iterators. Returns iterator following the last removed element. - iterator erase(const iterator& position) { - if (size_ >= 0) { - int i = position.array_iter_ - array_; - array_[i].~value_type(); - --size_; - if (i != size_) { - new (&array_[i]) value_type(std::move(array_[size_])); - array_[size_].~value_type(); - return iterator(array_ + i); - } - return end(); - } - return iterator(map_.erase(position.hash_iter_)); - } - - size_t erase(const key_type& key) { - iterator iter = find(key); - if (iter == end()) return 0u; - erase(iter); - return 1u; - } - - size_t count(const key_type& key) const { - return (find(key) == end()) ? 0 : 1; - } - - size_t size() const { - if (size_ >= 0) { - return static_cast<size_t>(size_); - } else { - return map_.size(); - } - } - - bool empty() const { - if (size_ >= 0) { - return (size_ == 0); - } else { - return map_.empty(); - } - } - - // Returns true if we have fallen back to using the underlying map - // representation. - bool UsingFullMap() const { - return size_ < 0; - } - - inline NormalMap* map() { - CHECK(UsingFullMap()); - return &map_; - } - inline const NormalMap* map() const { - CHECK(UsingFullMap()); - return &map_; - } - - private: - int size_; // negative = using hash_map - - MapInit functor_; - - // We want to call constructors and destructors manually, but we don't want to - // allocate and deallocate the memory used for them separately. Since array_ - // and map_ are mutually exclusive, we'll put them in a union. - union { - value_type array_[kArraySize]; - NormalMap map_; - }; - - void ConvertToRealMap() { - // Storage for the elements in the temporary array. This is intentionally - // declared as a union to avoid having to default-construct |kArraySize| - // elements, only to move construct over them in the initial loop. - union Storage { - Storage() {} - ~Storage() {} - value_type array[kArraySize]; - } temp; - - // Move the current elements into a temporary array. - for (int i = 0; i < kArraySize; i++) { - new (&temp.array[i]) value_type(std::move(array_[i])); - array_[i].~value_type(); - } - - // Initialize the map. - size_ = -1; - functor_(&map_); - - // Insert elements into it. - for (int i = 0; i < kArraySize; i++) { - map_.insert(std::move(temp.array[i])); - temp.array[i].~value_type(); - } - } - - // Helpers for constructors and destructors. - void InitFrom(const small_map& src) { - functor_ = src.functor_; - size_ = src.size_; - if (src.size_ >= 0) { - for (int i = 0; i < size_; i++) { - new (&array_[i]) value_type(src.array_[i]); - } - } else { - functor_(&map_); - map_ = src.map_; - } - } - void Destroy() { - if (size_ >= 0) { - for (int i = 0; i < size_; i++) { - array_[i].~value_type(); - } - } else { - map_.~NormalMap(); - } - } -}; - -template <typename NormalMap, - int kArraySize, - typename EqualKey, - typename Functor> -inline bool small_map<NormalMap, kArraySize, EqualKey, Functor>::iterator:: -operator==(const const_iterator& other) const { - return other == *this; -} -template <typename NormalMap, - int kArraySize, - typename EqualKey, - typename Functor> -inline bool small_map<NormalMap, kArraySize, EqualKey, Functor>::iterator:: -operator!=(const const_iterator& other) const { - return other != *this; -} - -} // namespace base - -#endif // BASE_CONTAINERS_SMALL_MAP_H_
diff --git a/base/containers/stack_container.h b/base/containers/stack_container.h deleted file mode 100644 index 7d84d07..0000000 --- a/base/containers/stack_container.h +++ /dev/null
@@ -1,229 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_CONTAINERS_STACK_CONTAINER_H_ -#define BASE_CONTAINERS_STACK_CONTAINER_H_ - -#include <stddef.h> - -#include <vector> - -#include "base/macros.h" -#include "build_config.h" - -namespace base { - -// This allocator can be used with STL containers to provide a stack buffer -// from which to allocate memory and overflows onto the heap. This stack buffer -// would be allocated on the stack and allows us to avoid heap operations in -// some situations. -// -// STL likes to make copies of allocators, so the allocator itself can't hold -// the data. Instead, we make the creator responsible for creating a -// StackAllocator::Source which contains the data. Copying the allocator -// merely copies the pointer to this shared source, so all allocators created -// based on our allocator will share the same stack buffer. -// -// This stack buffer implementation is very simple. The first allocation that -// fits in the stack buffer will use the stack buffer. Any subsequent -// allocations will not use the stack buffer, even if there is unused room. -// This makes it appropriate for array-like containers, but the caller should -// be sure to reserve() in the container up to the stack buffer size. Otherwise -// the container will allocate a small array which will "use up" the stack -// buffer. -template<typename T, size_t stack_capacity> -class StackAllocator : public std::allocator<T> { - public: - typedef typename std::allocator<T>::pointer pointer; - typedef typename std::allocator<T>::size_type size_type; - - // Backing store for the allocator. The container owner is responsible for - // maintaining this for as long as any containers using this allocator are - // live. - struct Source { - Source() : used_stack_buffer_(false) { - } - - // Casts the buffer in its right type. - T* stack_buffer() { return reinterpret_cast<T*>(stack_buffer_); } - const T* stack_buffer() const { - return reinterpret_cast<const T*>(&stack_buffer_); - } - - // The buffer itself. It is not of type T because we don't want the - // constructors and destructors to be automatically called. Define a POD - // buffer of the right size instead. - alignas(T) char stack_buffer_[sizeof(T[stack_capacity])]; -#if defined(__GNUC__) && !defined(ARCH_CPU_X86_FAMILY) - static_assert(alignof(T) <= 16, "http://crbug.com/115612"); -#endif - - // Set when the stack buffer is used for an allocation. We do not track - // how much of the buffer is used, only that somebody is using it. - bool used_stack_buffer_; - }; - - // Used by containers when they want to refer to an allocator of type U. - template<typename U> - struct rebind { - typedef StackAllocator<U, stack_capacity> other; - }; - - // For the straight up copy c-tor, we can share storage. - StackAllocator(const StackAllocator<T, stack_capacity>& rhs) - : std::allocator<T>(), source_(rhs.source_) { - } - - // ISO C++ requires the following constructor to be defined, - // and std::vector in VC++2008SP1 Release fails with an error - // in the class _Container_base_aux_alloc_real (from <xutility>) - // if the constructor does not exist. - // For this constructor, we cannot share storage; there's - // no guarantee that the Source buffer of Ts is large enough - // for Us. - // TODO: If we were fancy pants, perhaps we could share storage - // iff sizeof(T) == sizeof(U). - template<typename U, size_t other_capacity> - StackAllocator(const StackAllocator<U, other_capacity>& other) - : source_(NULL) { - } - - // This constructor must exist. It creates a default allocator that doesn't - // actually have a stack buffer. glibc's std::string() will compare the - // current allocator against the default-constructed allocator, so this - // should be fast. - StackAllocator() : source_(NULL) { - } - - explicit StackAllocator(Source* source) : source_(source) { - } - - // Actually do the allocation. Use the stack buffer if nobody has used it yet - // and the size requested fits. Otherwise, fall through to the standard - // allocator. - pointer allocate(size_type n, void* hint = 0) { - if (source_ != NULL && !source_->used_stack_buffer_ - && n <= stack_capacity) { - source_->used_stack_buffer_ = true; - return source_->stack_buffer(); - } else { - return std::allocator<T>::allocate(n, hint); - } - } - - // Free: when trying to free the stack buffer, just mark it as free. For - // non-stack-buffer pointers, just fall though to the standard allocator. - void deallocate(pointer p, size_type n) { - if (source_ != NULL && p == source_->stack_buffer()) - source_->used_stack_buffer_ = false; - else - std::allocator<T>::deallocate(p, n); - } - - private: - Source* source_; -}; - -// A wrapper around STL containers that maintains a stack-sized buffer that the -// initial capacity of the vector is based on. Growing the container beyond the -// stack capacity will transparently overflow onto the heap. The container must -// support reserve(). -// -// This will not work with std::string since some implementations allocate -// more bytes than requested in calls to reserve(), forcing the allocation onto -// the heap. http://crbug.com/709273 -// -// WATCH OUT: the ContainerType MUST use the proper StackAllocator for this -// type. This object is really intended to be used only internally. You'll want -// to use the wrappers below for different types. -template<typename TContainerType, int stack_capacity> -class StackContainer { - public: - typedef TContainerType ContainerType; - typedef typename ContainerType::value_type ContainedType; - typedef StackAllocator<ContainedType, stack_capacity> Allocator; - - // Allocator must be constructed before the container! - StackContainer() : allocator_(&stack_data_), container_(allocator_) { - // Make the container use the stack allocation by reserving our buffer size - // before doing anything else. - container_.reserve(stack_capacity); - } - - // Getters for the actual container. - // - // Danger: any copies of this made using the copy constructor must have - // shorter lifetimes than the source. The copy will share the same allocator - // and therefore the same stack buffer as the original. Use std::copy to - // copy into a "real" container for longer-lived objects. - ContainerType& container() { return container_; } - const ContainerType& container() const { return container_; } - - // Support operator-> to get to the container. This allows nicer syntax like: - // StackContainer<...> foo; - // std::sort(foo->begin(), foo->end()); - ContainerType* operator->() { return &container_; } - const ContainerType* operator->() const { return &container_; } - -#ifdef UNIT_TEST - // Retrieves the stack source so that that unit tests can verify that the - // buffer is being used properly. - const typename Allocator::Source& stack_data() const { - return stack_data_; - } -#endif - - protected: - typename Allocator::Source stack_data_; - Allocator allocator_; - ContainerType container_; - - private: - DISALLOW_COPY_AND_ASSIGN(StackContainer); -}; - -// StackVector ----------------------------------------------------------------- - -// Example: -// StackVector<int, 16> foo; -// foo->push_back(22); // we have overloaded operator-> -// foo[0] = 10; // as well as operator[] -template<typename T, size_t stack_capacity> -class StackVector : public StackContainer< - std::vector<T, StackAllocator<T, stack_capacity> >, - stack_capacity> { - public: - StackVector() : StackContainer< - std::vector<T, StackAllocator<T, stack_capacity> >, - stack_capacity>() { - } - - // We need to put this in STL containers sometimes, which requires a copy - // constructor. We can't call the regular copy constructor because that will - // take the stack buffer from the original. Here, we create an empty object - // and make a stack buffer of its own. - StackVector(const StackVector<T, stack_capacity>& other) - : StackContainer< - std::vector<T, StackAllocator<T, stack_capacity> >, - stack_capacity>() { - this->container().assign(other->begin(), other->end()); - } - - StackVector<T, stack_capacity>& operator=( - const StackVector<T, stack_capacity>& other) { - this->container().assign(other->begin(), other->end()); - return *this; - } - - // Vectors are commonly indexed, which isn't very convenient even with - // operator-> (using "->at()" does exception stuff we don't want). - T& operator[](size_t i) { return this->container().operator[](i); } - const T& operator[](size_t i) const { - return this->container().operator[](i); - } -}; - -} // namespace base - -#endif // BASE_CONTAINERS_STACK_CONTAINER_H_
diff --git a/base/containers/unique_ptr_adapters.h b/base/containers/unique_ptr_adapters.h deleted file mode 100644 index 42fab19..0000000 --- a/base/containers/unique_ptr_adapters.h +++ /dev/null
@@ -1,78 +0,0 @@ -// Copyright 2017 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_CONTAINERS_UNIQUE_PTR_ADAPTERS_H_ -#define BASE_CONTAINERS_UNIQUE_PTR_ADAPTERS_H_ - -#include <memory> - -namespace base { - -// This transparent comparator allows to lookup by raw pointer in -// a container of unique pointers. This functionality is based on C++14 -// extensions to std::set/std::map interface, and can also be used -// with base::flat_set/base::flat_map. -// -// Example usage: -// Foo* foo = ... -// std::set<std::unique_ptr<Foo>, base::UniquePtrComparator> set; -// set.insert(std::unique_ptr<Foo>(foo)); -// ... -// auto it = set.find(foo); -// EXPECT_EQ(foo, it->get()); -// -// You can find more information about transparent comparisons here: -// http://en.cppreference.com/w/cpp/utility/functional/less_void -struct UniquePtrComparator { - using is_transparent = int; - - template <typename T> - bool operator()(const std::unique_ptr<T>& lhs, - const std::unique_ptr<T>& rhs) const { - return lhs < rhs; - } - - template <typename T> - bool operator()(const T* lhs, const std::unique_ptr<T>& rhs) const { - return lhs < rhs.get(); - } - - template <typename T> - bool operator()(const std::unique_ptr<T>& lhs, const T* rhs) const { - return lhs.get() < rhs; - } -}; - -// UniquePtrMatcher is useful for finding an element in a container of -// unique_ptrs when you have the raw pointer. -// -// Example usage: -// std::vector<std::unique_ptr<Foo>> vector; -// Foo* element = ... -// auto iter = std::find_if(vector.begin(), vector.end(), -// MatchesUniquePtr(element)); -// -// Example of erasing from container: -// EraseIf(v, MatchesUniquePtr(element)); -// -template <class T, class Deleter = std::default_delete<T>> -struct UniquePtrMatcher { - explicit UniquePtrMatcher(T* t) : t_(t) {} - - bool operator()(const std::unique_ptr<T, Deleter>& o) { - return o.get() == t_; - } - - private: - T* const t_; -}; - -template <class T, class Deleter = std::default_delete<T>> -UniquePtrMatcher<T, Deleter> MatchesUniquePtr(T* t) { - return UniquePtrMatcher<T, Deleter>(t); -} - -} // namespace base - -#endif // BASE_CONTAINERS_UNIQUE_PTR_ADAPTERS_H_
diff --git a/base/cpu.cc b/base/cpu.cc deleted file mode 100644 index 68a6bbc..0000000 --- a/base/cpu.cc +++ /dev/null
@@ -1,242 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/cpu.h" - -#include <limits.h> -#include <stddef.h> -#include <stdint.h> -#include <string.h> - -#include <algorithm> -#include <utility> - -#include "base/macros.h" -#include "build_config.h" - -#if defined(ARCH_CPU_ARM_FAMILY) && (defined(OS_ANDROID) || defined(OS_LINUX)) -#include "base/files/file_util.h" -#endif - -#if defined(ARCH_CPU_X86_FAMILY) -#if defined(COMPILER_MSVC) -#include <intrin.h> -#include <immintrin.h> // For _xgetbv() -#endif -#endif - -namespace base { - -CPU::CPU() - : signature_(0), - type_(0), - family_(0), - model_(0), - stepping_(0), - ext_model_(0), - ext_family_(0), - has_mmx_(false), - has_sse_(false), - has_sse2_(false), - has_sse3_(false), - has_ssse3_(false), - has_sse41_(false), - has_sse42_(false), - has_popcnt_(false), - has_avx_(false), - has_avx2_(false), - has_aesni_(false), - has_non_stop_time_stamp_counter_(false), - cpu_vendor_("unknown") { - Initialize(); -} - -namespace { - -#if defined(ARCH_CPU_X86_FAMILY) -#if !defined(COMPILER_MSVC) - -#if defined(__pic__) && defined(__i386__) - -void __cpuid(int cpu_info[4], int info_type) { - __asm__ volatile( - "mov %%ebx, %%edi\n" - "cpuid\n" - "xchg %%edi, %%ebx\n" - : "=a"(cpu_info[0]), "=D"(cpu_info[1]), "=c"(cpu_info[2]), - "=d"(cpu_info[3]) - : "a"(info_type), "c"(0)); -} - -#else - -void __cpuid(int cpu_info[4], int info_type) { - __asm__ volatile("cpuid\n" - : "=a"(cpu_info[0]), "=b"(cpu_info[1]), "=c"(cpu_info[2]), - "=d"(cpu_info[3]) - : "a"(info_type), "c"(0)); -} - -#endif - -// _xgetbv returns the value of an Intel Extended Control Register (XCR). -// Currently only XCR0 is defined by Intel so |xcr| should always be zero. -uint64_t _xgetbv(uint32_t xcr) { - uint32_t eax, edx; - - __asm__ volatile ( - "xgetbv" : "=a"(eax), "=d"(edx) : "c"(xcr)); - return (static_cast<uint64_t>(edx) << 32) | eax; -} - -#endif // !defined(COMPILER_MSVC) -#endif // ARCH_CPU_X86_FAMILY - -#if defined(ARCH_CPU_ARM_FAMILY) && (defined(OS_ANDROID) || defined(OS_LINUX)) -std::string* CpuInfoBrand() { - static std::string* brand = []() { - // This function finds the value from /proc/cpuinfo under the key "model - // name" or "Processor". "model name" is used in Linux 3.8 and later (3.7 - // and later for arm64) and is shown once per CPU. "Processor" is used in - // earler versions and is shown only once at the top of /proc/cpuinfo - // regardless of the number CPUs. - const char kModelNamePrefix[] = "model name\t: "; - const char kProcessorPrefix[] = "Processor\t: "; - - std::string contents; - ReadFileToString(FilePath("/proc/cpuinfo"), &contents); - DCHECK(!contents.empty()); - - std::istringstream iss(contents); - std::string line; - while (std::getline(iss, line)) { - if (line.compare(0, strlen(kModelNamePrefix), kModelNamePrefix) == 0) - return new std::string(line.substr(strlen(kModelNamePrefix))); - if (line.compare(0, strlen(kProcessorPrefix), kProcessorPrefix) == 0) - return new std::string(line.substr(strlen(kProcessorPrefix))); - } - - return new std::string(); - }(); - - return brand; -} -#endif // defined(ARCH_CPU_ARM_FAMILY) && (defined(OS_ANDROID) || - // defined(OS_LINUX)) - -} // namespace - -void CPU::Initialize() { -#if defined(ARCH_CPU_X86_FAMILY) - int cpu_info[4] = {-1}; - // This array is used to temporarily hold the vendor name and then the brand - // name. Thus it has to be big enough for both use cases. There are - // static_asserts below for each of the use cases to make sure this array is - // big enough. - char cpu_string[sizeof(cpu_info) * 3 + 1]; - - // __cpuid with an InfoType argument of 0 returns the number of - // valid Ids in CPUInfo[0] and the CPU identification string in - // the other three array elements. The CPU identification string is - // not in linear order. The code below arranges the information - // in a human readable form. The human readable order is CPUInfo[1] | - // CPUInfo[3] | CPUInfo[2]. CPUInfo[2] and CPUInfo[3] are swapped - // before using memcpy() to copy these three array elements to |cpu_string|. - __cpuid(cpu_info, 0); - int num_ids = cpu_info[0]; - std::swap(cpu_info[2], cpu_info[3]); - static constexpr size_t kVendorNameSize = 3 * sizeof(cpu_info[1]); - static_assert(kVendorNameSize < arraysize(cpu_string), - "cpu_string too small"); - memcpy(cpu_string, &cpu_info[1], kVendorNameSize); - cpu_string[kVendorNameSize] = '\0'; - cpu_vendor_ = cpu_string; - - // Interpret CPU feature information. - if (num_ids > 0) { - int cpu_info7[4] = {0}; - __cpuid(cpu_info, 1); - if (num_ids >= 7) { - __cpuid(cpu_info7, 7); - } - signature_ = cpu_info[0]; - stepping_ = cpu_info[0] & 0xf; - model_ = ((cpu_info[0] >> 4) & 0xf) + ((cpu_info[0] >> 12) & 0xf0); - family_ = (cpu_info[0] >> 8) & 0xf; - type_ = (cpu_info[0] >> 12) & 0x3; - ext_model_ = (cpu_info[0] >> 16) & 0xf; - ext_family_ = (cpu_info[0] >> 20) & 0xff; - has_mmx_ = (cpu_info[3] & 0x00800000) != 0; - has_sse_ = (cpu_info[3] & 0x02000000) != 0; - has_sse2_ = (cpu_info[3] & 0x04000000) != 0; - has_sse3_ = (cpu_info[2] & 0x00000001) != 0; - has_ssse3_ = (cpu_info[2] & 0x00000200) != 0; - has_sse41_ = (cpu_info[2] & 0x00080000) != 0; - has_sse42_ = (cpu_info[2] & 0x00100000) != 0; - has_popcnt_ = (cpu_info[2] & 0x00800000) != 0; - - // AVX instructions will generate an illegal instruction exception unless - // a) they are supported by the CPU, - // b) XSAVE is supported by the CPU and - // c) XSAVE is enabled by the kernel. - // See http://software.intel.com/en-us/blogs/2011/04/14/is-avx-enabled - // - // In addition, we have observed some crashes with the xgetbv instruction - // even after following Intel's example code. (See crbug.com/375968.) - // Because of that, we also test the XSAVE bit because its description in - // the CPUID documentation suggests that it signals xgetbv support. - has_avx_ = - (cpu_info[2] & 0x10000000) != 0 && - (cpu_info[2] & 0x04000000) != 0 /* XSAVE */ && - (cpu_info[2] & 0x08000000) != 0 /* OSXSAVE */ && - (_xgetbv(0) & 6) == 6 /* XSAVE enabled by kernel */; - has_aesni_ = (cpu_info[2] & 0x02000000) != 0; - has_avx2_ = has_avx_ && (cpu_info7[1] & 0x00000020) != 0; - } - - // Get the brand string of the cpu. - __cpuid(cpu_info, 0x80000000); - const int max_parameter = cpu_info[0]; - - static constexpr int kParameterStart = 0x80000002; - static constexpr int kParameterEnd = 0x80000004; - static constexpr int kParameterSize = kParameterEnd - kParameterStart + 1; - static_assert(kParameterSize * sizeof(cpu_info) + 1 == arraysize(cpu_string), - "cpu_string has wrong size"); - - if (max_parameter >= kParameterEnd) { - size_t i = 0; - for (int parameter = kParameterStart; parameter <= kParameterEnd; - ++parameter) { - __cpuid(cpu_info, parameter); - memcpy(&cpu_string[i], cpu_info, sizeof(cpu_info)); - i += sizeof(cpu_info); - } - cpu_string[i] = '\0'; - cpu_brand_ = cpu_string; - } - - static constexpr int kParameterContainingNonStopTimeStampCounter = 0x80000007; - if (max_parameter >= kParameterContainingNonStopTimeStampCounter) { - __cpuid(cpu_info, kParameterContainingNonStopTimeStampCounter); - has_non_stop_time_stamp_counter_ = (cpu_info[3] & (1 << 8)) != 0; - } -#elif defined(ARCH_CPU_ARM_FAMILY) && (defined(OS_ANDROID) || defined(OS_LINUX)) - cpu_brand_ = *CpuInfoBrand(); -#endif -} - -CPU::IntelMicroArchitecture CPU::GetIntelMicroArchitecture() const { - if (has_avx2()) return AVX2; - if (has_avx()) return AVX; - if (has_sse42()) return SSE42; - if (has_sse41()) return SSE41; - if (has_ssse3()) return SSSE3; - if (has_sse3()) return SSE3; - if (has_sse2()) return SSE2; - if (has_sse()) return SSE; - return PENTIUM; -} - -} // namespace base
diff --git a/base/cpu.h b/base/cpu.h deleted file mode 100644 index 2c6caea..0000000 --- a/base/cpu.h +++ /dev/null
@@ -1,88 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_CPU_H_ -#define BASE_CPU_H_ - -#include <string> - -#include "base/base_export.h" - -namespace base { - -// Query information about the processor. -class BASE_EXPORT CPU final { - public: - CPU(); - - enum IntelMicroArchitecture { - PENTIUM, - SSE, - SSE2, - SSE3, - SSSE3, - SSE41, - SSE42, - AVX, - AVX2, - MAX_INTEL_MICRO_ARCHITECTURE - }; - - // Accessors for CPU information. - const std::string& vendor_name() const { return cpu_vendor_; } - int signature() const { return signature_; } - int stepping() const { return stepping_; } - int model() const { return model_; } - int family() const { return family_; } - int type() const { return type_; } - int extended_model() const { return ext_model_; } - int extended_family() const { return ext_family_; } - bool has_mmx() const { return has_mmx_; } - bool has_sse() const { return has_sse_; } - bool has_sse2() const { return has_sse2_; } - bool has_sse3() const { return has_sse3_; } - bool has_ssse3() const { return has_ssse3_; } - bool has_sse41() const { return has_sse41_; } - bool has_sse42() const { return has_sse42_; } - bool has_popcnt() const { return has_popcnt_; } - bool has_avx() const { return has_avx_; } - bool has_avx2() const { return has_avx2_; } - bool has_aesni() const { return has_aesni_; } - bool has_non_stop_time_stamp_counter() const { - return has_non_stop_time_stamp_counter_; - } - - IntelMicroArchitecture GetIntelMicroArchitecture() const; - const std::string& cpu_brand() const { return cpu_brand_; } - - private: - // Query the processor for CPUID information. - void Initialize(); - - int signature_; // raw form of type, family, model, and stepping - int type_; // process type - int family_; // family of the processor - int model_; // model of processor - int stepping_; // processor revision number - int ext_model_; - int ext_family_; - bool has_mmx_; - bool has_sse_; - bool has_sse2_; - bool has_sse3_; - bool has_ssse3_; - bool has_sse41_; - bool has_sse42_; - bool has_popcnt_; - bool has_avx_; - bool has_avx2_; - bool has_aesni_; - bool has_non_stop_time_stamp_counter_; - std::string cpu_vendor_; - std::string cpu_brand_; -}; - -} // namespace base - -#endif // BASE_CPU_H_
diff --git a/base/file_descriptor_posix.h b/base/file_descriptor_posix.h deleted file mode 100644 index 2a36611..0000000 --- a/base/file_descriptor_posix.h +++ /dev/null
@@ -1,59 +0,0 @@ -// Copyright (c) 2006-2009 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_FILE_DESCRIPTOR_POSIX_H_ -#define BASE_FILE_DESCRIPTOR_POSIX_H_ - -#include "base/files/file.h" -#include "base/files/scoped_file.h" - -namespace base { - -// ----------------------------------------------------------------------------- -// We introduct a special structure for file descriptors in order that we are -// able to use template specialisation to special-case their handling. -// -// IMPORTANT: This is primarily intended for use when sending file descriptors -// over IPC. Even if |auto_close| is true, base::FileDescriptor does NOT close() -// |fd| when going out of scope. Instead, a consumer of a base::FileDescriptor -// must invoke close() on |fd| if |auto_close| is true. -// -// In the case of IPC, the the IPC subsystem knows to close() |fd| after sending -// a message that contains a base::FileDescriptor if auto_close == true. On the -// other end, the receiver must make sure to close() |fd| after it has finished -// processing the IPC message. See the IPC::ParamTraits<> specialization in -// ipc/ipc_message_utils.h for all the details. -// ----------------------------------------------------------------------------- -struct FileDescriptor { - FileDescriptor() : fd(-1), auto_close(false) {} - - FileDescriptor(int ifd, bool iauto_close) : fd(ifd), auto_close(iauto_close) { - } - - FileDescriptor(File file) : fd(file.TakePlatformFile()), auto_close(true) {} - explicit FileDescriptor(ScopedFD fd) : fd(fd.release()), auto_close(true) {} - - bool operator==(const FileDescriptor& other) const { - return (fd == other.fd && auto_close == other.auto_close); - } - - bool operator!=(const FileDescriptor& other) const { - return !operator==(other); - } - - // A comparison operator so that we can use these as keys in a std::map. - bool operator<(const FileDescriptor& other) const { - return other.fd < fd; - } - - int fd; - // If true, this file descriptor should be closed after it has been used. For - // example an IPC system might interpret this flag as indicating that the - // file descriptor it has been given should be closed after use. - bool auto_close; -}; - -} // namespace base - -#endif // BASE_FILE_DESCRIPTOR_POSIX_H_
diff --git a/base/file_descriptor_store.cc b/base/file_descriptor_store.cc deleted file mode 100644 index 71cf2b3..0000000 --- a/base/file_descriptor_store.cc +++ /dev/null
@@ -1,73 +0,0 @@ -// Copyright 2017 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/file_descriptor_store.h" - -#include <utility> - -#include "base/logging.h" - -namespace base { - -FileDescriptorStore::Descriptor::Descriptor(const std::string& key, - base::ScopedFD fd) - : key(key), - fd(std::move(fd)), - region(base::MemoryMappedFile::Region::kWholeFile) {} - -FileDescriptorStore::Descriptor::Descriptor( - const std::string& key, - base::ScopedFD fd, - base::MemoryMappedFile::Region region) - : key(key), fd(std::move(fd)), region(region) {} - -FileDescriptorStore::Descriptor::Descriptor( - FileDescriptorStore::Descriptor&& other) - : key(other.key), fd(std::move(other.fd)), region(other.region) {} - -FileDescriptorStore::Descriptor::~Descriptor() = default; - -// static -FileDescriptorStore& FileDescriptorStore::GetInstance() { - static FileDescriptorStore* store = new FileDescriptorStore; - return *store; -} - -base::ScopedFD FileDescriptorStore::TakeFD( - const std::string& key, - base::MemoryMappedFile::Region* region) { - base::ScopedFD fd = MaybeTakeFD(key, region); - if (!fd.is_valid()) - DLOG(DCHECK) << "Unknown global descriptor: " << key; - return fd; -} - -base::ScopedFD FileDescriptorStore::MaybeTakeFD( - const std::string& key, - base::MemoryMappedFile::Region* region) { - auto iter = descriptors_.find(key); - if (iter == descriptors_.end()) - return base::ScopedFD(); - *region = iter->second.region; - base::ScopedFD result = std::move(iter->second.fd); - descriptors_.erase(iter); - return result; -} - -void FileDescriptorStore::Set(const std::string& key, base::ScopedFD fd) { - Set(key, std::move(fd), base::MemoryMappedFile::Region::kWholeFile); -} - -void FileDescriptorStore::Set(const std::string& key, - base::ScopedFD fd, - base::MemoryMappedFile::Region region) { - Descriptor descriptor(key, std::move(fd), region); - descriptors_.insert(std::make_pair(key, std::move(descriptor))); -} - -FileDescriptorStore::FileDescriptorStore() = default; - -FileDescriptorStore::~FileDescriptorStore() = default; - -} // namespace base
diff --git a/base/file_descriptor_store.h b/base/file_descriptor_store.h deleted file mode 100644 index b6bd079..0000000 --- a/base/file_descriptor_store.h +++ /dev/null
@@ -1,73 +0,0 @@ -// Copyright 2017 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_FILE_DESCRIPTOR_STORE_H_ -#define BASE_FILE_DESCRIPTOR_STORE_H_ - -#include <map> -#include <string> - -#include "base/files/memory_mapped_file.h" -#include "base/files/scoped_file.h" -#include "base/macros.h" - -namespace base { - -// The file descriptor store is used to associate file descriptors with keys -// that must be unique. -// It is used to share file descriptors from a process to its child. -class BASE_EXPORT FileDescriptorStore { - public: - struct Descriptor { - Descriptor(const std::string& key, base::ScopedFD fd); - Descriptor(const std::string& key, - base::ScopedFD fd, - base::MemoryMappedFile::Region region); - Descriptor(Descriptor&& other); - ~Descriptor(); - - Descriptor& operator=(Descriptor&& other) = default; - - // Globally unique key. - std::string key; - // Actual FD. - base::ScopedFD fd; - // Optional region, defaults to kWholeFile. - base::MemoryMappedFile::Region region; - }; - using Mapping = std::map<std::string, Descriptor>; - - // Returns the singleton instance of FileDescriptorStore. - static FileDescriptorStore& GetInstance(); - - // Gets a descriptor given a key and also populates |region|. - // It is a fatal error if the key is not known. - base::ScopedFD TakeFD(const std::string& key, - base::MemoryMappedFile::Region* region); - - // Gets a descriptor given a key. Returns an empty ScopedFD on error. - base::ScopedFD MaybeTakeFD(const std::string& key, - base::MemoryMappedFile::Region* region); - - // Sets the descriptor for the given |key|. This sets the region associated - // with |key| to kWholeFile. - void Set(const std::string& key, base::ScopedFD fd); - - // Sets the descriptor and |region| for the given |key|. - void Set(const std::string& key, - base::ScopedFD fd, - base::MemoryMappedFile::Region region); - - private: - FileDescriptorStore(); - ~FileDescriptorStore(); - - Mapping descriptors_; - - DISALLOW_COPY_AND_ASSIGN(FileDescriptorStore); -}; - -} // namespace base - -#endif // BASE_FILE_DESCRIPTOR_STORE_H_
diff --git a/base/files/file_util.h b/base/files/file_util.h index 9c7c748..d95410a 100644 --- a/base/files/file_util.h +++ b/base/files/file_util.h
@@ -30,7 +30,6 @@ #if defined(OS_WIN) #include "base/win/windows_types.h" #elif defined(OS_POSIX) || defined(OS_FUCHSIA) -#include "base/file_descriptor_posix.h" #include "base/logging.h" #include "base/posix/eintr_wrapper.h" #endif
diff --git a/base/files/file_util_win.cc b/base/files/file_util_win.cc index c1a5ced..d59b7e4 100644 --- a/base/files/file_util_win.cc +++ b/base/files/file_util_win.cc
@@ -23,7 +23,6 @@ #include "base/logging.h" #include "base/macros.h" #include "base/process/process_handle.h" -#include "base/rand_util.h" #include "base/strings/string_number_conversions.h" #include "base/strings/string_piece.h" #include "base/strings/string_util.h" @@ -33,6 +32,13 @@ #include "base/win/scoped_handle.h" #include "base/win/windows_version.h" +// #define needed to link in RtlGenRandom(), a.k.a. SystemFunction036. See the +// "Community Additions" comment on MSDN here: +// http://msdn.microsoft.com/en-us/library/windows/desktop/aa387694.aspx +#define SystemFunction036 NTAPI SystemFunction036 +#include <NTSecAPI.h> +#undef SystemFunction036 + namespace base { namespace { @@ -258,11 +264,24 @@ bytes[1] & 0x0000ffff'ffffffffULL); } +void RandBytes(void* output, size_t output_length) { + char* output_ptr = static_cast<char*>(output); + while (output_length > 0) { + const ULONG output_bytes_this_pass = static_cast<ULONG>(std::min( + output_length, static_cast<size_t>(std::numeric_limits<ULONG>::max()))); + const bool success = + RtlGenRandom(output_ptr, output_bytes_this_pass) != FALSE; + CHECK(success); + output_length -= output_bytes_this_pass; + output_ptr += output_bytes_this_pass; + } +} + std::string GenerateGUID() { uint64_t sixteen_bytes[2]; // Use base::RandBytes instead of crypto::RandBytes, because crypto calls the // base version directly, and to prevent the dependency from base/ to crypto/. - base::RandBytes(&sixteen_bytes, sizeof(sixteen_bytes)); + RandBytes(&sixteen_bytes, sizeof(sixteen_bytes)); // Set the GUID to version 4 as described in RFC 4122, section 4.4. // The format of GUID version 4 must be xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx, @@ -488,8 +507,7 @@ new_dir_name.assign(prefix); new_dir_name.append(IntToString16(GetCurrentProcId())); new_dir_name.push_back('_'); - new_dir_name.append( - IntToString16(RandInt(0, std::numeric_limits<int16_t>::max()))); + new_dir_name.append(UTF8ToUTF16(GenerateGUID())); path_to_create = base_dir.Append(new_dir_name); if (::CreateDirectory(path_to_create.value().c_str(), NULL)) {
diff --git a/base/format_macros.h b/base/format_macros.h deleted file mode 100644 index 46cd12c..0000000 --- a/base/format_macros.h +++ /dev/null
@@ -1,97 +0,0 @@ -// Copyright (c) 2009 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_FORMAT_MACROS_H_ -#define BASE_FORMAT_MACROS_H_ - -// This file defines the format macros for some integer types. - -// To print a 64-bit value in a portable way: -// int64_t value; -// printf("xyz:%" PRId64, value); -// The "d" in the macro corresponds to %d; you can also use PRIu64 etc. -// -// For wide strings, prepend "Wide" to the macro: -// int64_t value; -// StringPrintf(L"xyz: %" WidePRId64, value); -// -// To print a size_t value in a portable way: -// size_t size; -// printf("xyz: %" PRIuS, size); -// The "u" in the macro corresponds to %u, and S is for "size". - -#include <stddef.h> -#include <stdint.h> - -#include "build_config.h" - -#if (defined(OS_POSIX) || defined(OS_FUCHSIA)) && \ - (defined(_INTTYPES_H) || defined(_INTTYPES_H_)) && !defined(PRId64) -#error "inttypes.h has already been included before this header file, but " -#error "without __STDC_FORMAT_MACROS defined." -#endif - -#if (defined(OS_POSIX) || defined(OS_FUCHSIA)) && !defined(__STDC_FORMAT_MACROS) -#define __STDC_FORMAT_MACROS -#endif - -#include <inttypes.h> - -#if defined(OS_WIN) - -#if !defined(PRId64) || !defined(PRIu64) || !defined(PRIx64) -#error "inttypes.h provided by win toolchain should define these." -#endif - -#define WidePRId64 L"I64d" -#define WidePRIu64 L"I64u" -#define WidePRIx64 L"I64x" - -#if !defined(PRIuS) -#define PRIuS "Iu" -#endif - -#elif defined(OS_POSIX) || defined(OS_FUCHSIA) - -// GCC will concatenate wide and narrow strings correctly, so nothing needs to -// be done here. -#define WidePRId64 PRId64 -#define WidePRIu64 PRIu64 -#define WidePRIx64 PRIx64 - -#if !defined(PRIuS) -#define PRIuS "zu" -#endif - -#endif // defined(OS_WIN) - -// The size of NSInteger and NSUInteger varies between 32-bit and 64-bit -// architectures and Apple does not provides standard format macros and -// recommends casting. This has many drawbacks, so instead define macros -// for formatting those types. -#if defined(OS_MACOSX) -#if defined(ARCH_CPU_64_BITS) -#if !defined(PRIdNS) -#define PRIdNS "ld" -#endif -#if !defined(PRIuNS) -#define PRIuNS "lu" -#endif -#if !defined(PRIxNS) -#define PRIxNS "lx" -#endif -#else // defined(ARCH_CPU_64_BITS) -#if !defined(PRIdNS) -#define PRIdNS "d" -#endif -#if !defined(PRIuNS) -#define PRIuNS "u" -#endif -#if !defined(PRIxNS) -#define PRIxNS "x" -#endif -#endif -#endif // defined(OS_MACOSX) - -#endif // BASE_FORMAT_MACROS_H_
diff --git a/base/hash.cc b/base/hash.cc deleted file mode 100644 index ab5cebc..0000000 --- a/base/hash.cc +++ /dev/null
@@ -1,104 +0,0 @@ -// Copyright 2014 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/hash.h" - -// Definition in base/third_party/superfasthash/superfasthash.c. (Third-party -// code did not come with its own header file, so declaring the function here.) -// Note: This algorithm is also in Blink under Source/wtf/StringHasher.h. -extern "C" uint32_t SuperFastHash(const char* data, int len); - -namespace base { - -uint32_t Hash(const void* data, size_t length) { - // Currently our in-memory hash is the same as the persistent hash. The - // split between in-memory and persistent hash functions is maintained to - // allow the in-memory hash function to be updated in the future. - return PersistentHash(data, length); -} - -uint32_t Hash(const std::string& str) { - return PersistentHash(str.data(), str.size()); -} - -uint32_t Hash(const string16& str) { - return PersistentHash(str.data(), str.size() * sizeof(char16)); -} - -uint32_t PersistentHash(const void* data, size_t length) { - // This hash function must not change, since it is designed to be persistable - // to disk. - if (length > static_cast<size_t>(std::numeric_limits<int>::max())) { - NOTREACHED(); - return 0; - } - return ::SuperFastHash(reinterpret_cast<const char*>(data), - static_cast<int>(length)); -} - -uint32_t PersistentHash(const std::string& str) { - return PersistentHash(str.data(), str.size()); -} - -// Implement hashing for pairs of at-most 32 bit integer values. -// When size_t is 32 bits, we turn the 64-bit hash code into 32 bits by using -// multiply-add hashing. This algorithm, as described in -// Theorem 4.3.3 of the thesis "Über die Komplexität der Multiplikation in -// eingeschränkten Branchingprogrammmodellen" by Woelfel, is: -// -// h32(x32, y32) = (h64(x32, y32) * rand_odd64 + rand16 * 2^16) % 2^64 / 2^32 -// -// Contact danakj@chromium.org for any questions. -size_t HashInts32(uint32_t value1, uint32_t value2) { - uint64_t value1_64 = value1; - uint64_t hash64 = (value1_64 << 32) | value2; - - if (sizeof(size_t) >= sizeof(uint64_t)) - return static_cast<size_t>(hash64); - - uint64_t odd_random = 481046412LL << 32 | 1025306955LL; - uint32_t shift_random = 10121U << 16; - - hash64 = hash64 * odd_random + shift_random; - size_t high_bits = - static_cast<size_t>(hash64 >> (8 * (sizeof(uint64_t) - sizeof(size_t)))); - return high_bits; -} - -// Implement hashing for pairs of up-to 64-bit integer values. -// We use the compound integer hash method to produce a 64-bit hash code, by -// breaking the two 64-bit inputs into 4 32-bit values: -// http://opendatastructures.org/versions/edition-0.1d/ods-java/node33.html#SECTION00832000000000000000 -// Then we reduce our result to 32 bits if required, similar to above. -size_t HashInts64(uint64_t value1, uint64_t value2) { - uint32_t short_random1 = 842304669U; - uint32_t short_random2 = 619063811U; - uint32_t short_random3 = 937041849U; - uint32_t short_random4 = 3309708029U; - - uint32_t value1a = static_cast<uint32_t>(value1 & 0xffffffff); - uint32_t value1b = static_cast<uint32_t>((value1 >> 32) & 0xffffffff); - uint32_t value2a = static_cast<uint32_t>(value2 & 0xffffffff); - uint32_t value2b = static_cast<uint32_t>((value2 >> 32) & 0xffffffff); - - uint64_t product1 = static_cast<uint64_t>(value1a) * short_random1; - uint64_t product2 = static_cast<uint64_t>(value1b) * short_random2; - uint64_t product3 = static_cast<uint64_t>(value2a) * short_random3; - uint64_t product4 = static_cast<uint64_t>(value2b) * short_random4; - - uint64_t hash64 = product1 + product2 + product3 + product4; - - if (sizeof(size_t) >= sizeof(uint64_t)) - return static_cast<size_t>(hash64); - - uint64_t odd_random = 1578233944LL << 32 | 194370989LL; - uint32_t shift_random = 20591U << 16; - - hash64 = hash64 * odd_random + shift_random; - size_t high_bits = - static_cast<size_t>(hash64 >> (8 * (sizeof(uint64_t) - sizeof(size_t)))); - return high_bits; -} - -} // namespace base
diff --git a/base/hash.h b/base/hash.h deleted file mode 100644 index 165899e..0000000 --- a/base/hash.h +++ /dev/null
@@ -1,69 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_HASH_H_ -#define BASE_HASH_H_ - -#include <stddef.h> -#include <stdint.h> - -#include <limits> -#include <string> -#include <utility> - -#include "base/base_export.h" -#include "base/logging.h" -#include "base/strings/string16.h" - -namespace base { - -// Computes a hash of a memory buffer. This hash function is subject to change -// in the future, so use only for temporary in-memory structures. If you need -// to persist a change on disk or between computers, use PersistentHash(). -// -// WARNING: This hash function should not be used for any cryptographic purpose. -BASE_EXPORT uint32_t Hash(const void* data, size_t length); -BASE_EXPORT uint32_t Hash(const std::string& str); -BASE_EXPORT uint32_t Hash(const string16& str); - -// Computes a hash of a memory buffer. This hash function must not change so -// that code can use the hashed values for persistent storage purposes or -// sending across the network. If a new persistent hash function is desired, a -// new version will have to be added in addition. -// -// WARNING: This hash function should not be used for any cryptographic purpose. -BASE_EXPORT uint32_t PersistentHash(const void* data, size_t length); -BASE_EXPORT uint32_t PersistentHash(const std::string& str); - -// Hash pairs of 32-bit or 64-bit numbers. -BASE_EXPORT size_t HashInts32(uint32_t value1, uint32_t value2); -BASE_EXPORT size_t HashInts64(uint64_t value1, uint64_t value2); - -template <typename T1, typename T2> -inline size_t HashInts(T1 value1, T2 value2) { - // This condition is expected to be compile-time evaluated and optimised away - // in release builds. - if (sizeof(T1) > sizeof(uint32_t) || (sizeof(T2) > sizeof(uint32_t))) - return HashInts64(value1, value2); - - return HashInts32(value1, value2); -} - -// A templated hasher for pairs of integer types. Example: -// -// using MyPair = std::pair<int32_t, int32_t>; -// std::unordered_set<MyPair, base::IntPairHash<MyPair>> set; -template <typename T> -struct IntPairHash; - -template <typename Type1, typename Type2> -struct IntPairHash<std::pair<Type1, Type2>> { - size_t operator()(std::pair<Type1, Type2> value) const { - return HashInts(value.first, value.second); - } -}; - -} // namespace base - -#endif // BASE_HASH_H_
diff --git a/base/json/OWNERS b/base/json/OWNERS deleted file mode 100644 index 14fce2a..0000000 --- a/base/json/OWNERS +++ /dev/null
@@ -1 +0,0 @@ -rsesek@chromium.org
diff --git a/base/json/json_correctness_fuzzer.cc b/base/json/json_correctness_fuzzer.cc deleted file mode 100644 index 1f32d8c..0000000 --- a/base/json/json_correctness_fuzzer.cc +++ /dev/null
@@ -1,63 +0,0 @@ -// Copyright 2016 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -// A fuzzer that checks correctness of json parser/writer. -// The fuzzer input is passed through parsing twice, -// so that presumably valid json is parsed/written again. - -#include <stddef.h> -#include <stdint.h> - -#include <string> - -#include "base/json/json_reader.h" -#include "base/json/json_writer.h" -#include "base/json/string_escape.h" -#include "base/logging.h" -#include "base/values.h" - -// Entry point for libFuzzer. -// We will use the last byte of data as parsing options. -// The rest will be used as text input to the parser. -extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) { - if (size < 2) - return 0; - - int error_code, error_line, error_column; - std::string error_message; - - // Create a copy of input buffer, as otherwise we don't catch - // overflow that touches the last byte (which is used in options). - std::unique_ptr<char[]> input(new char[size - 1]); - memcpy(input.get(), data, size - 1); - - base::StringPiece input_string(input.get(), size - 1); - - const int options = data[size - 1]; - auto parsed_value = base::JSONReader::ReadAndReturnError( - input_string, options, &error_code, &error_message, &error_line, - &error_column); - if (!parsed_value) - return 0; - - std::string parsed_output; - bool b = base::JSONWriter::Write(*parsed_value, &parsed_output); - LOG_ASSERT(b); - - auto double_parsed_value = base::JSONReader::ReadAndReturnError( - parsed_output, options, &error_code, &error_message, &error_line, - &error_column); - LOG_ASSERT(double_parsed_value); - std::string double_parsed_output; - bool b2 = - base::JSONWriter::Write(*double_parsed_value, &double_parsed_output); - LOG_ASSERT(b2); - - LOG_ASSERT(parsed_output == double_parsed_output) - << "Parser/Writer mismatch." - << "\nInput=" << base::GetQuotedJSONString(parsed_output) - << "\nOutput=" << base::GetQuotedJSONString(double_parsed_output); - - return 0; -}
diff --git a/base/json/json_reader_fuzzer.cc b/base/json/json_reader_fuzzer.cc deleted file mode 100644 index a8490da..0000000 --- a/base/json/json_reader_fuzzer.cc +++ /dev/null
@@ -1,29 +0,0 @@ -// Copyright 2015 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/json/json_reader.h" -#include "base/values.h" - -int error_code, error_line, error_column; -std::string error_message; - -// Entry point for LibFuzzer. -extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) { - if (size < 2) - return 0; - - // Create a copy of input buffer, as otherwise we don't catch - // overflow that touches the last byte (which is used in options). - std::unique_ptr<char[]> input(new char[size - 1]); - memcpy(input.get(), data, size - 1); - - base::StringPiece input_string(input.get(), size - 1); - - const int options = data[size - 1]; - base::JSONReader::ReadAndReturnError(input_string, options, &error_code, - &error_message, &error_line, - &error_column); - - return 0; -}
diff --git a/base/json/string_escape_fuzzer.cc b/base/json/string_escape_fuzzer.cc deleted file mode 100644 index e44bd4f..0000000 --- a/base/json/string_escape_fuzzer.cc +++ /dev/null
@@ -1,37 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/json/string_escape.h" - -#include <memory> - -std::string escaped_string; - -// Entry point for LibFuzzer. -extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) { - if (size < 2) - return 0; - - const bool put_in_quotes = data[size - 1]; - - // Create a copy of input buffer, as otherwise we don't catch - // overflow that touches the last byte (which is used in put_in_quotes). - size_t actual_size_char8 = size - 1; - std::unique_ptr<char[]> input(new char[actual_size_char8]); - memcpy(input.get(), data, actual_size_char8); - - base::StringPiece input_string(input.get(), actual_size_char8); - base::EscapeJSONString(input_string, put_in_quotes, &escaped_string); - - // Test for wide-strings if available size is even. - if (actual_size_char8 & 1) - return 0; - - size_t actual_size_char16 = actual_size_char8 / 2; - base::StringPiece16 input_string16( - reinterpret_cast<base::char16*>(input.get()), actual_size_char16); - base::EscapeJSONString(input_string16, put_in_quotes, &escaped_string); - - return 0; -}
diff --git a/base/linux_util.cc b/base/linux_util.cc deleted file mode 100644 index 1f3ae49..0000000 --- a/base/linux_util.cc +++ /dev/null
@@ -1,211 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/linux_util.h" - -#include <dirent.h> -#include <errno.h> -#include <fcntl.h> -#include <limits.h> -#include <stdlib.h> -#include <sys/stat.h> -#include <sys/types.h> -#include <unistd.h> - -#include <memory> -#include <vector> - -#include "base/command_line.h" -#include "base/files/file_util.h" -#include "base/memory/singleton.h" -#include "base/strings/string_number_conversions.h" -#include "base/strings/string_split.h" -#include "base/strings/string_tokenizer.h" -#include "base/strings/string_util.h" -#include "base/synchronization/lock.h" -#include "build_config.h" - -namespace { - -// Not needed for OS_CHROMEOS. -#if defined(OS_LINUX) -enum LinuxDistroState { - STATE_DID_NOT_CHECK = 0, - STATE_CHECK_STARTED = 1, - STATE_CHECK_FINISHED = 2, -}; - -// Helper class for GetLinuxDistro(). -class LinuxDistroHelper { - public: - // Retrieves the Singleton. - static LinuxDistroHelper* GetInstance() { - return base::Singleton<LinuxDistroHelper>::get(); - } - - // The simple state machine goes from: - // STATE_DID_NOT_CHECK -> STATE_CHECK_STARTED -> STATE_CHECK_FINISHED. - LinuxDistroHelper() : state_(STATE_DID_NOT_CHECK) {} - ~LinuxDistroHelper() = default; - - // Retrieve the current state, if we're in STATE_DID_NOT_CHECK, - // we automatically move to STATE_CHECK_STARTED so nobody else will - // do the check. - LinuxDistroState State() { - base::AutoLock scoped_lock(lock_); - if (STATE_DID_NOT_CHECK == state_) { - state_ = STATE_CHECK_STARTED; - return STATE_DID_NOT_CHECK; - } - return state_; - } - - // Indicate the check finished, move to STATE_CHECK_FINISHED. - void CheckFinished() { - base::AutoLock scoped_lock(lock_); - DCHECK_EQ(STATE_CHECK_STARTED, state_); - state_ = STATE_CHECK_FINISHED; - } - - private: - base::Lock lock_; - LinuxDistroState state_; -}; -#endif // if defined(OS_LINUX) - -bool GetTasksForProcess(pid_t pid, std::vector<pid_t>* tids) { - char buf[256]; - snprintf(buf, sizeof(buf), "/proc/%d/task", pid); - - DIR* task = opendir(buf); - if (!task) { - DLOG(WARNING) << "Cannot open " << buf; - return false; - } - - struct dirent* dent; - while ((dent = readdir(task))) { - char* endptr; - const unsigned long int tid_ul = strtoul(dent->d_name, &endptr, 10); - if (tid_ul == ULONG_MAX || *endptr) - continue; - tids->push_back(tid_ul); - } - closedir(task); - return true; -} - -} // namespace - -namespace base { - -// Account for the terminating null character. -static const int kDistroSize = 128 + 1; - -// We use this static string to hold the Linux distro info. If we -// crash, the crash handler code will send this in the crash dump. -char g_linux_distro[kDistroSize] = "Unknown"; - -std::string GetLinuxDistro() { - LinuxDistroHelper* distro_state_singleton = LinuxDistroHelper::GetInstance(); - LinuxDistroState state = distro_state_singleton->State(); - if (STATE_CHECK_FINISHED == state) - return g_linux_distro; - if (STATE_CHECK_STARTED == state) - return "Unknown"; // Don't wait for other thread to finish. - DCHECK_EQ(state, STATE_DID_NOT_CHECK); - // We do this check only once per process. If it fails, there's - // little reason to believe it will work if we attempt to run - // lsb_release again. - std::vector<std::string> argv; - argv.push_back("lsb_release"); - argv.push_back("-d"); - std::string output; - GetAppOutput(CommandLine(argv), &output); - if (output.length() > 0) { - // lsb_release -d should return: Description:<tab>Distro Info - const char field[] = "Description:\t"; - if (output.compare(0, strlen(field), field) == 0) { - SetLinuxDistro(output.substr(strlen(field))); - } - } - distro_state_singleton->CheckFinished(); - return g_linux_distro; -} - -void SetLinuxDistro(const std::string& distro) { - std::string trimmed_distro; - TrimWhitespaceASCII(distro, TRIM_ALL, &trimmed_distro); - strlcpy(g_linux_distro, trimmed_distro.c_str(), kDistroSize); -} - -pid_t FindThreadIDWithSyscall(pid_t pid, const std::string& expected_data, - bool* syscall_supported) { - if (syscall_supported != nullptr) - *syscall_supported = false; - - std::vector<pid_t> tids; - if (!GetTasksForProcess(pid, &tids)) - return -1; - - std::unique_ptr<char[]> syscall_data(new char[expected_data.length()]); - for (pid_t tid : tids) { - char buf[256]; - snprintf(buf, sizeof(buf), "/proc/%d/task/%d/syscall", pid, tid); - int fd = open(buf, O_RDONLY); - if (fd < 0) - continue; - if (syscall_supported != nullptr) - *syscall_supported = true; - bool read_ret = ReadFromFD(fd, syscall_data.get(), expected_data.length()); - close(fd); - if (!read_ret) - continue; - - if (0 == strncmp(expected_data.c_str(), syscall_data.get(), - expected_data.length())) { - return tid; - } - } - return -1; -} - -pid_t FindThreadID(pid_t pid, pid_t ns_tid, bool* ns_pid_supported) { - if (ns_pid_supported) - *ns_pid_supported = false; - - std::vector<pid_t> tids; - if (!GetTasksForProcess(pid, &tids)) - return -1; - - for (pid_t tid : tids) { - char buf[256]; - snprintf(buf, sizeof(buf), "/proc/%d/task/%d/status", pid, tid); - std::string status; - if (!ReadFileToString(FilePath(buf), &status)) - return -1; - StringTokenizer tokenizer(status, "\n"); - while (tokenizer.GetNext()) { - StringPiece value_str(tokenizer.token_piece()); - if (!value_str.starts_with("NSpid")) - continue; - if (ns_pid_supported) - *ns_pid_supported = true; - std::vector<StringPiece> split_value_str = SplitStringPiece( - value_str, "\t", TRIM_WHITESPACE, SPLIT_WANT_NONEMPTY); - DCHECK_GE(split_value_str.size(), 2u); - int value; - // The last value in the list is the PID in the namespace. - if (StringToInt(split_value_str.back(), &value) && value == ns_tid) { - // The second value in the list is the real PID. - if (StringToInt(split_value_str[1], &value)) - return value; - } - break; - } - } - return -1; -} - -} // namespace base
diff --git a/base/linux_util.h b/base/linux_util.h deleted file mode 100644 index 272e06b..0000000 --- a/base/linux_util.h +++ /dev/null
@@ -1,44 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_LINUX_UTIL_H_ -#define BASE_LINUX_UTIL_H_ - -#include <stdint.h> -#include <sys/types.h> - -#include <string> - -#include "base/base_export.h" - -namespace base { - -// This is declared here so the crash reporter can access the memory directly -// in compromised context without going through the standard library. -BASE_EXPORT extern char g_linux_distro[]; - -// Get the Linux Distro if we can, or return "Unknown". -BASE_EXPORT std::string GetLinuxDistro(); - -// Set the Linux Distro string. -BASE_EXPORT void SetLinuxDistro(const std::string& distro); - -// For a given process |pid|, look through all its threads and find the first -// thread with /proc/[pid]/task/[thread_id]/syscall whose first N bytes matches -// |expected_data|, where N is the length of |expected_data|. -// Returns the thread id or -1 on error. If |syscall_supported| is -// set to false the kernel does not support syscall in procfs. -BASE_EXPORT pid_t FindThreadIDWithSyscall(pid_t pid, - const std::string& expected_data, - bool* syscall_supported); - -// For a given process |pid|, look through all its threads and find the first -// thread with /proc/[pid]/task/[thread_id]/status where NSpid matches |ns_tid|. -// Returns the thread id or -1 on error. If |ns_pid_supported| is -// set to false the kernel does not support NSpid in procfs. -BASE_EXPORT pid_t FindThreadID(pid_t pid, pid_t ns_tid, bool* ns_pid_supported); - -} // namespace base - -#endif // BASE_LINUX_UTIL_H_
diff --git a/base/mac/OWNERS b/base/mac/OWNERS deleted file mode 100644 index 93e90e0..0000000 --- a/base/mac/OWNERS +++ /dev/null
@@ -1,8 +0,0 @@ -mark@chromium.org -thakis@chromium.org - -# sdk_forward_declarations.[h|mm] will likely need to be modified by Cocoa -# developers in general. -per-file sdk_forward_declarations.*=file://chrome/browser/ui/cocoa/OWNERS - -# COMPONENT: Internals
diff --git a/base/mac/authorization_util.h b/base/mac/authorization_util.h deleted file mode 100644 index 4629039..0000000 --- a/base/mac/authorization_util.h +++ /dev/null
@@ -1,82 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_AUTHORIZATION_UTIL_H_ -#define BASE_MAC_AUTHORIZATION_UTIL_H_ - -// AuthorizationExecuteWithPrivileges fork()s and exec()s the tool, but it -// does not wait() for it. It also doesn't provide the caller with access to -// the forked pid. If used irresponsibly, zombie processes will accumulate. -// -// Apple's really gotten us between a rock and a hard place, here. -// -// Fortunately, AuthorizationExecuteWithPrivileges does give access to the -// tool's stdout (and stdin) via a FILE* pipe. The tool can output its pid -// to this pipe, and the main program can read it, and then have something -// that it can wait() for. -// -// The contract is that any tool executed by the wrappers declared in this -// file must print its pid to stdout on a line by itself before doing anything -// else. -// -// http://developer.apple.com/library/mac/#samplecode/BetterAuthorizationSample/Listings/BetterAuthorizationSampleLib_c.html -// (Look for "What's This About Zombies?") - -#include <CoreFoundation/CoreFoundation.h> -#include <Security/Authorization.h> -#include <stdio.h> -#include <sys/types.h> - -#include "base/base_export.h" - -namespace base { -namespace mac { - -// Obtains an AuthorizationRef for the rights indicated by |rights|. If -// necessary, prompts the user for authentication. If the user is prompted, -// |prompt| will be used as the prompt string and an icon appropriate for the -// application will be displayed in a prompt dialog. Note that the system -// appends its own text to the prompt string. |extraFlags| will be ORed -// together with the default flags. Returns NULL on failure. -BASE_EXPORT -AuthorizationRef GetAuthorizationRightsWithPrompt( - AuthorizationRights* rights, - CFStringRef prompt, - AuthorizationFlags extraFlags); - -// Obtains an AuthorizationRef (using |GetAuthorizationRightsWithPrompt|) that -// can be used to run commands as root. -BASE_EXPORT -AuthorizationRef AuthorizationCreateToRunAsRoot(CFStringRef prompt); - -// Calls straight through to AuthorizationExecuteWithPrivileges. If that -// call succeeds, |pid| will be set to the pid of the executed tool. If the -// pid can't be determined, |pid| will be set to -1. |pid| must not be NULL. -// |pipe| may be NULL, but the tool will always be executed with a pipe in -// order to read the pid from its stdout. -BASE_EXPORT -OSStatus ExecuteWithPrivilegesAndGetPID(AuthorizationRef authorization, - const char* tool_path, - AuthorizationFlags options, - const char** arguments, - FILE** pipe, - pid_t* pid); - -// Calls ExecuteWithPrivilegesAndGetPID, and if that call succeeds, calls -// waitpid() to wait for the process to exit. If waitpid() succeeds, the -// exit status is placed in |exit_status|, otherwise, -1 is stored. -// |exit_status| may be NULL and this function will still wait for the process -// to exit. -BASE_EXPORT -OSStatus ExecuteWithPrivilegesAndWait(AuthorizationRef authorization, - const char* tool_path, - AuthorizationFlags options, - const char** arguments, - FILE** pipe, - int* exit_status); - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_AUTHORIZATION_UTIL_H_
diff --git a/base/mac/authorization_util.mm b/base/mac/authorization_util.mm deleted file mode 100644 index a3bc4f9..0000000 --- a/base/mac/authorization_util.mm +++ /dev/null
@@ -1,201 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/mac/authorization_util.h" - -#import <Foundation/Foundation.h> -#include <stddef.h> -#include <sys/wait.h> - -#include <string> - -#include "base/logging.h" -#include "base/mac/bundle_locations.h" -#include "base/mac/foundation_util.h" -#include "base/mac/mac_logging.h" -#include "base/mac/scoped_authorizationref.h" -#include "base/macros.h" -#include "base/posix/eintr_wrapper.h" -#include "base/strings/string_number_conversions.h" -#include "base/strings/string_util.h" - -namespace base { -namespace mac { - -AuthorizationRef GetAuthorizationRightsWithPrompt( - AuthorizationRights* rights, - CFStringRef prompt, - AuthorizationFlags extraFlags) { - // Create an empty AuthorizationRef. - ScopedAuthorizationRef authorization; - OSStatus status = AuthorizationCreate(NULL, kAuthorizationEmptyEnvironment, - kAuthorizationFlagDefaults, - authorization.get_pointer()); - if (status != errAuthorizationSuccess) { - OSSTATUS_LOG(ERROR, status) << "AuthorizationCreate"; - return NULL; - } - - AuthorizationFlags flags = kAuthorizationFlagDefaults | - kAuthorizationFlagInteractionAllowed | - kAuthorizationFlagExtendRights | - kAuthorizationFlagPreAuthorize | - extraFlags; - - // product_logo_32.png is used instead of app.icns because Authorization - // Services can't deal with .icns files. - NSString* icon_path = - [base::mac::FrameworkBundle() pathForResource:@"product_logo_32" - ofType:@"png"]; - const char* icon_path_c = [icon_path fileSystemRepresentation]; - size_t icon_path_length = icon_path_c ? strlen(icon_path_c) : 0; - - // The OS will dispay |prompt| along with a sentence asking the user to type - // the "password to allow this." - NSString* prompt_ns = base::mac::CFToNSCast(prompt); - const char* prompt_c = [prompt_ns UTF8String]; - size_t prompt_length = prompt_c ? strlen(prompt_c) : 0; - - AuthorizationItem environment_items[] = { - {kAuthorizationEnvironmentIcon, icon_path_length, (void*)icon_path_c, 0}, - {kAuthorizationEnvironmentPrompt, prompt_length, (void*)prompt_c, 0} - }; - - AuthorizationEnvironment environment = {arraysize(environment_items), - environment_items}; - - status = AuthorizationCopyRights(authorization, - rights, - &environment, - flags, - NULL); - - if (status != errAuthorizationSuccess) { - if (status != errAuthorizationCanceled) { - OSSTATUS_LOG(ERROR, status) << "AuthorizationCopyRights"; - } - return NULL; - } - - return authorization.release(); -} - -AuthorizationRef AuthorizationCreateToRunAsRoot(CFStringRef prompt) { - // Specify the "system.privilege.admin" right, which allows - // AuthorizationExecuteWithPrivileges to run commands as root. - AuthorizationItem right_items[] = { - {kAuthorizationRightExecute, 0, NULL, 0} - }; - AuthorizationRights rights = {arraysize(right_items), right_items}; - - return GetAuthorizationRightsWithPrompt(&rights, prompt, 0); -} - -OSStatus ExecuteWithPrivilegesAndGetPID(AuthorizationRef authorization, - const char* tool_path, - AuthorizationFlags options, - const char** arguments, - FILE** pipe, - pid_t* pid) { - // pipe may be NULL, but this function needs one. In that case, use a local - // pipe. - FILE* local_pipe; - FILE** pipe_pointer; - if (pipe) { - pipe_pointer = pipe; - } else { - pipe_pointer = &local_pipe; - } - -// AuthorizationExecuteWithPrivileges is deprecated in macOS 10.7, but no good -// replacement exists. https://crbug.com/593133. -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wdeprecated-declarations" - // AuthorizationExecuteWithPrivileges wants |char* const*| for |arguments|, - // but it doesn't actually modify the arguments, and that type is kind of - // silly and callers probably aren't dealing with that. Put the cast here - // to make things a little easier on callers. - OSStatus status = AuthorizationExecuteWithPrivileges(authorization, - tool_path, - options, - (char* const*)arguments, - pipe_pointer); -#pragma clang diagnostic pop - if (status != errAuthorizationSuccess) { - return status; - } - - int line_pid = -1; - size_t line_length = 0; - char* line_c = fgetln(*pipe_pointer, &line_length); - if (line_c) { - if (line_length > 0 && line_c[line_length - 1] == '\n') { - // line_c + line_length is the start of the next line if there is one. - // Back up one character. - --line_length; - } - std::string line(line_c, line_length); - if (!base::StringToInt(line, &line_pid)) { - // StringToInt may have set line_pid to something, but if the conversion - // was imperfect, use -1. - LOG(ERROR) << "ExecuteWithPrivilegesAndGetPid: funny line: " << line; - line_pid = -1; - } - } else { - LOG(ERROR) << "ExecuteWithPrivilegesAndGetPid: no line"; - } - - if (!pipe) { - fclose(*pipe_pointer); - } - - if (pid) { - *pid = line_pid; - } - - return status; -} - -OSStatus ExecuteWithPrivilegesAndWait(AuthorizationRef authorization, - const char* tool_path, - AuthorizationFlags options, - const char** arguments, - FILE** pipe, - int* exit_status) { - pid_t pid; - OSStatus status = ExecuteWithPrivilegesAndGetPID(authorization, - tool_path, - options, - arguments, - pipe, - &pid); - if (status != errAuthorizationSuccess) { - return status; - } - - // exit_status may be NULL, but this function needs it. In that case, use a - // local version. - int local_exit_status; - int* exit_status_pointer; - if (exit_status) { - exit_status_pointer = exit_status; - } else { - exit_status_pointer = &local_exit_status; - } - - if (pid != -1) { - pid_t wait_result = HANDLE_EINTR(waitpid(pid, exit_status_pointer, 0)); - if (wait_result != pid) { - PLOG(ERROR) << "waitpid"; - *exit_status_pointer = -1; - } - } else { - *exit_status_pointer = -1; - } - - return status; -} - -} // namespace mac -} // namespace base
diff --git a/base/mac/call_with_eh_frame.cc b/base/mac/call_with_eh_frame.cc deleted file mode 100644 index 35e01bc..0000000 --- a/base/mac/call_with_eh_frame.cc +++ /dev/null
@@ -1,54 +0,0 @@ -// Copyright 2015 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/mac/call_with_eh_frame.h" - -#include <stdint.h> -#include <unwind.h> - -#include "build_config.h" - -namespace base { -namespace mac { - -#if defined(OS_IOS) -// No iOS assembly implementation exists, so just call the block directly. -void CallWithEHFrame(void (^block)(void)) { - block(); -} -#else // OS_MACOSX -extern "C" _Unwind_Reason_Code __gxx_personality_v0(int, - _Unwind_Action, - uint64_t, - struct _Unwind_Exception*, - struct _Unwind_Context*); - -_Unwind_Reason_Code CxxPersonalityRoutine( - int version, - _Unwind_Action actions, - uint64_t exception_class, - struct _Unwind_Exception* exception_object, - struct _Unwind_Context* context) { - // Unwinding is a two-phase process: phase one searches for an exception - // handler, and phase two performs cleanup. For phase one, this custom - // personality will terminate the search. For phase two, this should delegate - // back to the standard personality routine. - - if ((actions & _UA_SEARCH_PHASE) != 0) { - // Tell libunwind that this is the end of the stack. When it encounters the - // CallWithEHFrame, it will stop searching for an exception handler. The - // result is that no exception handler has been found higher on the stack, - // and any that are lower on the stack (e.g. in CFRunLoopRunSpecific), will - // now be skipped. Since this is reporting the end of the stack, and no - // exception handler will have been found, std::terminate() will be called. - return _URC_END_OF_STACK; - } - - return __gxx_personality_v0(version, actions, exception_class, - exception_object, context); -} -#endif // defined(OS_IOS) - -} // namespace mac -} // namespace base
diff --git a/base/mac/call_with_eh_frame.h b/base/mac/call_with_eh_frame.h deleted file mode 100644 index 1f7d5e0..0000000 --- a/base/mac/call_with_eh_frame.h +++ /dev/null
@@ -1,26 +0,0 @@ -// Copyright 2015 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_CALL_WITH_EH_FRAME_H_ -#define BASE_MAC_CALL_WITH_EH_FRAME_H_ - -#include "base/base_export.h" - -namespace base { -namespace mac { - -// Invokes the specified block in a stack frame with a special exception -// handler. This function creates an exception handling stack frame that -// specifies a custom C++ exception personality routine, which terminates the -// search for an exception handler at this frame. -// -// The purpose of this function is to prevent a try/catch statement in system -// libraries, acting as a global exception handler, from handling exceptions -// in such a way that disrupts the generation of useful stack traces. -void BASE_EXPORT CallWithEHFrame(void (^block)(void)); - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_CALL_WITH_EH_FRAME_H_
diff --git a/base/mac/call_with_eh_frame_asm.S b/base/mac/call_with_eh_frame_asm.S deleted file mode 100644 index 0e399cf..0000000 --- a/base/mac/call_with_eh_frame_asm.S +++ /dev/null
@@ -1,89 +0,0 @@ -// Copyright 2015 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -// base::mac::CallWithEHFrame(void () block_pointer) -#define CALL_WITH_EH_FRAME __ZN4base3mac15CallWithEHFrameEU13block_pointerFvvE - - .section __TEXT,__text,regular,pure_instructions -#if !defined(COMPONENT_BUILD) - .private_extern CALL_WITH_EH_FRAME -#endif - .globl CALL_WITH_EH_FRAME - .align 4 -CALL_WITH_EH_FRAME: - - .cfi_startproc - - // Configure the C++ exception handler personality routine. Normally the - // compiler would emit ___gxx_personality_v0 here. The purpose of this - // function is to use a custom personality routine. - .cfi_personality 155, __ZN4base3mac21CxxPersonalityRoutineEi14_Unwind_ActionyP17_Unwind_ExceptionP15_Unwind_Context - .cfi_lsda 16, CallWithEHFrame_exception_table - -Lfunction_start: - pushq %rbp - .cfi_def_cfa_offset 16 - .cfi_offset %rbp, -16 - movq %rsp, %rbp - .cfi_def_cfa_register %rbp - - // Load the function pointer from the block descriptor. - movq 16(%rdi), %rax - - // Execute the block in the context of a C++ try{}. -Ltry_start: - callq *%rax -Ltry_end: - popq %rbp - ret - - // Landing pad for the exception handler. This should never be called, since - // the personality routine will stop the search for an exception handler, - // which will cause the runtime to invoke the default terminate handler. -Lcatch: - movq %rax, %rdi - callq ___cxa_begin_catch // The ABI requires a call to the catch handler. - ud2 // In the event this is called, make it fatal. - -Lfunction_end: - .cfi_endproc - -// The C++ exception table that is used to identify this frame as an -// exception handler. See http://llvm.org/docs/ExceptionHandling.html and -// http://mentorembedded.github.io/cxx-abi/exceptions.pdf. - .section __TEXT,__gcc_except_tab - .align 2 -CallWithEHFrame_exception_table: - .byte 255 // DW_EH_PE_omit - .byte 155 // DW_EH_PE_indirect | DW_EH_PE_pcrel | DW_EH_PE_sdata4 - .asciz "\242\200\200" // LE int128 for the number of bytes in this table. - .byte 3 // DW_EH_PE_udata4 - .byte 26 // Callsite table length. - -// First callsite. -CS1_begin = Ltry_start - Lfunction_start - .long CS1_begin -CS1_end = Ltry_end - Ltry_start - .long CS1_end - -// First landing pad. -LP1 = Lcatch - Lfunction_start - .long LP1 - .byte 1 // Action record. - -// Second callsite. -CS2_begin = Ltry_end - Lfunction_start - .long CS2_begin -CS2_end = Lfunction_end - Ltry_end - .long CS2_end - -// Second landing pad (none). - .long 0 - .byte 0 // No action. - -// Action table. - .byte 1 // Action record 1. - .byte 0 // No further action to take. - .long 0 // No type filter for this catch(){} clause. - .align 2
diff --git a/base/mac/close_nocancel.cc b/base/mac/close_nocancel.cc deleted file mode 100644 index 8971e73..0000000 --- a/base/mac/close_nocancel.cc +++ /dev/null
@@ -1,70 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -// http://crbug.com/269623 -// http://openradar.appspot.com/14999594 -// -// When the default version of close used on Mac OS X fails with EINTR, the -// file descriptor is not in a deterministic state. It may have been closed, -// or it may not have been. This makes it impossible to gracefully recover -// from the error. If the close is retried after the FD has been closed, the -// subsequent close can report EBADF, or worse, it can close an unrelated FD -// opened by another thread. If the close is not retried after the FD has been -// left open, the FD is leaked. Neither of these are good options. -// -// Mac OS X provides an alternate version of close, close$NOCANCEL. This -// version will never fail with EINTR before the FD is actually closed. With -// this version, it is thus safe to call close without checking for EINTR (as -// the HANDLE_EINTR macro does) and not risk leaking the FD. In fact, mixing -// this verison of close with HANDLE_EINTR is hazardous. -// -// The $NOCANCEL variants of various system calls are activated by compiling -// with __DARWIN_NON_CANCELABLE, which prevents them from being pthread -// cancellation points. Rather than taking such a heavy-handed approach, this -// file implements an alternative: to use the $NOCANCEL variant of close (thus -// preventing it from being a pthread cancellation point) without affecting -// any other system calls. -// -// This file operates by providing a close function with the non-$NOCANCEL -// symbol name expected for the compilation environment as set by <unistd.h> -// and <sys/cdefs.h> (the DARWIN_ALIAS_C macro). That name is set by an asm -// label on the declaration of the close function, so the definition of that -// function receives that name. The function calls the $NOCANCEL variant, which -// is resolved from libsyscall. By linking with this version of close prior to -// the libsyscall version, close's implementation is overridden. - -#include <sys/cdefs.h> -#include <unistd.h> - -// If the non-cancelable variants of all system calls have already been -// chosen, do nothing. -#if !__DARWIN_NON_CANCELABLE - -extern "C" { - -#if !__DARWIN_ONLY_UNIX_CONFORMANCE - -// When there's a choice between UNIX2003 and pre-UNIX2003. There's no -// close$NOCANCEL symbol in this case, so use close$NOCANCEL$UNIX2003 as the -// implementation. It does the same thing that close$NOCANCEL would do. -#define close_implementation close$NOCANCEL$UNIX2003 - -#else // __DARWIN_ONLY_UNIX_CONFORMANCE - -// When only UNIX2003 is supported: -#define close_implementation close$NOCANCEL - -#endif - -int close_implementation(int fd); - -int close(int fd) { - return close_implementation(fd); -} - -#undef close_implementation - -} // extern "C" - -#endif // !__DARWIN_NON_CANCELABLE
diff --git a/base/mac/launch_services_util.h b/base/mac/launch_services_util.h deleted file mode 100644 index 30d1eec..0000000 --- a/base/mac/launch_services_util.h +++ /dev/null
@@ -1,31 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_LAUNCH_SERVICES_UTIL_H_ -#define BASE_MAC_LAUNCH_SERVICES_UTIL_H_ - -#import <AppKit/AppKit.h> - -#include "base/base_export.h" -#include "base/command_line.h" -#include "base/files/file_path.h" -#include "base/process/process.h" - -namespace base { -namespace mac { - -// Launches the application bundle at |bundle_path|, passing argv[1..] from -// |command_line| as command line arguments if the app isn't already running. -// |launch_options| are passed directly to -// -[NSWorkspace launchApplicationAtURL:options:configuration:error:]. -// Returns a valid process if the app was successfully launched. -BASE_EXPORT Process -OpenApplicationWithPath(const FilePath& bundle_path, - const CommandLine& command_line, - NSWorkspaceLaunchOptions launch_options); - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_LAUNCH_SERVICES_UTIL_H_
diff --git a/base/mac/launch_services_util.mm b/base/mac/launch_services_util.mm deleted file mode 100644 index fa6e808..0000000 --- a/base/mac/launch_services_util.mm +++ /dev/null
@@ -1,52 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#import "base/mac/launch_services_util.h" - -#include "base/logging.h" -#include "base/strings/sys_string_conversions.h" - -namespace base { -namespace mac { - -Process OpenApplicationWithPath(const base::FilePath& bundle_path, - const CommandLine& command_line, - NSWorkspaceLaunchOptions launch_options) { - NSString* bundle_url_spec = base::SysUTF8ToNSString(bundle_path.value()); - NSURL* bundle_url = [NSURL fileURLWithPath:bundle_url_spec isDirectory:YES]; - DCHECK(bundle_url); - if (!bundle_url) { - return Process(); - } - - // NSWorkspace automatically adds the binary path as the first argument and - // it should not be included into the list. - std::vector<std::string> argv = command_line.argv(); - int argc = argv.size(); - NSMutableArray* launch_args = [NSMutableArray arrayWithCapacity:argc - 1]; - for (int i = 1; i < argc; ++i) { - [launch_args addObject:base::SysUTF8ToNSString(argv[i])]; - } - - NSDictionary* configuration = @{ - NSWorkspaceLaunchConfigurationArguments : launch_args, - }; - NSError* launch_error = nil; - // TODO(jeremya): this opens a new browser window if Chrome is already - // running without any windows open. - NSRunningApplication* app = - [[NSWorkspace sharedWorkspace] launchApplicationAtURL:bundle_url - options:launch_options - configuration:configuration - error:&launch_error]; - if (launch_error) { - LOG(ERROR) << base::SysNSStringToUTF8([launch_error localizedDescription]); - return Process(); - } - DCHECK(app); - return Process([app processIdentifier]); -} - -} // namespace mac -} // namespace base
diff --git a/base/mac/launchd.cc b/base/mac/launchd.cc deleted file mode 100644 index 0337d2e..0000000 --- a/base/mac/launchd.cc +++ /dev/null
@@ -1,75 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/mac/launchd.h" - -#include "base/logging.h" -#include "base/mac/scoped_launch_data.h" - -namespace base { -namespace mac { - -// MessageForJob sends a single message to launchd with a simple dictionary -// mapping |operation| to |job_label|, and returns the result of calling -// launch_msg to send that message. On failure, returns NULL. The caller -// assumes ownership of the returned launch_data_t object. -launch_data_t MessageForJob(const std::string& job_label, - const char* operation) { - // launch_data_alloc returns something that needs to be freed. - ScopedLaunchData message(launch_data_alloc(LAUNCH_DATA_DICTIONARY)); - if (!message.is_valid()) { - LOG(ERROR) << "launch_data_alloc"; - return NULL; - } - - // launch_data_new_string returns something that needs to be freed, but - // the dictionary will assume ownership when launch_data_dict_insert is - // called, so put it in a scoper and .release() it when given to the - // dictionary. - ScopedLaunchData job_label_launchd(launch_data_new_string(job_label.c_str())); - if (!job_label_launchd.is_valid()) { - LOG(ERROR) << "launch_data_new_string"; - return NULL; - } - - if (!launch_data_dict_insert(message.get(), job_label_launchd.release(), - operation)) { - return NULL; - } - - return launch_msg(message.get()); -} - -pid_t PIDForJob(const std::string& job_label) { - ScopedLaunchData response(MessageForJob(job_label, LAUNCH_KEY_GETJOB)); - if (!response.is_valid()) { - return -1; - } - - launch_data_type_t response_type = launch_data_get_type(response.get()); - if (response_type != LAUNCH_DATA_DICTIONARY) { - if (response_type == LAUNCH_DATA_ERRNO) { - LOG(ERROR) << "PIDForJob: error " - << launch_data_get_errno(response.get()); - } else { - LOG(ERROR) << "PIDForJob: expected dictionary, got " << response_type; - } - return -1; - } - - launch_data_t pid_data = - launch_data_dict_lookup(response.get(), LAUNCH_JOBKEY_PID); - if (!pid_data) - return 0; - - if (launch_data_get_type(pid_data) != LAUNCH_DATA_INTEGER) { - LOG(ERROR) << "PIDForJob: expected integer"; - return -1; - } - - return launch_data_get_integer(pid_data); -} - -} // namespace mac -} // namespace base
diff --git a/base/mac/launchd.h b/base/mac/launchd.h deleted file mode 100644 index 9e4514e..0000000 --- a/base/mac/launchd.h +++ /dev/null
@@ -1,34 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_LAUNCHD_H_ -#define BASE_MAC_LAUNCHD_H_ - -#include <launch.h> -#include <sys/types.h> - -#include <string> - -#include "base/base_export.h" - -namespace base { -namespace mac { - -// MessageForJob sends a single message to launchd with a simple dictionary -// mapping |operation| to |job_label|, and returns the result of calling -// launch_msg to send that message. On failure, returns NULL. The caller -// assumes ownership of the returned launch_data_t object. -BASE_EXPORT -launch_data_t MessageForJob(const std::string& job_label, - const char* operation); - -// Returns the process ID for |job_label| if the job is running, 0 if the job -// is loaded but not running, or -1 on error. -BASE_EXPORT -pid_t PIDForJob(const std::string& job_label); - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_LAUNCHD_H_
diff --git a/base/mac/mach_port_broker.h b/base/mac/mach_port_broker.h deleted file mode 100644 index 4554b6a..0000000 --- a/base/mac/mach_port_broker.h +++ /dev/null
@@ -1,108 +0,0 @@ -// Copyright 2016 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_MACH_PORT_BROKER_H_ -#define BASE_MAC_MACH_PORT_BROKER_H_ - -#include <mach/mach.h> - -#include <map> -#include <memory> -#include <string> - -#include "base/base_export.h" -#include "base/mac/dispatch_source_mach.h" -#include "base/mac/scoped_mach_port.h" -#include "base/macros.h" -#include "base/process/port_provider_mac.h" -#include "base/process/process_handle.h" -#include "base/synchronization/lock.h" - -namespace base { - -// On OS X, the task port of a process is required to collect metrics about the -// process, and to insert Mach ports into the process. Running |task_for_pid()| -// is only allowed for privileged code. However, a process has port rights to -// all its subprocesses, so let the child processes send their Mach port to the -// parent over IPC. -// -// Mach ports can only be sent over Mach IPC, not over the |socketpair()| that -// the regular IPC system uses. Hence, the child processes opens a Mach -// connection shortly after launching and ipc their mach data to the parent -// process. A single |MachPortBroker| with a given name is expected to exist in -// the parent process. -// -// Since this data arrives over a separate channel, it is not available -// immediately after a child process has been started. -class BASE_EXPORT MachPortBroker : public base::PortProvider { - public: - // For use in child processes. This will send the task port of the current - // process over Mach IPC to the port registered by name (via this class) in - // the parent process. Returns true if the message was sent successfully - // and false if otherwise. - static bool ChildSendTaskPortToParent(const std::string& name); - - // Returns the Mach port name to use when sending or receiving messages. - // Does the Right Thing in the browser and in child processes. - static std::string GetMachPortName(const std::string& name, bool is_child); - - MachPortBroker(const std::string& name); - ~MachPortBroker() override; - - // Performs any initialization work. - bool Init(); - - // Adds a placeholder to the map for the given pid with MACH_PORT_NULL. - // Callers are expected to later update the port with FinalizePid(). Callers - // MUST acquire the lock given by GetLock() before calling this method (and - // release the lock afterwards). - void AddPlaceholderForPid(base::ProcessHandle pid); - - // Removes |pid| from the task port map. Callers MUST acquire the lock given - // by GetLock() before calling this method (and release the lock afterwards). - void InvalidatePid(base::ProcessHandle pid); - - // The lock that protects this MachPortBroker object. Callers MUST acquire - // and release this lock around calls to AddPlaceholderForPid(), - // InvalidatePid(), and FinalizePid(); - base::Lock& GetLock() { return lock_; } - - // Implement |base::PortProvider|. - mach_port_t TaskForPid(base::ProcessHandle process) const override; - - private: - friend class MachPortBrokerTest; - - // Message handler that is invoked on |dispatch_source_| when an - // incoming message needs to be received. - void HandleRequest(); - - // Updates the mapping for |pid| to include the given |mach_info|. Does - // nothing if PlaceholderForPid() has not already been called for the given - // |pid|. Callers MUST acquire the lock given by GetLock() before calling - // this method (and release the lock afterwards). - void FinalizePid(base::ProcessHandle pid, mach_port_t task_port); - - // Name used to identify a particular port broker. - const std::string name_; - - // The Mach port on which the server listens. - base::mac::ScopedMachReceiveRight server_port_; - - // The dispatch source and queue on which Mach messages will be received. - std::unique_ptr<base::DispatchSourceMach> dispatch_source_; - - // Stores mach info for every process in the broker. - typedef std::map<base::ProcessHandle, mach_port_t> MachMap; - MachMap mach_map_; - - // Mutex that guards |mach_map_|. - mutable base::Lock lock_; - - DISALLOW_COPY_AND_ASSIGN(MachPortBroker); -}; - -} // namespace base - -#endif // BASE_MAC_MACH_PORT_BROKER_H_
diff --git a/base/mac/mach_port_broker.mm b/base/mac/mach_port_broker.mm deleted file mode 100644 index 6d9fec5..0000000 --- a/base/mac/mach_port_broker.mm +++ /dev/null
@@ -1,184 +0,0 @@ -// Copyright 2016 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/mac/mach_port_broker.h" - -#include <bsm/libbsm.h> -#include <servers/bootstrap.h> - -#include "base/logging.h" -#include "base/mac/foundation_util.h" -#include "base/mac/mach_logging.h" -#include "base/strings/string_util.h" -#include "base/strings/stringprintf.h" - -namespace base { - -namespace { - -// Mach message structure used in the child as a sending message. -struct MachPortBroker_ChildSendMsg { - mach_msg_header_t header; - mach_msg_body_t body; - mach_msg_port_descriptor_t child_task_port; -}; - -// Complement to the ChildSendMsg, this is used in the parent for receiving -// a message. Contains a message trailer with audit information. -struct MachPortBroker_ParentRecvMsg : public MachPortBroker_ChildSendMsg { - mach_msg_audit_trailer_t trailer; -}; - -} // namespace - -// static -bool MachPortBroker::ChildSendTaskPortToParent(const std::string& name) { - // Look up the named MachPortBroker port that's been registered with the - // bootstrap server. - mach_port_t parent_port; - kern_return_t kr = bootstrap_look_up(bootstrap_port, - const_cast<char*>(GetMachPortName(name, true).c_str()), &parent_port); - if (kr != KERN_SUCCESS) { - BOOTSTRAP_LOG(ERROR, kr) << "bootstrap_look_up"; - return false; - } - base::mac::ScopedMachSendRight scoped_right(parent_port); - - // Create the check in message. This will copy a send right on this process' - // (the child's) task port and send it to the parent. - MachPortBroker_ChildSendMsg msg; - bzero(&msg, sizeof(msg)); - msg.header.msgh_bits = MACH_MSGH_BITS_REMOTE(MACH_MSG_TYPE_COPY_SEND) | - MACH_MSGH_BITS_COMPLEX; - msg.header.msgh_remote_port = parent_port; - msg.header.msgh_size = sizeof(msg); - msg.body.msgh_descriptor_count = 1; - msg.child_task_port.name = mach_task_self(); - msg.child_task_port.disposition = MACH_MSG_TYPE_PORT_SEND; - msg.child_task_port.type = MACH_MSG_PORT_DESCRIPTOR; - - kr = mach_msg(&msg.header, MACH_SEND_MSG | MACH_SEND_TIMEOUT, sizeof(msg), - 0, MACH_PORT_NULL, 100 /*milliseconds*/, MACH_PORT_NULL); - if (kr != KERN_SUCCESS) { - MACH_LOG(ERROR, kr) << "mach_msg"; - return false; - } - - return true; -} - -// static -std::string MachPortBroker::GetMachPortName(const std::string& name, - bool is_child) { - // In child processes, use the parent's pid. - const pid_t pid = is_child ? getppid() : getpid(); - return base::StringPrintf( - "%s.%s.%d", base::mac::BaseBundleID(), name.c_str(), pid); -} - -mach_port_t MachPortBroker::TaskForPid(base::ProcessHandle pid) const { - base::AutoLock lock(lock_); - MachPortBroker::MachMap::const_iterator it = mach_map_.find(pid); - if (it == mach_map_.end()) - return MACH_PORT_NULL; - return it->second; -} - -MachPortBroker::MachPortBroker(const std::string& name) : name_(name) {} - -MachPortBroker::~MachPortBroker() {} - -bool MachPortBroker::Init() { - DCHECK(server_port_.get() == MACH_PORT_NULL); - - // Check in with launchd and publish the service name. - mach_port_t port; - kern_return_t kr = bootstrap_check_in( - bootstrap_port, GetMachPortName(name_, false).c_str(), &port); - if (kr != KERN_SUCCESS) { - BOOTSTRAP_LOG(ERROR, kr) << "bootstrap_check_in"; - return false; - } - server_port_.reset(port); - - // Start the dispatch source. - std::string queue_name = - base::StringPrintf("%s.MachPortBroker", base::mac::BaseBundleID()); - dispatch_source_.reset(new base::DispatchSourceMach( - queue_name.c_str(), server_port_.get(), ^{ HandleRequest(); })); - dispatch_source_->Resume(); - - return true; -} - -void MachPortBroker::AddPlaceholderForPid(base::ProcessHandle pid) { - lock_.AssertAcquired(); - DCHECK_EQ(0u, mach_map_.count(pid)); - mach_map_[pid] = MACH_PORT_NULL; -} - -void MachPortBroker::InvalidatePid(base::ProcessHandle pid) { - lock_.AssertAcquired(); - - MachMap::iterator mach_it = mach_map_.find(pid); - if (mach_it != mach_map_.end()) { - kern_return_t kr = mach_port_deallocate(mach_task_self(), mach_it->second); - MACH_LOG_IF(WARNING, kr != KERN_SUCCESS, kr) << "mach_port_deallocate"; - mach_map_.erase(mach_it); - } -} - -void MachPortBroker::HandleRequest() { - MachPortBroker_ParentRecvMsg msg; - bzero(&msg, sizeof(msg)); - msg.header.msgh_size = sizeof(msg); - msg.header.msgh_local_port = server_port_.get(); - - const mach_msg_option_t options = MACH_RCV_MSG | - MACH_RCV_TRAILER_TYPE(MACH_RCV_TRAILER_AUDIT) | - MACH_RCV_TRAILER_ELEMENTS(MACH_RCV_TRAILER_AUDIT); - - kern_return_t kr = mach_msg(&msg.header, - options, - 0, - sizeof(msg), - server_port_.get(), - MACH_MSG_TIMEOUT_NONE, - MACH_PORT_NULL); - if (kr != KERN_SUCCESS) { - MACH_LOG(ERROR, kr) << "mach_msg"; - return; - } - - // Use the kernel audit information to make sure this message is from - // a task that this process spawned. The kernel audit token contains the - // unspoofable pid of the task that sent the message. - pid_t child_pid = audit_token_to_pid(msg.trailer.msgh_audit); - mach_port_t child_task_port = msg.child_task_port.name; - - // Take the lock and update the broker information. - { - base::AutoLock lock(lock_); - FinalizePid(child_pid, child_task_port); - } - NotifyObservers(child_pid); -} - -void MachPortBroker::FinalizePid(base::ProcessHandle pid, - mach_port_t task_port) { - lock_.AssertAcquired(); - - MachMap::iterator it = mach_map_.find(pid); - if (it == mach_map_.end()) { - // Do nothing for unknown pids. - LOG(ERROR) << "Unknown process " << pid << " is sending Mach IPC messages!"; - return; - } - - DCHECK(it->second == MACH_PORT_NULL); - if (it->second == MACH_PORT_NULL) - it->second = task_port; -} - -} // namespace base
diff --git a/base/mac/mach_port_util.cc b/base/mac/mach_port_util.cc deleted file mode 100644 index 0eee210..0000000 --- a/base/mac/mach_port_util.cc +++ /dev/null
@@ -1,136 +0,0 @@ -// Copyright 2016 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/mac/mach_port_util.h" - -#include "base/logging.h" - -namespace base { - -namespace { - -// Struct for sending a complex Mach message. -struct MachSendComplexMessage { - mach_msg_header_t header; - mach_msg_body_t body; - mach_msg_port_descriptor_t data; -}; - -// Struct for receiving a complex message. -struct MachReceiveComplexMessage { - mach_msg_header_t header; - mach_msg_body_t body; - mach_msg_port_descriptor_t data; - mach_msg_trailer_t trailer; -}; - -} // namespace - -kern_return_t SendMachPort(mach_port_t endpoint, - mach_port_t port_to_send, - int disposition) { - MachSendComplexMessage send_msg; - send_msg.header.msgh_bits = - MACH_MSGH_BITS(MACH_MSG_TYPE_MOVE_SEND_ONCE, 0) | MACH_MSGH_BITS_COMPLEX; - send_msg.header.msgh_size = sizeof(send_msg); - send_msg.header.msgh_remote_port = endpoint; - send_msg.header.msgh_local_port = MACH_PORT_NULL; - send_msg.header.msgh_reserved = 0; - send_msg.header.msgh_id = 0; - send_msg.body.msgh_descriptor_count = 1; - send_msg.data.name = port_to_send; - send_msg.data.disposition = disposition; - send_msg.data.type = MACH_MSG_PORT_DESCRIPTOR; - - kern_return_t kr = - mach_msg(&send_msg.header, MACH_SEND_MSG | MACH_SEND_TIMEOUT, - send_msg.header.msgh_size, - 0, // receive limit - MACH_PORT_NULL, // receive name - 0, // timeout - MACH_PORT_NULL); // notification port - - if (kr != KERN_SUCCESS) - mach_port_deallocate(mach_task_self(), endpoint); - - return kr; -} - -base::mac::ScopedMachSendRight ReceiveMachPort(mach_port_t port_to_listen_on) { - MachReceiveComplexMessage recv_msg; - mach_msg_header_t* recv_hdr = &recv_msg.header; - recv_hdr->msgh_local_port = port_to_listen_on; - recv_hdr->msgh_size = sizeof(recv_msg); - - kern_return_t kr = - mach_msg(recv_hdr, MACH_RCV_MSG | MACH_RCV_TIMEOUT, 0, - recv_hdr->msgh_size, port_to_listen_on, 0, MACH_PORT_NULL); - if (kr != KERN_SUCCESS) - return base::mac::ScopedMachSendRight(MACH_PORT_NULL); - if (recv_msg.header.msgh_id != 0) - return base::mac::ScopedMachSendRight(MACH_PORT_NULL); - return base::mac::ScopedMachSendRight(recv_msg.data.name); -} - -mach_port_name_t CreateIntermediateMachPort( - mach_port_t task_port, - base::mac::ScopedMachSendRight port_to_insert, - MachCreateError* error_code) { - DCHECK_NE(mach_task_self(), task_port); - DCHECK_NE(static_cast<mach_port_name_t>(MACH_PORT_NULL), task_port); - - // Make a port with receive rights in the destination task. - mach_port_name_t endpoint; - kern_return_t kr = - mach_port_allocate(task_port, MACH_PORT_RIGHT_RECEIVE, &endpoint); - if (kr != KERN_SUCCESS) { - if (error_code) - *error_code = MachCreateError::ERROR_MAKE_RECEIVE_PORT; - return MACH_PORT_NULL; - } - - // Change its message queue limit so that it accepts one message. - mach_port_limits limits = {}; - limits.mpl_qlimit = 1; - kr = mach_port_set_attributes(task_port, endpoint, MACH_PORT_LIMITS_INFO, - reinterpret_cast<mach_port_info_t>(&limits), - MACH_PORT_LIMITS_INFO_COUNT); - if (kr != KERN_SUCCESS) { - if (error_code) - *error_code = MachCreateError::ERROR_SET_ATTRIBUTES; - mach_port_deallocate(task_port, endpoint); - return MACH_PORT_NULL; - } - - // Get a send right. - mach_port_t send_once_right; - mach_msg_type_name_t send_right_type; - kr = - mach_port_extract_right(task_port, endpoint, MACH_MSG_TYPE_MAKE_SEND_ONCE, - &send_once_right, &send_right_type); - if (kr != KERN_SUCCESS) { - if (error_code) - *error_code = MachCreateError::ERROR_EXTRACT_DEST_RIGHT; - mach_port_deallocate(task_port, endpoint); - return MACH_PORT_NULL; - } - DCHECK_EQ(static_cast<mach_msg_type_name_t>(MACH_MSG_TYPE_PORT_SEND_ONCE), - send_right_type); - - // This call takes ownership of |send_once_right|. - kr = base::SendMachPort( - send_once_right, port_to_insert.get(), MACH_MSG_TYPE_COPY_SEND); - if (kr != KERN_SUCCESS) { - if (error_code) - *error_code = MachCreateError::ERROR_SEND_MACH_PORT; - mach_port_deallocate(task_port, endpoint); - return MACH_PORT_NULL; - } - - // Endpoint is intentionally leaked into the destination task. An IPC must be - // sent to the destination task so that it can clean up this port. - return endpoint; -} - -} // namespace base
diff --git a/base/mac/mach_port_util.h b/base/mac/mach_port_util.h deleted file mode 100644 index f7a7f32..0000000 --- a/base/mac/mach_port_util.h +++ /dev/null
@@ -1,48 +0,0 @@ -// Copyright 2016 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_MACH_PORT_UTIL_H_ -#define BASE_MAC_MACH_PORT_UTIL_H_ - -#include <mach/mach.h> - -#include "base/base_export.h" -#include "base/mac/scoped_mach_port.h" - -namespace base { - -enum class MachCreateError { - ERROR_MAKE_RECEIVE_PORT, - ERROR_SET_ATTRIBUTES, - ERROR_EXTRACT_DEST_RIGHT, - ERROR_SEND_MACH_PORT, -}; - -// Sends a Mach port to |dest_port|. Assumes that |dest_port| is a send once -// right. Takes ownership of |dest_port|. -BASE_EXPORT kern_return_t SendMachPort(mach_port_t dest_port, - mach_port_t port_to_send, - int disposition); - -// Receives a Mach port from |port_to_listen_on|, which should have exactly one -// queued message. Returns |MACH_PORT_NULL| on any error. -BASE_EXPORT base::mac::ScopedMachSendRight ReceiveMachPort( - mach_port_t port_to_listen_on); - -// Creates an intermediate Mach port in |task_port| and sends |port_to_insert| -// as a mach_msg to the intermediate Mach port. -// |task_port| is the task port of another process. -// |port_to_insert| must be a send right in the current task's name space. -// Returns the intermediate port on success, and MACH_PORT_NULL on failure. -// On failure, |error_code| is set if not null. -// This method takes ownership of |port_to_insert|. On success, ownership is -// passed to the intermediate Mach port. -BASE_EXPORT mach_port_name_t CreateIntermediateMachPort( - mach_port_t task_port, - base::mac::ScopedMachSendRight port_to_insert, - MachCreateError* error_code); - -} // namespace base - -#endif // BASE_MAC_MACH_PORT_UTIL_H_
diff --git a/base/mac/objc_release_properties.h b/base/mac/objc_release_properties.h deleted file mode 100644 index d064cf9..0000000 --- a/base/mac/objc_release_properties.h +++ /dev/null
@@ -1,65 +0,0 @@ -// Copyright 2016 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#if defined(__has_feature) && __has_feature(objc_arc) -#error "ARC manages properties, so base::mac::ReleaseProperties isn't needed." -#endif - -#ifndef BASE_MAC_OBJC_RELEASE_PROPERTIES_H_ -#define BASE_MAC_OBJC_RELEASE_PROPERTIES_H_ - -#import <Foundation/Foundation.h> - -#include "base/base_export.h" - -// base::mac::ReleaseProperties(self) can be used in a class's -dealloc method -// to release all properties marked "retain" or "copy" and backed by instance -// variables. It only affects properties defined by the calling class, not -// sub/superclass properties. -// -// Example usage: -// -// @interface AllaysIBF : NSObject -// -// @property(retain, nonatomic) NSString* string; -// @property(copy, nonatomic) NSMutableDictionary* dictionary; -// @property(assign, nonatomic) IBFDelegate* delegate; -// -// @end // @interface AllaysIBF -// -// @implementation AllaysIBF -// -// - (void)dealloc { -// base::mac::ReleaseProperties(self); -// [super dealloc]; -// } -// -// @end // @implementation AllaysIBF -// -// self.string and self.dictionary will each be released, but self.delegate -// will not because it is marked "assign", not "retain" or "copy". -// -// Another approach would be to provide a base class to inherit from whose -// -dealloc walks the property lists of all subclasses to release their -// properties. Distant subclasses might not expect it and over-release their -// properties, so don't do that. - -namespace base { -namespace mac { - -namespace details { - -BASE_EXPORT void ReleaseProperties(id, Class); - -} // namespace details - -template <typename Self> -void ReleaseProperties(Self* self) { - details::ReleaseProperties(self, [Self class]); -} - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_OBJC_RELEASE_PROPERTIES_H_
diff --git a/base/mac/objc_release_properties.mm b/base/mac/objc_release_properties.mm deleted file mode 100644 index d0006cf..0000000 --- a/base/mac/objc_release_properties.mm +++ /dev/null
@@ -1,66 +0,0 @@ -// Copyright 2016 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/mac/objc_release_properties.h" - -#include <memory> - -#include <objc/runtime.h> - -#include "base/logging.h" -#include "base/memory/free_deleter.h" - -namespace { - -bool IsRetained(objc_property_t property) { - // The format of the string returned by property_getAttributes is documented - // at - // http://developer.apple.com/library/mac/#documentation/Cocoa/Conceptual/ObjCRuntimeGuide/Articles/ocrtPropertyIntrospection.html#//apple_ref/doc/uid/TP40008048-CH101-SW6 - const char* attribute = property_getAttributes(property); - while (attribute[0]) { - switch (attribute[0]) { - case 'C': // copy - case '&': // retain - return true; - } - do { - attribute++; - } while (attribute[0] && attribute[-1] != ','); - } - return false; -} - -id ValueOf(id obj, objc_property_t property) { - std::unique_ptr<char, base::FreeDeleter> ivar_name( - property_copyAttributeValue(property, "V")); // instance variable name - if (!ivar_name) - return nil; - id ivar_value = nil; - Ivar ivar = object_getInstanceVariable(obj, &*ivar_name, - reinterpret_cast<void**>(&ivar_value)); - DCHECK(ivar); - return ivar_value; -} - -} // namespace - -namespace base { -namespace mac { -namespace details { - -void ReleaseProperties(id self, Class cls) { - unsigned int property_count; - std::unique_ptr<objc_property_t[], base::FreeDeleter> properties( - class_copyPropertyList(cls, &property_count)); - for (size_t i = 0; i < property_count; ++i) { - objc_property_t property = properties[i]; - if (!IsRetained(property)) - continue; - [ValueOf(self, property) release]; - } -} - -} // namespace details -} // namespace mac -} // namespace base
diff --git a/base/mac/os_crash_dumps.cc b/base/mac/os_crash_dumps.cc deleted file mode 100644 index 95af009..0000000 --- a/base/mac/os_crash_dumps.cc +++ /dev/null
@@ -1,61 +0,0 @@ -// Copyright (c) 2010 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/mac/os_crash_dumps.h" - -#include <signal.h> -#include <stddef.h> -#include <unistd.h> - -#include "base/logging.h" -#include "base/macros.h" - -namespace base { -namespace mac { - -namespace { - -void ExitSignalHandler(int sig) { - // A call to exit() can call atexit() handlers. If we SIGSEGV due - // to a corrupt heap, and if we have an atexit handler that - // allocates or frees memory, we are in trouble if we do not _exit. - _exit(128 + sig); -} - -} // namespace - -void DisableOSCrashDumps() { - // These are the POSIX signals corresponding to the Mach exceptions that - // Apple Crash Reporter handles. See ux_exception() in xnu's - // bsd/uxkern/ux_exception.c and machine_exception() in xnu's - // bsd/dev/*/unix_signal.c. - const int signals_to_intercept[] = { - // Hardware faults - SIGILL, // EXC_BAD_INSTRUCTION - SIGTRAP, // EXC_BREAKPOINT - SIGFPE, // EXC_ARITHMETIC - SIGBUS, // EXC_BAD_ACCESS - SIGSEGV, // EXC_BAD_ACCESS - // Not a hardware fault - SIGABRT - }; - - // For all these signals, just wire things up so we exit immediately. - for (size_t i = 0; i < arraysize(signals_to_intercept); ++i) { - struct sigaction act = {}; - act.sa_handler = ExitSignalHandler; - - // It is better to allow the signal handler to run on the stack - // registered with sigaltstack(), if one is present. - act.sa_flags = SA_ONSTACK; - - if (sigemptyset(&act.sa_mask) != 0) - DPLOG(FATAL) << "sigemptyset() failed"; - if (sigaction(signals_to_intercept[i], &act, NULL) != 0) - DPLOG(FATAL) << "sigaction() failed"; - } -} - -} // namespace mac -} // namespace base
diff --git a/base/mac/os_crash_dumps.h b/base/mac/os_crash_dumps.h deleted file mode 100644 index 31d90fb..0000000 --- a/base/mac/os_crash_dumps.h +++ /dev/null
@@ -1,22 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_OS_CRASH_DUMPS_H_ -#define BASE_MAC_OS_CRASH_DUMPS_H_ - -#include "base/base_export.h" - -namespace base { -namespace mac { - -// On Mac OS X, it can take a really long time for the OS crash handler to -// process a Chrome crash when debugging symbols are available. This -// translates into a long wait until the process actually dies. This call -// disables Apple Crash Reporter entirely. -BASE_EXPORT void DisableOSCrashDumps(); - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_OS_CRASH_DUMPS_H_
diff --git a/base/mac/scoped_aedesc.h b/base/mac/scoped_aedesc.h deleted file mode 100644 index 7327092..0000000 --- a/base/mac/scoped_aedesc.h +++ /dev/null
@@ -1,52 +0,0 @@ -// Copyright (c) 2010 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_SCOPED_AEDESC_H_ -#define BASE_MAC_SCOPED_AEDESC_H_ - -#import <CoreServices/CoreServices.h> - -#include "base/macros.h" - -namespace base { -namespace mac { - -// The ScopedAEDesc is used to scope AppleEvent descriptors. On creation, -// it will store a NULL descriptor. On destruction, it will dispose of the -// descriptor. -// -// This class is parameterized for additional type safety checks. You can use -// the generic AEDesc type by not providing a template parameter: -// ScopedAEDesc<> desc; -template <typename AEDescType = AEDesc> -class ScopedAEDesc { - public: - ScopedAEDesc() { - AECreateDesc(typeNull, NULL, 0, &desc_); - } - - ~ScopedAEDesc() { - AEDisposeDesc(&desc_); - } - - // Used for in parameters. - operator const AEDescType*() { - return &desc_; - } - - // Used for out parameters. - AEDescType* OutPointer() { - return &desc_; - } - - private: - AEDescType desc_; - - DISALLOW_COPY_AND_ASSIGN(ScopedAEDesc); -}; - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_SCOPED_AEDESC_H_
diff --git a/base/mac/scoped_authorizationref.h b/base/mac/scoped_authorizationref.h deleted file mode 100644 index b83f8df..0000000 --- a/base/mac/scoped_authorizationref.h +++ /dev/null
@@ -1,82 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_SCOPED_AUTHORIZATIONREF_H_ -#define BASE_MAC_SCOPED_AUTHORIZATIONREF_H_ - -#include <Security/Authorization.h> - -#include "base/compiler_specific.h" -#include "base/macros.h" - -// ScopedAuthorizationRef maintains ownership of an AuthorizationRef. It is -// patterned after the unique_ptr interface. - -namespace base { -namespace mac { - -class ScopedAuthorizationRef { - public: - explicit ScopedAuthorizationRef(AuthorizationRef authorization = NULL) - : authorization_(authorization) { - } - - ~ScopedAuthorizationRef() { - if (authorization_) { - AuthorizationFree(authorization_, kAuthorizationFlagDestroyRights); - } - } - - void reset(AuthorizationRef authorization = NULL) { - if (authorization_ != authorization) { - if (authorization_) { - AuthorizationFree(authorization_, kAuthorizationFlagDestroyRights); - } - authorization_ = authorization; - } - } - - bool operator==(AuthorizationRef that) const { - return authorization_ == that; - } - - bool operator!=(AuthorizationRef that) const { - return authorization_ != that; - } - - operator AuthorizationRef() const { - return authorization_; - } - - AuthorizationRef* get_pointer() { return &authorization_; } - - AuthorizationRef get() const { - return authorization_; - } - - void swap(ScopedAuthorizationRef& that) { - AuthorizationRef temp = that.authorization_; - that.authorization_ = authorization_; - authorization_ = temp; - } - - // ScopedAuthorizationRef::release() is like std::unique_ptr<>::release. It is - // NOT a wrapper for AuthorizationFree(). To force a ScopedAuthorizationRef - // object to call AuthorizationFree(), use ScopedAuthorizationRef::reset(). - AuthorizationRef release() WARN_UNUSED_RESULT { - AuthorizationRef temp = authorization_; - authorization_ = NULL; - return temp; - } - - private: - AuthorizationRef authorization_; - - DISALLOW_COPY_AND_ASSIGN(ScopedAuthorizationRef); -}; - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_SCOPED_AUTHORIZATIONREF_H_
diff --git a/base/mac/scoped_cffiledescriptorref.h b/base/mac/scoped_cffiledescriptorref.h deleted file mode 100644 index 923a159..0000000 --- a/base/mac/scoped_cffiledescriptorref.h +++ /dev/null
@@ -1,39 +0,0 @@ -// Copyright 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_SCOPED_CFFILEDESCRIPTORREF_H_ -#define BASE_MAC_SCOPED_CFFILEDESCRIPTORREF_H_ - -#include <CoreFoundation/CoreFoundation.h> - -#include "base/scoped_generic.h" - -namespace base { -namespace mac { - -namespace internal { - -struct ScopedCFFileDescriptorRefTraits { - static CFFileDescriptorRef InvalidValue() { return nullptr; } - static void Free(CFFileDescriptorRef ref) { - CFFileDescriptorInvalidate(ref); - CFRelease(ref); - } -}; - -} // namespace internal - -// ScopedCFFileDescriptorRef is designed after ScopedCFTypeRef<>. On -// destruction, it will invalidate the file descriptor. -// ScopedCFFileDescriptorRef (unlike ScopedCFTypeRef<>) does not support RETAIN -// semantics, copying, or assignment, as doing so would increase the chances -// that a file descriptor is invalidated while still in use. -using ScopedCFFileDescriptorRef = - ScopedGeneric<CFFileDescriptorRef, - internal::ScopedCFFileDescriptorRefTraits>; - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_SCOPED_CFFILEDESCRIPTORREF_H_
diff --git a/base/mac/scoped_ionotificationportref.h b/base/mac/scoped_ionotificationportref.h deleted file mode 100644 index 93ebc98..0000000 --- a/base/mac/scoped_ionotificationportref.h +++ /dev/null
@@ -1,33 +0,0 @@ -// Copyright 2016 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_SCOPED_IONOTIFICATIONPORTREF_H_ -#define BASE_MAC_SCOPED_IONOTIFICATIONPORTREF_H_ - -#include <IOKit/IOKitLib.h> - -#include "base/scoped_generic.h" - -namespace base { -namespace mac { - -namespace internal { - -struct ScopedIONotificationPortRefTraits { - static IONotificationPortRef InvalidValue() { return nullptr; } - static void Free(IONotificationPortRef object) { - IONotificationPortDestroy(object); - } -}; - -} // namepsace internal - -using ScopedIONotificationPortRef = - ScopedGeneric<IONotificationPortRef, - internal::ScopedIONotificationPortRefTraits>; - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_SCOPED_IONOTIFICATIONPORTREF_H_
diff --git a/base/mac/scoped_ioplugininterface.h b/base/mac/scoped_ioplugininterface.h deleted file mode 100644 index 872da8e..0000000 --- a/base/mac/scoped_ioplugininterface.h +++ /dev/null
@@ -1,38 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_SCOPED_IOPLUGININTERFACE_H_ -#define BASE_MAC_SCOPED_IOPLUGININTERFACE_H_ - -#include <IOKit/IOKitLib.h> - -#include "base/mac/scoped_typeref.h" - -namespace base { -namespace mac { - -namespace internal { - -template <typename T> -struct ScopedIOPluginInterfaceTraits { - static T InvalidValue() { return nullptr; } - static T Retain(T t) { - (*t)->AddRef(t); - return t; - } - static void Release(T t) { (*t)->Release(t); } -}; - -} // namespace internal - -// Just like ScopedCFTypeRef but for IOCFPlugInInterface and friends -// (IOUSBInterfaceStruct and IOUSBDeviceStruct320 in particular). -template <typename T> -using ScopedIOPluginInterface = - ScopedTypeRef<T**, internal::ScopedIOPluginInterfaceTraits<T**>>; - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_SCOPED_IOPLUGININTERFACE_H_
diff --git a/base/mac/scoped_launch_data.h b/base/mac/scoped_launch_data.h deleted file mode 100644 index f4db330..0000000 --- a/base/mac/scoped_launch_data.h +++ /dev/null
@@ -1,31 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_SCOPED_LAUNCH_DATA_H_ -#define BASE_MAC_SCOPED_LAUNCH_DATA_H_ - -#include <launch.h> - -#include "base/scoped_generic.h" - -namespace base { -namespace mac { - -namespace internal { - -struct ScopedLaunchDataTraits { - static launch_data_t InvalidValue() { return nullptr; } - static void Free(launch_data_t ldt) { launch_data_free(ldt); } -}; - -} // namespace internal - -// Just like std::unique_ptr<> but for launch_data_t. -using ScopedLaunchData = - ScopedGeneric<launch_data_t, internal::ScopedLaunchDataTraits>; - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_SCOPED_LAUNCH_DATA_H_
diff --git a/base/mac/scoped_mach_vm.cc b/base/mac/scoped_mach_vm.cc deleted file mode 100644 index d52c77f..0000000 --- a/base/mac/scoped_mach_vm.cc +++ /dev/null
@@ -1,33 +0,0 @@ -// Copyright 2014 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/mac/scoped_mach_vm.h" - -namespace base { -namespace mac { - -void ScopedMachVM::reset(vm_address_t address, vm_size_t size) { - DCHECK_EQ(address % PAGE_SIZE, 0u); - DCHECK_EQ(size % PAGE_SIZE, 0u); - - if (size_) { - if (address_ < address) { - vm_deallocate(mach_task_self(), - address_, - std::min(size_, address - address_)); - } - if (address_ + size_ > address + size) { - vm_address_t deallocate_start = std::max(address_, address + size); - vm_deallocate(mach_task_self(), - deallocate_start, - address_ + size_ - deallocate_start); - } - } - - address_ = address; - size_ = size; -} - -} // namespace mac -} // namespace base
diff --git a/base/mac/scoped_mach_vm.h b/base/mac/scoped_mach_vm.h deleted file mode 100644 index 58a13f6..0000000 --- a/base/mac/scoped_mach_vm.h +++ /dev/null
@@ -1,93 +0,0 @@ -// Copyright 2014 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_SCOPED_MACH_VM_H_ -#define BASE_MAC_SCOPED_MACH_VM_H_ - -#include <mach/mach.h> -#include <stddef.h> - -#include <algorithm> - -#include "base/base_export.h" -#include "base/logging.h" -#include "base/macros.h" - -// Use ScopedMachVM to supervise ownership of pages in the current process -// through the Mach VM subsystem. Pages allocated with vm_allocate can be -// released when exiting a scope with ScopedMachVM. -// -// The Mach VM subsystem operates on a page-by-page basis, and a single VM -// allocation managed by a ScopedMachVM object may span multiple pages. As far -// as Mach is concerned, allocated pages may be deallocated individually. This -// is in contrast to higher-level allocators such as malloc, where the base -// address of an allocation implies the size of an allocated block. -// Consequently, it is not sufficient to just pass the base address of an -// allocation to ScopedMachVM, it also needs to know the size of the -// allocation. To avoid any confusion, both the base address and size must -// be page-aligned. -// -// When dealing with Mach VM, base addresses will naturally be page-aligned, -// but user-specified sizes may not be. If there's a concern that a size is -// not page-aligned, use the mach_vm_round_page macro to correct it. -// -// Example: -// -// vm_address_t address = 0; -// vm_size_t size = 12345; // This requested size is not page-aligned. -// kern_return_t kr = -// vm_allocate(mach_task_self(), &address, size, VM_FLAGS_ANYWHERE); -// if (kr != KERN_SUCCESS) { -// return false; -// } -// ScopedMachVM vm_owner(address, mach_vm_round_page(size)); - -namespace base { -namespace mac { - -class BASE_EXPORT ScopedMachVM { - public: - explicit ScopedMachVM(vm_address_t address = 0, vm_size_t size = 0) - : address_(address), size_(size) { - DCHECK_EQ(address % PAGE_SIZE, 0u); - DCHECK_EQ(size % PAGE_SIZE, 0u); - } - - ~ScopedMachVM() { - if (size_) { - vm_deallocate(mach_task_self(), address_, size_); - } - } - - void reset(vm_address_t address = 0, vm_size_t size = 0); - - vm_address_t address() const { - return address_; - } - - vm_size_t size() const { - return size_; - } - - void swap(ScopedMachVM& that) { - std::swap(address_, that.address_); - std::swap(size_, that.size_); - } - - void release() { - address_ = 0; - size_ = 0; - } - - private: - vm_address_t address_; - vm_size_t size_; - - DISALLOW_COPY_AND_ASSIGN(ScopedMachVM); -}; - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_SCOPED_MACH_VM_H_
diff --git a/base/mac/scoped_objc_class_swizzler.h b/base/mac/scoped_objc_class_swizzler.h deleted file mode 100644 index e18e4ab..0000000 --- a/base/mac/scoped_objc_class_swizzler.h +++ /dev/null
@@ -1,49 +0,0 @@ -// Copyright 2014 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_SCOPED_OBJC_CLASS_SWIZZLER_H_ -#define BASE_MAC_SCOPED_OBJC_CLASS_SWIZZLER_H_ - -#import <objc/runtime.h> - -#include "base/base_export.h" -#include "base/macros.h" - -namespace base { -namespace mac { - -// Within a given scope, swaps method implementations of a class interface, or -// between two class interfaces. The argument and return types must match. -class BASE_EXPORT ScopedObjCClassSwizzler { - public: - // Given two classes that each respond to |selector|, swap the implementations - // of those methods. - ScopedObjCClassSwizzler(Class target, Class source, SEL selector); - - // Given two selectors on the same class interface, |target| (e.g. via - // inheritance or categories), swap the implementations of methods |original| - // and |alternate|. - ScopedObjCClassSwizzler(Class target, SEL original, SEL alternate); - - ~ScopedObjCClassSwizzler(); - - // Return a callable function pointer for the replaced method. To call this - // from the replacing function, the first two arguments should be |self| and - // |_cmd|. These are followed by the (variadic) method arguments. - IMP GetOriginalImplementation(); - - private: - // Delegated constructor. - void Init(Class target, Class source, SEL original, SEL alternate); - - Method old_selector_impl_; - Method new_selector_impl_; - - DISALLOW_COPY_AND_ASSIGN(ScopedObjCClassSwizzler); -}; - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_SCOPED_OBJC_CLASS_SWIZZLER_H_
diff --git a/base/mac/scoped_objc_class_swizzler.mm b/base/mac/scoped_objc_class_swizzler.mm deleted file mode 100644 index 20e5c56..0000000 --- a/base/mac/scoped_objc_class_swizzler.mm +++ /dev/null
@@ -1,71 +0,0 @@ -// Copyright 2014 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#import "base/mac/scoped_objc_class_swizzler.h" - -#include <string.h> - -#include "base/logging.h" - -namespace base { -namespace mac { - -ScopedObjCClassSwizzler::ScopedObjCClassSwizzler(Class target, - Class source, - SEL selector) - : old_selector_impl_(NULL), new_selector_impl_(NULL) { - Init(target, source, selector, selector); -} - -ScopedObjCClassSwizzler::ScopedObjCClassSwizzler(Class target, - SEL original, - SEL alternate) - : old_selector_impl_(NULL), new_selector_impl_(NULL) { - Init(target, target, original, alternate); -} - -ScopedObjCClassSwizzler::~ScopedObjCClassSwizzler() { - if (old_selector_impl_ && new_selector_impl_) - method_exchangeImplementations(old_selector_impl_, new_selector_impl_); -} - -IMP ScopedObjCClassSwizzler::GetOriginalImplementation() { - // Note that while the swizzle is in effect the "new" method is actually - // pointing to the original implementation, since they have been swapped. - return method_getImplementation(new_selector_impl_); -} - -void ScopedObjCClassSwizzler::Init(Class target, - Class source, - SEL original, - SEL alternate) { - old_selector_impl_ = class_getInstanceMethod(target, original); - new_selector_impl_ = class_getInstanceMethod(source, alternate); - if (!old_selector_impl_ && !new_selector_impl_) { - // Try class methods. - old_selector_impl_ = class_getClassMethod(target, original); - new_selector_impl_ = class_getClassMethod(source, alternate); - } - - DCHECK(old_selector_impl_); - DCHECK(new_selector_impl_); - if (!old_selector_impl_ || !new_selector_impl_) - return; - - // The argument and return types must match exactly. - const char* old_types = method_getTypeEncoding(old_selector_impl_); - const char* new_types = method_getTypeEncoding(new_selector_impl_); - DCHECK(old_types); - DCHECK(new_types); - DCHECK_EQ(0, strcmp(old_types, new_types)); - if (!old_types || !new_types || strcmp(old_types, new_types)) { - old_selector_impl_ = new_selector_impl_ = NULL; - return; - } - - method_exchangeImplementations(old_selector_impl_, new_selector_impl_); -} - -} // namespace mac -} // namespace base
diff --git a/base/mac/scoped_sending_event.h b/base/mac/scoped_sending_event.h deleted file mode 100644 index c579cef..0000000 --- a/base/mac/scoped_sending_event.h +++ /dev/null
@@ -1,48 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_MAC_SCOPED_SENDING_EVENT_H_ -#define BASE_MAC_SCOPED_SENDING_EVENT_H_ - -#include "base/base_export.h" -#include "base/macros.h" -#include "base/message_loop/message_pump_mac.h" - -// Nested event loops can pump IPC messages, including -// script-initiated tab closes, which could release objects that the -// nested event loop might message. CrAppProtocol defines how to ask -// the embedding NSApplication subclass if an event is currently being -// handled, in which case such closes are deferred to the top-level -// event loop. -// -// ScopedSendingEvent allows script-initiated event loops to work like -// a nested event loop, as such events do not arrive via -sendEvent:. -// CrAppControlProtocol lets ScopedSendingEvent tell the embedding -// NSApplication what to return from -handlingSendEvent. - -@protocol CrAppControlProtocol<CrAppProtocol> -- (void)setHandlingSendEvent:(BOOL)handlingSendEvent; -@end - -namespace base { -namespace mac { - -class BASE_EXPORT ScopedSendingEvent { - public: - ScopedSendingEvent(); - ~ScopedSendingEvent(); - - private: - // The NSApp in control at the time the constructor was run, to be - // sure the |handling_| setting is restored appropriately. - NSObject<CrAppControlProtocol>* app_; - BOOL handling_; // Value of -[app_ handlingSendEvent] at construction. - - DISALLOW_COPY_AND_ASSIGN(ScopedSendingEvent); -}; - -} // namespace mac -} // namespace base - -#endif // BASE_MAC_SCOPED_SENDING_EVENT_H_
diff --git a/base/mac/scoped_sending_event.mm b/base/mac/scoped_sending_event.mm deleted file mode 100644 index c3813d8..0000000 --- a/base/mac/scoped_sending_event.mm +++ /dev/null
@@ -1,24 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#import "base/mac/scoped_sending_event.h" - -#include "base/logging.h" - -namespace base { -namespace mac { - -ScopedSendingEvent::ScopedSendingEvent() - : app_(static_cast<NSObject<CrAppControlProtocol>*>(NSApp)) { - DCHECK([app_ conformsToProtocol:@protocol(CrAppControlProtocol)]); - handling_ = [app_ isHandlingSendEvent]; - [app_ setHandlingSendEvent:YES]; -} - -ScopedSendingEvent::~ScopedSendingEvent() { - [app_ setHandlingSendEvent:handling_]; -} - -} // namespace mac -} // namespace base
diff --git a/base/memory/ref_counted.cc b/base/memory/ref_counted.cc index c2d40ef..79ab853 100644 --- a/base/memory/ref_counted.cc +++ b/base/memory/ref_counted.cc
@@ -4,8 +4,6 @@ #include "base/memory/ref_counted.h" -#include "base/threading/thread_collision_warner.h" - namespace base { namespace subtle {
diff --git a/base/memory/ref_counted.h b/base/memory/ref_counted.h index 6466c19..5cb731c 100644 --- a/base/memory/ref_counted.h +++ b/base/memory/ref_counted.h
@@ -15,7 +15,6 @@ #include "base/logging.h" #include "base/macros.h" #include "base/memory/scoped_refptr.h" -#include "base/threading/thread_collision_warner.h" #include "build_config.h" namespace base {
diff --git a/base/numerics/OWNERS b/base/numerics/OWNERS deleted file mode 100644 index 5493fba..0000000 --- a/base/numerics/OWNERS +++ /dev/null
@@ -1,5 +0,0 @@ -jschuh@chromium.org -tsepez@chromium.org - - -# COMPONENT: Internals
diff --git a/base/numerics/README.md b/base/numerics/README.md deleted file mode 100644 index 896b124..0000000 --- a/base/numerics/README.md +++ /dev/null
@@ -1,409 +0,0 @@ -# `base/numerics` - -This directory contains a dependency-free, header-only library of templates -providing well-defined semantics for safely and performantly handling a variety -of numeric operations, including most common arithmetic operations and -conversions. - -The public API is broken out into the following header files: - -* `checked_math.h` contains the `CheckedNumeric` template class and helper - functions for performing arithmetic and conversion operations that detect - errors and boundary conditions (e.g. overflow, truncation, etc.). -* `clamped_math.h` contains the `ClampedNumeric` template class and - helper functions for performing fast, clamped (i.e. non-sticky saturating) - arithmetic operations and conversions. -* `safe_conversions.h` contains the `StrictNumeric` template class and - a collection of custom casting templates and helper functions for safely - converting between a range of numeric types. -* `safe_math.h` includes all of the previously mentioned headers. - -*** aside -**Note:** The `Numeric` template types implicitly convert from C numeric types -and `Numeric` templates that are convertable to an underlying C numeric type. -The conversion priority for `Numeric` type coercions is: - -* `StrictNumeric` coerces to `ClampedNumeric` and `CheckedNumeric` -* `ClampedNumeric` coerces to `CheckedNumeric` -*** - -[TOC] - -## Common patterns and use-cases - -The following covers the preferred style for the most common uses of this -library. Please don't cargo-cult from anywhere else. 😉 - -### Performing checked arithmetic conversions - -The `checked_cast` template converts between arbitrary arithmetic types, and is -used for cases where a conversion failure should result in program termination: - -```cpp -// Crash if signed_value is out of range for buff_size. -size_t buff_size = checked_cast<size_t>(signed_value); -``` - -### Performing saturated (clamped) arithmetic conversions - -The `saturated_cast` template converts between arbitrary arithmetic types, and -is used in cases where an out-of-bounds source value should be saturated to the -corresponding maximum or minimum of the destination type: - -```cpp -// Convert from float with saturation to INT_MAX, INT_MIN, or 0 for NaN. -int int_value = saturated_cast<int>(floating_point_value); -``` - -### Enforcing arithmetic conversions at compile-time - -The `strict_cast` enforces type restrictions at compile-time and results in -emitted code that is identical to a normal `static_cast`. However, a -`strict_cast` assignment will fail to compile if the destination type cannot -represent the full range of the source type: - -```cpp -// Throw a compiler error if byte_value is changed to an out-of-range-type. -int int_value = strict_cast<int>(byte_value); -``` - -You can also enforce these compile-time restrictions on function parameters by -using the `StrictNumeric` template: - -```cpp -// Throw a compiler error if the size argument cannot be represented by a -// size_t (e.g. passing an int will fail to compile). -bool AllocateBuffer(void** buffer, StrictCast<size_t> size); -``` - -### Comparing values between arbitrary arithmetic types - -Both the `StrictNumeric` and `ClampedNumeric` types provide well defined -comparisons between arbitrary arithmetic types. This allows you to perform -comparisons that are not legal or would trigger compiler warnings or errors -under the normal arithmetic promotion rules: - -```cpp -bool foo(unsigned value, int upper_bound) { - // Converting to StrictNumeric allows this comparison to work correctly. - if (MakeStrictNum(value) >= upper_bound) - return false; -``` - -*** note -**Warning:** Do not perform manual conversions using the comparison operators. -Instead, use the cast templates described in the previous sections, or the -constexpr template functions `IsValueInRangeForNumericType` and -`IsTypeInRangeForNumericType`, as these templates properly handle the full range -of corner cases and employ various optimizations. -*** - -### Calculating a buffer size (checked arithmetic) - -When making exact calculations—such as for buffer lengths—it's often necessary -to know when those calculations trigger an overflow, undefined behavior, or -other boundary conditions. The `CheckedNumeric` template does this by storing -a bit determining whether or not some arithmetic operation has occured that -would put the variable in an "invalid" state. Attempting to extract the value -from a variable in an invalid state will trigger a check/trap condition, that -by default will result in process termination. - -Here's an example of a buffer calculation using a `CheckedNumeric` type (note: -the AssignIfValid method will trigger a compile error if the result is ignored). - -```cpp -// Calculate the buffer size and detect if an overflow occurs. -size_t size; -if (!CheckAdd(kHeaderSize, CheckMul(count, kItemSize)).AssignIfValid(&size)) { - // Handle an overflow error... -} -``` - -### Calculating clamped coordinates (non-sticky saturating arithmetic) - -Certain classes of calculations—such as coordinate calculations—require -well-defined semantics that always produce a valid result on boundary -conditions. The `ClampedNumeric` template addresses this by providing -performant, non-sticky saturating arithmetic operations. - -Here's an example of using a `ClampedNumeric` to calculate an operation -insetting a rectangle. - -```cpp -// Use clamped arithmetic since inset calculations might overflow. -void Rect::Inset(int left, int top, int right, int bottom) { - origin_ += Vector2d(left, top); - set_width(ClampSub(width(), ClampAdd(left, right))); - set_height(ClampSub(height(), ClampAdd(top, bottom))); -} -``` - -*** note -The `ClampedNumeric` type is not "sticky", which means the saturation is not -retained across individual operations. As such, one arithmetic operation may -result in a saturated value, while the next operation may then "desaturate" -the value. Here's an example: - -```cpp -ClampedNumeric<int> value = INT_MAX; -++value; // value is still INT_MAX, due to saturation. ---value; // value is now (INT_MAX - 1), because saturation is not sticky. -``` - -*** - -## Conversion functions and StrictNumeric<> in safe_conversions.h - -This header includes a collection of helper `constexpr` templates for safely -performing a range of conversions, assignments, and tests. - -### Safe casting templates - -* `as_signed()` - Returns the supplied integral value as a signed type of - the same width. -* `as_unsigned()` - Returns the supplied integral value as an unsigned type - of the same width. -* `checked_cast<>()` - Analogous to `static_cast<>` for numeric types, except - that by default it will trigger a crash on an out-of-bounds conversion (e.g. - overflow, underflow, NaN to integral) or a compile error if the conversion - error can be detected at compile time. The crash handler can be overridden - to perform a behavior other than crashing. -* `saturated_cast<>()` - Analogous to `static_cast` for numeric types, except - that it returns a saturated result when the specified numeric conversion - would otherwise overflow or underflow. An NaN source returns 0 by - default, but can be overridden to return a different result. -* `strict_cast<>()` - Analogous to `static_cast` for numeric types, except - this causes a compile failure if the destination type is not large - enough to contain any value in the source type. It performs no runtime - checking and thus introduces no runtime overhead. - -### Other helper and conversion functions - -* `IsValueInRangeForNumericType<>()` - A convenience function that returns - true if the type supplied as the template parameter can represent the value - passed as an argument to the function. -* `IsTypeInRangeForNumericType<>()` - A convenience function that evaluates - entirely at compile-time and returns true if the destination type (first - template parameter) can represent the full range of the source type - (second template parameter). -* `IsValueNegative()` - A convenience function that will accept any - arithmetic type as an argument and will return whether the value is less - than zero. Unsigned types always return false. -* `SafeUnsignedAbs()` - Returns the absolute value of the supplied integer - parameter as an unsigned result (thus avoiding an overflow if the value - is the signed, two's complement minimum). - -### StrictNumeric<> - -`StrictNumeric<>` is a wrapper type that performs assignments and copies via -the `strict_cast` template, and can perform valid arithmetic comparisons -across any range of arithmetic types. `StrictNumeric` is the return type for -values extracted from a `CheckedNumeric` class instance. The raw numeric value -is extracted via `static_cast` to the underlying type or any type with -sufficient range to represent the underlying type. - -* `MakeStrictNum()` - Creates a new `StrictNumeric` from the underlying type - of the supplied arithmetic or StrictNumeric type. -* `SizeT` - Alias for `StrictNumeric<size_t>`. - -## CheckedNumeric<> in checked_math.h - -`CheckedNumeric<>` implements all the logic and operators for detecting integer -boundary conditions such as overflow, underflow, and invalid conversions. -The `CheckedNumeric` type implicitly converts from floating point and integer -data types, and contains overloads for basic arithmetic operations (i.e.: `+`, -`-`, `*`, `/` for all types and `%`, `<<`, `>>`, `&`, `|`, `^` for integers). -However, *the [variadic template functions -](#CheckedNumeric_in-checked_math_h-Non_member-helper-functions) -are the prefered API,* as they remove type ambiguities and help prevent a number -of common errors. The variadic functions can also be more performant, as they -eliminate redundant expressions that are unavoidable with the with the operator -overloads. (Ideally the compiler should optimize those away, but better to avoid -them in the first place.) - -Type promotions are a slightly modified version of the [standard C/C++ numeric -promotions -](http://en.cppreference.com/w/cpp/language/implicit_conversion#Numeric_promotions) -with the two differences being that *there is no default promotion to int* -and *bitwise logical operations always return an unsigned of the wider type.* - -### Members - -The unary negation, increment, and decrement operators are supported, along -with the following unary arithmetic methods, which return a new -`CheckedNumeric` as a result of the operation: - -* `Abs()` - Absolute value. -* `UnsignedAbs()` - Absolute value as an equal-width unsigned underlying type - (valid for only integral types). -* `Max()` - Returns whichever is greater of the current instance or argument. - The underlying return type is whichever has the greatest magnitude. -* `Min()` - Returns whichever is lowest of the current instance or argument. - The underlying return type is whichever has can represent the lowest - number in the smallest width (e.g. int8_t over unsigned, int over - int8_t, and float over int). - -The following are for converting `CheckedNumeric` instances: - -* `type` - The underlying numeric type. -* `AssignIfValid()` - Assigns the underlying value to the supplied - destination pointer if the value is currently valid and within the - range supported by the destination type. Returns true on success. -* `Cast<>()` - Instance method returning a `CheckedNumeric` derived from - casting the current instance to a `CheckedNumeric` of the supplied - destination type. - -*** aside -The following member functions return a `StrictNumeric`, which is valid for -comparison and assignment operations, but will trigger a compile failure on -attempts to assign to a type of insufficient range. The underlying value can -be extracted by an explicit `static_cast` to the underlying type or any type -with sufficient range to represent the underlying type. -*** - -* `IsValid()` - Returns true if the underlying numeric value is valid (i.e. - has not wrapped or saturated and is not the result of an invalid - conversion). -* `ValueOrDie()` - Returns the underlying value. If the state is not valid - this call will trigger a crash by default (but may be overridden by - supplying an alternate handler to the template). -* `ValueOrDefault()` - Returns the current value, or the supplied default if - the state is not valid (but will not crash). - -**Comparison operators are explicitly not provided** for `CheckedNumeric` -types because they could result in a crash if the type is not in a valid state. -Patterns like the following should be used instead: - -```cpp -// Either input or padding (or both) may be arbitrary sizes. -size_t buff_size; -if (!CheckAdd(input, padding, kHeaderLength).AssignIfValid(&buff_size) || - buff_size >= kMaxBuffer) { - // Handle an error... -} else { - // Do stuff on success... -} -``` - -### Non-member helper functions - -The following variadic convenience functions, which accept standard arithmetic -or `CheckedNumeric` types, perform arithmetic operations, and return a -`CheckedNumeric` result. The supported functions are: - -* `CheckAdd()` - Addition. -* `CheckSub()` - Subtraction. -* `CheckMul()` - Multiplication. -* `CheckDiv()` - Division. -* `CheckMod()` - Modulus (integer only). -* `CheckLsh()` - Left integer shift (integer only). -* `CheckRsh()` - Right integer shift (integer only). -* `CheckAnd()` - Bitwise AND (integer only with unsigned result). -* `CheckOr()` - Bitwise OR (integer only with unsigned result). -* `CheckXor()` - Bitwise XOR (integer only with unsigned result). -* `CheckMax()` - Maximum of supplied arguments. -* `CheckMin()` - Minimum of supplied arguments. - -The following wrapper functions can be used to avoid the template -disambiguator syntax when converting a destination type. - -* `IsValidForType<>()` in place of: `a.template IsValid<>()` -* `ValueOrDieForType<>()` in place of: `a.template ValueOrDie<>()` -* `ValueOrDefaultForType<>()` in place of: `a.template ValueOrDefault<>()` - -The following general utility methods is are useful for converting from -arithmetic types to `CheckedNumeric` types: - -* `MakeCheckedNum()` - Creates a new `CheckedNumeric` from the underlying type - of the supplied arithmetic or directly convertible type. - -## ClampedNumeric<> in clamped_math.h - -`ClampedNumeric<>` implements all the logic and operators for clamped -(non-sticky saturating) arithmetic operations and conversions. The -`ClampedNumeric` type implicitly converts back and forth between floating point -and integer data types, saturating on assignment as appropriate. It contains -overloads for basic arithmetic operations (i.e.: `+`, `-`, `*`, `/` for -all types and `%`, `<<`, `>>`, `&`, `|`, `^` for integers) along with comparison -operators for arithmetic types of any size. However, *the [variadic template -functions -](#ClampedNumeric_in-clamped_math_h-Non_member-helper-functions) -are the prefered API,* as they remove type ambiguities and help prevent -a number of common errors. The variadic functions can also be more performant, -as they eliminate redundant expressions that are unavoidable with the operator -overloads. (Ideally the compiler should optimize those away, but better to avoid -them in the first place.) - -Type promotions are a slightly modified version of the [standard C/C++ numeric -promotions -](http://en.cppreference.com/w/cpp/language/implicit_conversion#Numeric_promotions) -with the two differences being that *there is no default promotion to int* -and *bitwise logical operations always return an unsigned of the wider type.* - -*** aside -Most arithmetic operations saturate normally, to the numeric limit in the -direction of the sign. The potentially unusual cases are: - -* **Division:** Division by zero returns the saturated limit in the direction - of sign of the dividend (first argument). The one exception is 0/0, which - returns zero (although logically is NaN). -* **Modulus:** Division by zero returns the dividend (first argument). -* **Left shift:** Non-zero values saturate in the direction of the signed - limit (max/min), even for shifts larger than the bit width. 0 shifted any - amount results in 0. -* **Right shift:** Negative values saturate to -1. Positive or 0 saturates - to 0. (Effectively just an unbounded arithmetic-right-shift.) -* **Bitwise operations:** No saturation; bit pattern is identical to - non-saturated bitwise operations. -*** - -### Members - -The unary negation, increment, and decrement operators are supported, along -with the following unary arithmetic methods, which return a new -`ClampedNumeric` as a result of the operation: - -* `Abs()` - Absolute value. -* `UnsignedAbs()` - Absolute value as an equal-width unsigned underlying type - (valid for only integral types). -* `Max()` - Returns whichever is greater of the current instance or argument. - The underlying return type is whichever has the greatest magnitude. -* `Min()` - Returns whichever is lowest of the current instance or argument. - The underlying return type is whichever has can represent the lowest - number in the smallest width (e.g. int8_t over unsigned, int over - int8_t, and float over int). - -The following are for converting `ClampedNumeric` instances: - -* `type` - The underlying numeric type. -* `RawValue()` - Returns the raw value as the underlying arithmetic type. This - is useful when e.g. assigning to an auto type or passing as a deduced - template parameter. -* `Cast<>()` - Instance method returning a `ClampedNumeric` derived from - casting the current instance to a `ClampedNumeric` of the supplied - destination type. - -### Non-member helper functions - -The following variadic convenience functions, which accept standard arithmetic -or `ClampedNumeric` types, perform arithmetic operations, and return a -`ClampedNumeric` result. The supported functions are: - -* `ClampAdd()` - Addition. -* `ClampSub()` - Subtraction. -* `ClampMul()` - Multiplication. -* `ClampDiv()` - Division. -* `ClampMod()` - Modulus (integer only). -* `ClampLsh()` - Left integer shift (integer only). -* `ClampRsh()` - Right integer shift (integer only). -* `ClampAnd()` - Bitwise AND (integer only with unsigned result). -* `ClampOr()` - Bitwise OR (integer only with unsigned result). -* `ClampXor()` - Bitwise XOR (integer only with unsigned result). -* `ClampMax()` - Maximum of supplied arguments. -* `ClampMin()` - Minimum of supplied arguments. - -The following is a general utility method that is useful for converting -to a `ClampedNumeric` type: - -* `MakeClampedNum()` - Creates a new `ClampedNumeric` from the underlying type - of the supplied arithmetic or directly convertible type.
diff --git a/base/observer_list.h b/base/observer_list.h deleted file mode 100644 index e900e43..0000000 --- a/base/observer_list.h +++ /dev/null
@@ -1,307 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_OBSERVER_LIST_H_ -#define BASE_OBSERVER_LIST_H_ - -#include <stddef.h> - -#include <algorithm> -#include <iterator> -#include <limits> -#include <utility> -#include <vector> - -#include "base/gtest_prod_util.h" -#include "base/logging.h" -#include "base/macros.h" -#include "base/memory/weak_ptr.h" -#include "base/stl_util.h" - -/////////////////////////////////////////////////////////////////////////////// -// -// OVERVIEW: -// -// A list of observers. Unlike a standard vector or list, this container can -// be modified during iteration without invalidating the iterator. So, it -// safely handles the case of an observer removing itself or other observers -// from the list while observers are being notified. -// -// -// WARNING: -// -// ObserverList is not thread-compatible. Iterating on the same ObserverList -// simultaneously in different threads is not safe, even when the ObserverList -// itself is not modified. -// -// For a thread-safe observer list, see ObserverListThreadSafe. -// -// -// TYPICAL USAGE: -// -// class MyWidget { -// public: -// ... -// -// class Observer { -// public: -// virtual void OnFoo(MyWidget* w) = 0; -// virtual void OnBar(MyWidget* w, int x, int y) = 0; -// }; -// -// void AddObserver(Observer* obs) { -// observers_.AddObserver(obs); -// } -// -// void RemoveObserver(const Observer* obs) { -// observers_.RemoveObserver(obs); -// } -// -// void NotifyFoo() { -// for (Observer& obs : observers_) -// obs.OnFoo(this); -// } -// -// void NotifyBar(int x, int y) { -// for (Observer& obs : observers_) -// obs.OnBar(this, x, y); -// } -// -// private: -// base::ObserverList<Observer> observers_; -// }; -// -// -/////////////////////////////////////////////////////////////////////////////// - -namespace base { - -// Enumeration of which observers are notified by ObserverList. -enum class ObserverListPolicy { - // Specifies that any observers added during notification are notified. - // This is the default policy if no policy is provided to the constructor. - ALL, - - // Specifies that observers added while sending out notification are not - // notified. - EXISTING_ONLY, -}; - -// When check_empty is true, assert that the list is empty on destruction. -// When allow_reentrancy is false, iterating throught the list while already in -// the iteration loop will result in DCHECK failure. -// TODO(oshima): Change the default to non reentrant. https://crbug.com/812109 -template <class ObserverType, - bool check_empty = false, - bool allow_reentrancy = true> -class ObserverList - : public SupportsWeakPtr< - ObserverList<ObserverType, check_empty, allow_reentrancy>> { - public: - // An iterator class that can be used to access the list of observers. - class Iter { - public: - using iterator_category = std::forward_iterator_tag; - using value_type = ObserverType; - using difference_type = ptrdiff_t; - using pointer = ObserverType*; - using reference = ObserverType&; - - Iter() : index_(0), max_index_(0) {} - - explicit Iter(const ObserverList* list) - : list_(const_cast<ObserverList*>(list)->AsWeakPtr()), - index_(0), - max_index_(list->policy_ == ObserverListPolicy::ALL - ? std::numeric_limits<size_t>::max() - : list->observers_.size()) { - DCHECK(list_); - DCHECK(allow_reentrancy || !list_->live_iterator_count_); - EnsureValidIndex(); - ++list_->live_iterator_count_; - } - - ~Iter() { - if (!list_) - return; - - DCHECK_GT(list_->live_iterator_count_, 0); - if (--list_->live_iterator_count_ == 0) - list_->Compact(); - } - - Iter(const Iter& other) - : list_(other.list_), - index_(other.index_), - max_index_(other.max_index_) { - if (list_) - ++list_->live_iterator_count_; - } - - Iter& operator=(Iter other) { - using std::swap; - swap(list_, other.list_); - swap(index_, other.index_); - swap(max_index_, other.max_index_); - return *this; - } - - bool operator==(const Iter& other) const { - return (is_end() && other.is_end()) || - (list_.get() == other.list_.get() && index_ == other.index_); - } - - bool operator!=(const Iter& other) const { return !(*this == other); } - - Iter& operator++() { - if (list_) { - ++index_; - EnsureValidIndex(); - } - return *this; - } - - Iter operator++(int) { - Iter it(*this); - ++(*this); - return it; - } - - ObserverType* operator->() const { - ObserverType* const current = GetCurrent(); - DCHECK(current); - return current; - } - - ObserverType& operator*() const { - ObserverType* const current = GetCurrent(); - DCHECK(current); - return *current; - } - - private: - FRIEND_TEST_ALL_PREFIXES(ObserverListTest, BasicStdIterator); - FRIEND_TEST_ALL_PREFIXES(ObserverListTest, StdIteratorRemoveFront); - - ObserverType* GetCurrent() const { - DCHECK(list_); - DCHECK_LT(index_, clamped_max_index()); - return list_->observers_[index_]; - } - - void EnsureValidIndex() { - DCHECK(list_); - const size_t max_index = clamped_max_index(); - while (index_ < max_index && !list_->observers_[index_]) - ++index_; - } - - size_t clamped_max_index() const { - return std::min(max_index_, list_->observers_.size()); - } - - bool is_end() const { return !list_ || index_ == clamped_max_index(); } - - WeakPtr<ObserverList> list_; - - // When initially constructed and each time the iterator is incremented, - // |index_| is guaranteed to point to a non-null index if the iterator - // has not reached the end of the ObserverList. - size_t index_; - size_t max_index_; - }; - - using iterator = Iter; - using const_iterator = Iter; - - const_iterator begin() const { - // An optimization: do not involve weak pointers for empty list. - return observers_.empty() ? const_iterator() : const_iterator(this); - } - - const_iterator end() const { return const_iterator(); } - - ObserverList() = default; - explicit ObserverList(ObserverListPolicy policy) : policy_(policy) {} - - ~ObserverList() { - if (check_empty) { - Compact(); - DCHECK(observers_.empty()); - } - } - - // Add an observer to this list. An observer should not be added to the same - // list more than once. - // - // Precondition: obs != nullptr - // Precondition: !HasObserver(obs) - void AddObserver(ObserverType* obs) { - DCHECK(obs); - if (HasObserver(obs)) { - NOTREACHED() << "Observers can only be added once!"; - return; - } - observers_.push_back(obs); - } - - // Removes the given observer from this list. Does nothing if this observer is - // not in this list. - void RemoveObserver(const ObserverType* obs) { - DCHECK(obs); - const auto it = std::find(observers_.begin(), observers_.end(), obs); - if (it == observers_.end()) - return; - - DCHECK_GE(live_iterator_count_, 0); - if (live_iterator_count_) { - *it = nullptr; - } else { - observers_.erase(it); - } - } - - // Determine whether a particular observer is in the list. - bool HasObserver(const ObserverType* obs) const { - return ContainsValue(observers_, obs); - } - - // Removes all the observers from this list. - void Clear() { - DCHECK_GE(live_iterator_count_, 0); - if (live_iterator_count_) { - std::fill(observers_.begin(), observers_.end(), nullptr); - } else { - observers_.clear(); - } - } - - bool might_have_observers() const { return !observers_.empty(); } - - private: - // Compacts list of observers by removing null pointers. - void Compact() { - observers_.erase(std::remove(observers_.begin(), observers_.end(), nullptr), - observers_.end()); - } - - std::vector<ObserverType*> observers_; - - // Number of active iterators referencing this ObserverList. - // - // This counter is not synchronized although it is modified by const - // iterators. - int live_iterator_count_ = 0; - - const ObserverListPolicy policy_ = ObserverListPolicy::ALL; - - DISALLOW_COPY_AND_ASSIGN(ObserverList); -}; - -template <class ObserverType, bool check_empty = false> -using ReentrantObserverList = ObserverList<ObserverType, check_empty, true>; - -} // namespace base - -#endif // BASE_OBSERVER_LIST_H_
diff --git a/base/observer_list_threadsafe.h b/base/observer_list_threadsafe.h deleted file mode 100644 index 05b5a56..0000000 --- a/base/observer_list_threadsafe.h +++ /dev/null
@@ -1,237 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_OBSERVER_LIST_THREADSAFE_H_ -#define BASE_OBSERVER_LIST_THREADSAFE_H_ - -#include <unordered_map> - -#include "base/base_export.h" -#include "base/bind.h" -#include "base/lazy_instance.h" -#include "base/location.h" -#include "base/logging.h" -#include "base/macros.h" -#include "base/memory/ref_counted.h" -#include "base/observer_list.h" -#include "base/sequenced_task_runner.h" -#include "base/stl_util.h" -#include "base/synchronization/lock.h" -#include "base/threading/sequenced_task_runner_handle.h" -#include "base/threading/thread_local.h" -#include "build_config.h" - -// TODO(fdoray): Removing these includes causes IWYU failures in other headers, -// remove them in a follow- up CL. -#include "base/memory/ptr_util.h" -#include "base/single_thread_task_runner.h" -#include "base/threading/thread_task_runner_handle.h" - -/////////////////////////////////////////////////////////////////////////////// -// -// OVERVIEW: -// -// A thread-safe container for a list of observers. This is similar to the -// observer_list (see observer_list.h), but it is more robust for multi- -// threaded situations. -// -// The following use cases are supported: -// * Observers can register for notifications from any sequence. They are -// always notified on the sequence from which they were registered. -// * Any sequence may trigger a notification via Notify(). -// * Observers can remove themselves from the observer list inside of a -// callback. -// * If one sequence is notifying observers concurrently with an observer -// removing itself from the observer list, the notifications will be -// silently dropped. -// -// The drawback of the threadsafe observer list is that notifications are not -// as real-time as the non-threadsafe version of this class. Notifications -// will always be done via PostTask() to another sequence, whereas with the -// non-thread-safe observer_list, notifications happen synchronously. -// -/////////////////////////////////////////////////////////////////////////////// - -namespace base { -namespace internal { - -class BASE_EXPORT ObserverListThreadSafeBase - : public RefCountedThreadSafe<ObserverListThreadSafeBase> { - public: - ObserverListThreadSafeBase() = default; - - protected: - template <typename ObserverType, typename Method> - struct Dispatcher; - - template <typename ObserverType, typename ReceiverType, typename... Params> - struct Dispatcher<ObserverType, void (ReceiverType::*)(Params...)> { - static void Run(void (ReceiverType::*m)(Params...), - Params... params, - ObserverType* obj) { - (obj->*m)(std::forward<Params>(params)...); - } - }; - - struct NotificationDataBase { - NotificationDataBase(void* observer_list_in, const Location& from_here_in) - : observer_list(observer_list_in), from_here(from_here_in) {} - - void* observer_list; - Location from_here; - }; - - virtual ~ObserverListThreadSafeBase() = default; - - static LazyInstance<ThreadLocalPointer<const NotificationDataBase>>::Leaky - tls_current_notification_; - - private: - friend class RefCountedThreadSafe<ObserverListThreadSafeBase>; - - DISALLOW_COPY_AND_ASSIGN(ObserverListThreadSafeBase); -}; - -} // namespace internal - -template <class ObserverType> -class ObserverListThreadSafe : public internal::ObserverListThreadSafeBase { - public: - ObserverListThreadSafe() = default; - explicit ObserverListThreadSafe(ObserverListPolicy policy) - : policy_(policy) {} - - // Adds |observer| to the list. |observer| must not already be in the list. - void AddObserver(ObserverType* observer) { - // TODO(fdoray): Change this to a DCHECK once all call sites have a - // SequencedTaskRunnerHandle. - if (!SequencedTaskRunnerHandle::IsSet()) - return; - - AutoLock auto_lock(lock_); - - // Add |observer| to the list of observers. - DCHECK(!ContainsKey(observers_, observer)); - const scoped_refptr<SequencedTaskRunner> task_runner = - SequencedTaskRunnerHandle::Get(); - observers_[observer] = task_runner; - - // If this is called while a notification is being dispatched on this thread - // and |policy_| is ALL, |observer| must be notified (if a notification is - // being dispatched on another thread in parallel, the notification may or - // may not make it to |observer| depending on the outcome of the race to - // |lock_|). - if (policy_ == ObserverListPolicy::ALL) { - const NotificationDataBase* current_notification = - tls_current_notification_.Get().Get(); - if (current_notification && current_notification->observer_list == this) { - task_runner->PostTask( - current_notification->from_here, - BindOnce( - &ObserverListThreadSafe<ObserverType>::NotifyWrapper, this, - observer, - *static_cast<const NotificationData*>(current_notification))); - } - } - } - - // Remove an observer from the list if it is in the list. - // - // If a notification was sent to the observer but hasn't started to run yet, - // it will be aborted. If a notification has started to run, removing the - // observer won't stop it. - void RemoveObserver(ObserverType* observer) { - AutoLock auto_lock(lock_); - observers_.erase(observer); - } - - // Verifies that the list is currently empty (i.e. there are no observers). - void AssertEmpty() const { -#if DCHECK_IS_ON() - AutoLock auto_lock(lock_); - DCHECK(observers_.empty()); -#endif - } - - // Asynchronously invokes a callback on all observers, on their registration - // sequence. You cannot assume that at the completion of the Notify call that - // all Observers have been Notified. The notification may still be pending - // delivery. - template <typename Method, typename... Params> - void Notify(const Location& from_here, Method m, Params&&... params) { - Callback<void(ObserverType*)> method = - Bind(&Dispatcher<ObserverType, Method>::Run, m, - std::forward<Params>(params)...); - - AutoLock lock(lock_); - for (const auto& observer : observers_) { - observer.second->PostTask( - from_here, - BindOnce(&ObserverListThreadSafe<ObserverType>::NotifyWrapper, this, - observer.first, NotificationData(this, from_here, method))); - } - } - - private: - friend class RefCountedThreadSafe<ObserverListThreadSafeBase>; - - struct NotificationData : public NotificationDataBase { - NotificationData(ObserverListThreadSafe* observer_list_in, - const Location& from_here_in, - const Callback<void(ObserverType*)>& method_in) - : NotificationDataBase(observer_list_in, from_here_in), - method(method_in) {} - - Callback<void(ObserverType*)> method; - }; - - ~ObserverListThreadSafe() override = default; - - void NotifyWrapper(ObserverType* observer, - const NotificationData& notification) { - { - AutoLock auto_lock(lock_); - - // Check whether the observer still needs a notification. - auto it = observers_.find(observer); - if (it == observers_.end()) - return; - DCHECK(it->second->RunsTasksInCurrentSequence()); - } - - // Keep track of the notification being dispatched on the current thread. - // This will be used if the callback below calls AddObserver(). - // - // Note: |tls_current_notification_| may not be nullptr if this runs in a - // nested loop started by a notification callback. In that case, it is - // important to save the previous value to restore it later. - auto& tls_current_notification = tls_current_notification_.Get(); - const NotificationDataBase* const previous_notification = - tls_current_notification.Get(); - tls_current_notification.Set(¬ification); - - // Invoke the callback. - notification.method.Run(observer); - - // Reset the notification being dispatched on the current thread to its - // previous value. - tls_current_notification.Set(previous_notification); - } - - const ObserverListPolicy policy_ = ObserverListPolicy::ALL; - - // Synchronizes access to |observers_|. - mutable Lock lock_; - - // Keys are observers. Values are the SequencedTaskRunners on which they must - // be notified. - std::unordered_map<ObserverType*, scoped_refptr<SequencedTaskRunner>> - observers_; - - DISALLOW_COPY_AND_ASSIGN(ObserverListThreadSafe); -}; - -} // namespace base - -#endif // BASE_OBSERVER_LIST_THREADSAFE_H_
diff --git a/base/posix/unix_domain_socket.cc b/base/posix/unix_domain_socket.cc deleted file mode 100644 index 17c8a24..0000000 --- a/base/posix/unix_domain_socket.cc +++ /dev/null
@@ -1,288 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/posix/unix_domain_socket.h" - -#include <errno.h> -#include <sys/socket.h> -#if !defined(OS_NACL_NONSFI) -#include <sys/un.h> -#endif -#include <unistd.h> - -#include <vector> - -#include "base/files/scoped_file.h" -#include "base/logging.h" -#include "base/pickle.h" -#include "base/posix/eintr_wrapper.h" -#include "base/stl_util.h" -#include "build_config.h" - -#if !defined(OS_NACL_NONSFI) -#include <sys/uio.h> -#endif - -namespace base { - -const size_t UnixDomainSocket::kMaxFileDescriptors = 16; - -#if !defined(OS_NACL_NONSFI) -bool CreateSocketPair(ScopedFD* one, ScopedFD* two) { - int raw_socks[2]; -#if defined(OS_MACOSX) - // macOS does not support SEQPACKET. - const int flags = SOCK_STREAM; -#else - const int flags = SOCK_SEQPACKET; -#endif - if (socketpair(AF_UNIX, flags, 0, raw_socks) == -1) - return false; -#if defined(OS_MACOSX) - // On macOS, preventing SIGPIPE is done with socket option. - const int no_sigpipe = 1; - if (setsockopt(raw_socks[0], SOL_SOCKET, SO_NOSIGPIPE, &no_sigpipe, - sizeof(no_sigpipe)) != 0) - return false; - if (setsockopt(raw_socks[1], SOL_SOCKET, SO_NOSIGPIPE, &no_sigpipe, - sizeof(no_sigpipe)) != 0) - return false; -#endif - one->reset(raw_socks[0]); - two->reset(raw_socks[1]); - return true; -} - -// static -bool UnixDomainSocket::EnableReceiveProcessId(int fd) { -#if !defined(OS_MACOSX) - const int enable = 1; - return setsockopt(fd, SOL_SOCKET, SO_PASSCRED, &enable, sizeof(enable)) == 0; -#else - // SO_PASSCRED is not supported on macOS. - return true; -#endif // OS_MACOSX -} -#endif // !defined(OS_NACL_NONSFI) - -// static -bool UnixDomainSocket::SendMsg(int fd, - const void* buf, - size_t length, - const std::vector<int>& fds) { - struct msghdr msg = {}; - struct iovec iov = {const_cast<void*>(buf), length}; - msg.msg_iov = &iov; - msg.msg_iovlen = 1; - - char* control_buffer = nullptr; - if (fds.size()) { - const unsigned control_len = CMSG_SPACE(sizeof(int) * fds.size()); - control_buffer = new char[control_len]; - - struct cmsghdr* cmsg; - msg.msg_control = control_buffer; - msg.msg_controllen = control_len; - cmsg = CMSG_FIRSTHDR(&msg); - cmsg->cmsg_level = SOL_SOCKET; - cmsg->cmsg_type = SCM_RIGHTS; - cmsg->cmsg_len = CMSG_LEN(sizeof(int) * fds.size()); - memcpy(CMSG_DATA(cmsg), &fds[0], sizeof(int) * fds.size()); - msg.msg_controllen = cmsg->cmsg_len; - } - -// Avoid a SIGPIPE if the other end breaks the connection. -// Due to a bug in the Linux kernel (net/unix/af_unix.c) MSG_NOSIGNAL isn't -// regarded for SOCK_SEQPACKET in the AF_UNIX domain, but it is mandated by -// POSIX. On Mac MSG_NOSIGNAL is not supported, so we need to ensure that -// SO_NOSIGPIPE is set during socket creation. -#if defined(OS_MACOSX) - const int flags = 0; - int no_sigpipe = 0; - socklen_t no_sigpipe_len = sizeof(no_sigpipe); - DPCHECK(getsockopt(fd, SOL_SOCKET, SO_NOSIGPIPE, &no_sigpipe, - &no_sigpipe_len) == 0) - << "Failed ot get socket option."; - DCHECK(no_sigpipe) << "SO_NOSIGPIPE not set on the socket."; -#else - const int flags = MSG_NOSIGNAL; -#endif // OS_MACOSX - const ssize_t r = HANDLE_EINTR(sendmsg(fd, &msg, flags)); - const bool ret = static_cast<ssize_t>(length) == r; - delete[] control_buffer; - return ret; -} - -// static -ssize_t UnixDomainSocket::RecvMsg(int fd, - void* buf, - size_t length, - std::vector<ScopedFD>* fds) { - return UnixDomainSocket::RecvMsgWithPid(fd, buf, length, fds, nullptr); -} - -// static -ssize_t UnixDomainSocket::RecvMsgWithPid(int fd, - void* buf, - size_t length, - std::vector<ScopedFD>* fds, - ProcessId* pid) { - return UnixDomainSocket::RecvMsgWithFlags(fd, buf, length, 0, fds, pid); -} - -// static -ssize_t UnixDomainSocket::RecvMsgWithFlags(int fd, - void* buf, - size_t length, - int flags, - std::vector<ScopedFD>* fds, - ProcessId* out_pid) { - fds->clear(); - - struct msghdr msg = {}; - struct iovec iov = {buf, length}; - msg.msg_iov = &iov; - msg.msg_iovlen = 1; - - const size_t kControlBufferSize = - CMSG_SPACE(sizeof(int) * kMaxFileDescriptors) -#if !defined(OS_NACL_NONSFI) && !defined(OS_MACOSX) - // The PNaCl toolchain for Non-SFI binary build and macOS do not support - // ucred. macOS supports xucred, but this structure is insufficient. - + CMSG_SPACE(sizeof(struct ucred)) -#endif // OS_NACL_NONSFI or OS_MACOSX - ; - char control_buffer[kControlBufferSize]; - msg.msg_control = control_buffer; - msg.msg_controllen = sizeof(control_buffer); - - const ssize_t r = HANDLE_EINTR(recvmsg(fd, &msg, flags)); - if (r == -1) - return -1; - - int* wire_fds = nullptr; - unsigned wire_fds_len = 0; - ProcessId pid = -1; - - if (msg.msg_controllen > 0) { - struct cmsghdr* cmsg; - for (cmsg = CMSG_FIRSTHDR(&msg); cmsg; cmsg = CMSG_NXTHDR(&msg, cmsg)) { - const unsigned payload_len = cmsg->cmsg_len - CMSG_LEN(0); - if (cmsg->cmsg_level == SOL_SOCKET && cmsg->cmsg_type == SCM_RIGHTS) { - DCHECK_EQ(payload_len % sizeof(int), 0u); - DCHECK_EQ(wire_fds, static_cast<void*>(nullptr)); - wire_fds = reinterpret_cast<int*>(CMSG_DATA(cmsg)); - wire_fds_len = payload_len / sizeof(int); - } -#if !defined(OS_NACL_NONSFI) && !defined(OS_MACOSX) - // The PNaCl toolchain for Non-SFI binary build and macOS do not support - // SCM_CREDENTIALS. - if (cmsg->cmsg_level == SOL_SOCKET && - cmsg->cmsg_type == SCM_CREDENTIALS) { - DCHECK_EQ(payload_len, sizeof(struct ucred)); - DCHECK_EQ(pid, -1); - pid = reinterpret_cast<struct ucred*>(CMSG_DATA(cmsg))->pid; - } -#endif // !defined(OS_NACL_NONSFI) && !defined(OS_MACOSX) - } - } - - if (msg.msg_flags & MSG_TRUNC || msg.msg_flags & MSG_CTRUNC) { - if (msg.msg_flags & MSG_CTRUNC) { - // Extraordinary case, not caller fixable. Log something. - LOG(ERROR) << "recvmsg returned MSG_CTRUNC flag, buffer len is " - << msg.msg_controllen; - } - for (unsigned i = 0; i < wire_fds_len; ++i) - close(wire_fds[i]); - errno = EMSGSIZE; - return -1; - } - - if (wire_fds) { - for (unsigned i = 0; i < wire_fds_len; ++i) - fds->push_back(ScopedFD(wire_fds[i])); // TODO(mdempsky): emplace_back - } - - if (out_pid) { -#if defined(OS_MACOSX) - socklen_t pid_size = sizeof(pid); - if (getsockopt(fd, SOL_LOCAL, LOCAL_PEERPID, &pid, &pid_size) != 0) - pid = -1; -#else - // |pid| will legitimately be -1 if we read EOF, so only DCHECK if we - // actually received a message. Unfortunately, Linux allows sending zero - // length messages, which are indistinguishable from EOF, so this check - // has false negatives. - if (r > 0 || msg.msg_controllen > 0) - DCHECK_GE(pid, 0); -#endif - - *out_pid = pid; - } - - return r; -} - -#if !defined(OS_NACL_NONSFI) -// static -ssize_t UnixDomainSocket::SendRecvMsg(int fd, - uint8_t* reply, - unsigned max_reply_len, - int* result_fd, - const Pickle& request) { - return UnixDomainSocket::SendRecvMsgWithFlags(fd, reply, max_reply_len, - 0, /* recvmsg_flags */ - result_fd, request); -} - -// static -ssize_t UnixDomainSocket::SendRecvMsgWithFlags(int fd, - uint8_t* reply, - unsigned max_reply_len, - int recvmsg_flags, - int* result_fd, - const Pickle& request) { - // This socketpair is only used for the IPC and is cleaned up before - // returning. - ScopedFD recv_sock, send_sock; - if (!CreateSocketPair(&recv_sock, &send_sock)) - return -1; - - { - std::vector<int> send_fds; - send_fds.push_back(send_sock.get()); - if (!SendMsg(fd, request.data(), request.size(), send_fds)) - return -1; - } - - // Close the sending end of the socket right away so that if our peer closes - // it before sending a response (e.g., from exiting), RecvMsgWithFlags() will - // return EOF instead of hanging. - send_sock.reset(); - - std::vector<ScopedFD> recv_fds; - // When porting to OSX keep in mind it doesn't support MSG_NOSIGNAL, so the - // sender might get a SIGPIPE. - const ssize_t reply_len = RecvMsgWithFlags( - recv_sock.get(), reply, max_reply_len, recvmsg_flags, &recv_fds, nullptr); - recv_sock.reset(); - if (reply_len == -1) - return -1; - - // If we received more file descriptors than caller expected, then we treat - // that as an error. - if (recv_fds.size() > (result_fd != nullptr ? 1 : 0)) { - NOTREACHED(); - return -1; - } - - if (result_fd) - *result_fd = recv_fds.empty() ? -1 : recv_fds[0].release(); - - return reply_len; -} -#endif // !defined(OS_NACL_NONSFI) - -} // namespace base
diff --git a/base/posix/unix_domain_socket.h b/base/posix/unix_domain_socket.h deleted file mode 100644 index 0bbd064..0000000 --- a/base/posix/unix_domain_socket.h +++ /dev/null
@@ -1,111 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_POSIX_UNIX_DOMAIN_SOCKET_H_ -#define BASE_POSIX_UNIX_DOMAIN_SOCKET_H_ - -#include <stddef.h> -#include <stdint.h> -#include <sys/types.h> -#include <vector> - -#include "base/base_export.h" -#include "base/files/scoped_file.h" -#include "base/process/process_handle.h" -#include "build_config.h" - -namespace base { - -class Pickle; - -#if !defined(OS_NACL_NONSFI) -// Creates a connected pair of UNIX-domain SOCK_SEQPACKET sockets, and passes -// ownership of the newly allocated file descriptors to |one| and |two|. -// Returns true on success. -bool BASE_EXPORT CreateSocketPair(ScopedFD* one, ScopedFD* two); -#endif - -class BASE_EXPORT UnixDomainSocket { - public: - // Maximum number of file descriptors that can be read by RecvMsg(). - static const size_t kMaxFileDescriptors; - -#if !defined(OS_NACL_NONSFI) - // Use to enable receiving process IDs in RecvMsgWithPid. Should be called on - // the receiving socket (i.e., the socket passed to RecvMsgWithPid). Returns - // true if successful. - static bool EnableReceiveProcessId(int fd); -#endif // !defined(OS_NACL_NONSFI) - - // Use sendmsg to write the given msg and include a vector of file - // descriptors. Returns true if successful. - static bool SendMsg(int fd, - const void* msg, - size_t length, - const std::vector<int>& fds); - - // Use recvmsg to read a message and an array of file descriptors. Returns - // -1 on failure. Note: will read, at most, |kMaxFileDescriptors| descriptors. - static ssize_t RecvMsg(int fd, - void* msg, - size_t length, - std::vector<ScopedFD>* fds); - - // Same as RecvMsg above, but also returns the sender's process ID (as seen - // from the caller's namespace). However, before using this function to - // receive process IDs, EnableReceiveProcessId() should be called on the - // receiving socket. - static ssize_t RecvMsgWithPid(int fd, - void* msg, - size_t length, - std::vector<ScopedFD>* fds, - ProcessId* pid); - -#if !defined(OS_NACL_NONSFI) - // Perform a sendmsg/recvmsg pair. - // 1. This process creates a UNIX SEQPACKET socketpair. Using - // connection-oriented sockets (SEQPACKET or STREAM) is critical here, - // because if one of the ends closes the other one must be notified. - // 2. This process writes a request to |fd| with an SCM_RIGHTS control - // message containing on end of the fresh socket pair. - // 3. This process blocks reading from the other end of the fresh - // socketpair. - // 4. The target process receives the request, processes it and writes the - // reply to the end of the socketpair contained in the request. - // 5. This process wakes up and continues. - // - // fd: descriptor to send the request on - // reply: buffer for the reply - // reply_len: size of |reply| - // result_fd: (may be NULL) the file descriptor returned in the reply - // (if any) - // request: the bytes to send in the request - static ssize_t SendRecvMsg(int fd, - uint8_t* reply, - unsigned reply_len, - int* result_fd, - const Pickle& request); - - // Similar to SendRecvMsg(), but |recvmsg_flags| allows to control the flags - // of the recvmsg(2) call. - static ssize_t SendRecvMsgWithFlags(int fd, - uint8_t* reply, - unsigned reply_len, - int recvmsg_flags, - int* result_fd, - const Pickle& request); -#endif // !defined(OS_NACL_NONSFI) - private: - // Similar to RecvMsg, but allows to specify |flags| for recvmsg(2). - static ssize_t RecvMsgWithFlags(int fd, - void* msg, - size_t length, - int flags, - std::vector<ScopedFD>* fds, - ProcessId* pid); -}; - -} // namespace base - -#endif // BASE_POSIX_UNIX_DOMAIN_SOCKET_H_
diff --git a/base/post_task_and_reply_with_result_internal.h b/base/post_task_and_reply_with_result_internal.h deleted file mode 100644 index 6f50de8..0000000 --- a/base/post_task_and_reply_with_result_internal.h +++ /dev/null
@@ -1,34 +0,0 @@ -// Copyright 2016 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_POST_TASK_AND_REPLY_WITH_RESULT_INTERNAL_H_ -#define BASE_POST_TASK_AND_REPLY_WITH_RESULT_INTERNAL_H_ - -#include <utility> - -#include "base/callback.h" - -namespace base { - -namespace internal { - -// Adapts a function that produces a result via a return value to -// one that returns via an output parameter. -template <typename ReturnType> -void ReturnAsParamAdapter(OnceCallback<ReturnType()> func, ReturnType* result) { - *result = std::move(func).Run(); -} - -// Adapts a T* result to a callblack that expects a T. -template <typename TaskReturnType, typename ReplyArgType> -void ReplyAdapter(OnceCallback<void(ReplyArgType)> callback, - TaskReturnType* result) { - std::move(callback).Run(std::move(*result)); -} - -} // namespace internal - -} // namespace base - -#endif // BASE_POST_TASK_AND_REPLY_WITH_RESULT_INTERNAL_H_
diff --git a/base/process/port_provider_mac.cc b/base/process/port_provider_mac.cc deleted file mode 100644 index 23d214c..0000000 --- a/base/process/port_provider_mac.cc +++ /dev/null
@@ -1,28 +0,0 @@ -// Copyright 2015 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/process/port_provider_mac.h" - -namespace base { - -PortProvider::PortProvider() : lock_(), observer_list_() {} -PortProvider::~PortProvider() {} - -void PortProvider::AddObserver(Observer* observer) { - base::AutoLock l(lock_); - observer_list_.AddObserver(observer); -} - -void PortProvider::RemoveObserver(Observer* observer) { - base::AutoLock l(lock_); - observer_list_.RemoveObserver(observer); -} - -void PortProvider::NotifyObservers(ProcessHandle process) { - base::AutoLock l(lock_); - for (auto& observer : observer_list_) - observer.OnReceivedTaskPort(process); -} - -} // namespace base
diff --git a/base/process/port_provider_mac.h b/base/process/port_provider_mac.h deleted file mode 100644 index 2f40297..0000000 --- a/base/process/port_provider_mac.h +++ /dev/null
@@ -1,61 +0,0 @@ -// Copyright 2015 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_PROCESS_PORT_PROVIDER_MAC_H_ -#define BASE_PROCESS_PORT_PROVIDER_MAC_H_ - -#include <mach/mach.h> - -#include "base/base_export.h" -#include "base/macros.h" -#include "base/observer_list.h" -#include "base/process/process_handle.h" -#include "base/synchronization/lock.h" - -namespace base { - -// Abstract base class that provides a mapping from ProcessHandle (pid_t) to the -// Mach task port. This replicates task_for_pid(), which requires root -// privileges. -class BASE_EXPORT PortProvider { - public: - PortProvider(); - virtual ~PortProvider(); - - class Observer { - public: - virtual ~Observer() {}; - // Called by the PortProvider to notify observers that the task port was - // received for a given process. - // No guarantees are made about the thread on which this notification will - // be sent. - // Observers must not call AddObserver() or RemoveObserver() in this - // callback, as doing so will deadlock. - virtual void OnReceivedTaskPort(ProcessHandle process) = 0; - }; - - // Returns the mach task port for |process| if possible, or else - // |MACH_PORT_NULL|. - virtual mach_port_t TaskForPid(ProcessHandle process) const = 0; - - // Observer interface. - void AddObserver(Observer* observer); - void RemoveObserver(Observer* observer); - - protected: - // Called by subclasses to send a notification to observers. - void NotifyObservers(ProcessHandle process); - - private: - // ObserverList is not thread-safe, so |lock_| ensures consistency of - // |observer_list_|. - base::Lock lock_; - base::ObserverList<Observer> observer_list_; - - DISALLOW_COPY_AND_ASSIGN(PortProvider); -}; - -} // namespace base - -#endif // BASE_PROCESS_PORT_PROVIDER_MAC_H_
diff --git a/base/process/process.h b/base/process/process.h index 2633355..dbfc701 100644 --- a/base/process/process.h +++ b/base/process/process.h
@@ -15,10 +15,6 @@ #include "base/win/scoped_handle.h" #endif -#if defined(OS_MACOSX) -#include "base/process/port_provider_mac.h" -#endif - namespace base { // Provides a move-only encapsulation of a process. @@ -64,15 +60,6 @@ static Process OpenWithAccess(ProcessId pid, DWORD desired_access); #endif - // Creates an object from a |handle| owned by someone else. - // Don't use this for new code. It is only intended to ease the migration to - // a strict ownership model. - // TODO(rvargas) crbug.com/417532: Remove this code. - static Process DeprecatedGetProcessFromHandle(ProcessHandle handle); - - // Returns true if processes can be backgrounded. - static bool CanBackgroundProcesses(); - // Terminates the current process immediately with |exit_code|. [[noreturn]] static void TerminateCurrentProcessImmediately(int exit_code); @@ -132,38 +119,6 @@ // process though that should be avoided. void Exited(int exit_code) const; -#if defined(OS_MACOSX) - // The Mac needs a Mach port in order to manipulate a process's priority, - // and there's no good way to get that from base given the pid. These Mac - // variants of the IsProcessBackgrounded and SetProcessBackgrounded API take - // a port provider for this reason. See crbug.com/460102 - // - // A process is backgrounded when its task priority is - // |TASK_BACKGROUND_APPLICATION|. - // - // Returns true if the port_provider can locate a task port for the process - // and it is backgrounded. If port_provider is null, returns false. - bool IsProcessBackgrounded(PortProvider* port_provider) const; - - // Set the process as backgrounded. If value is - // true, the priority of the associated task will be set to - // TASK_BACKGROUND_APPLICATION. If value is false, the - // priority of the process will be set to TASK_FOREGROUND_APPLICATION. - // - // Returns true if the priority was changed, false otherwise. If - // |port_provider| is null, this is a no-op and it returns false. - bool SetProcessBackgrounded(PortProvider* port_provider, bool value); -#else - // A process is backgrounded when it's priority is lower than normal. - // Return true if this process is backgrounded, false otherwise. - bool IsProcessBackgrounded() const; - - // Set a process as backgrounded. If value is true, the priority of the - // process will be lowered. If value is false, the priority of the process - // will be made "normal" - equivalent to default process priority. - // Returns true if the priority was changed, false otherwise. - bool SetProcessBackgrounded(bool value); -#endif // defined(OS_MACOSX) // Returns an integer representing the priority of a process. The meaning // of this value is OS dependent. int GetPriority() const;
diff --git a/base/process/process_linux.cc b/base/process/process_linux.cc deleted file mode 100644 index 066c647..0000000 --- a/base/process/process_linux.cc +++ /dev/null
@@ -1,60 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/process/process.h" - -#include <errno.h> -#include <sys/resource.h> - -#include "base/files/file_util.h" -#include "base/logging.h" -#include "base/strings/string_number_conversions.h" -#include "base/strings/string_split.h" -#include "base/strings/stringprintf.h" -#include "base/synchronization/lock.h" -#include "build_config.h" - -namespace base { - -namespace { - -const int kForegroundPriority = 0; - -const int kBackgroundPriority = 5; - -bool CanReraisePriority() { - // We won't be able to raise the priority if we don't have the right rlimit. - // The limit may be adjusted in /etc/security/limits.conf for PAM systems. - struct rlimit rlim; - return (getrlimit(RLIMIT_NICE, &rlim) == 0) && - (20 - kForegroundPriority) <= static_cast<int>(rlim.rlim_cur); -} - -} // namespace - -// static -bool Process::CanBackgroundProcesses() { - static const bool can_reraise_priority = CanReraisePriority(); - return can_reraise_priority; -} - -bool Process::IsProcessBackgrounded() const { - DCHECK(IsValid()); - - return GetPriority() == kBackgroundPriority; -} - -bool Process::SetProcessBackgrounded(bool background) { - DCHECK(IsValid()); - - if (!CanBackgroundProcesses()) - return false; - - int priority = background ? kBackgroundPriority : kForegroundPriority; - int result = setpriority(PRIO_PROCESS, process_, priority); - DPCHECK(result == 0); - return result == 0; -} - -} // namespace base
diff --git a/base/process/process_mac.cc b/base/process/process_mac.cc deleted file mode 100644 index cd47c62..0000000 --- a/base/process/process_mac.cc +++ /dev/null
@@ -1,72 +0,0 @@ -// Copyright 2016 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/process/process.h" - -#include <mach/mach.h> - -#include "base/mac/mach_logging.h" - -namespace base { - -bool Process::CanBackgroundProcesses() { - return false; -} - -bool Process::IsProcessBackgrounded(PortProvider* port_provider) const { - DCHECK(IsValid()); - if (port_provider == nullptr || !CanBackgroundProcesses()) - return false; - - mach_port_t task_port = port_provider->TaskForPid(Pid()); - if (task_port == TASK_NULL) - return false; - - task_category_policy_data_t category_policy; - mach_msg_type_number_t task_info_count = TASK_CATEGORY_POLICY_COUNT; - boolean_t get_default = FALSE; - - kern_return_t result = - task_policy_get(task_port, TASK_CATEGORY_POLICY, - reinterpret_cast<task_policy_t>(&category_policy), - &task_info_count, &get_default); - MACH_LOG_IF(ERROR, result != KERN_SUCCESS, result) - << "task_policy_get TASK_CATEGORY_POLICY"; - - if (result == KERN_SUCCESS && get_default == FALSE) { - return category_policy.role == TASK_BACKGROUND_APPLICATION; - } - return false; -} - -bool Process::SetProcessBackgrounded(PortProvider* port_provider, - bool background) { - DCHECK(IsValid()); - if (port_provider == nullptr || !CanBackgroundProcesses()) - return false; - - mach_port_t task_port = port_provider->TaskForPid(Pid()); - if (task_port == TASK_NULL) - return false; - - if (IsProcessBackgrounded(port_provider) == background) - return true; - - task_category_policy category_policy; - category_policy.role = - background ? TASK_BACKGROUND_APPLICATION : TASK_FOREGROUND_APPLICATION; - kern_return_t result = - task_policy_set(task_port, TASK_CATEGORY_POLICY, - reinterpret_cast<task_policy_t>(&category_policy), - TASK_CATEGORY_POLICY_COUNT); - - if (result != KERN_SUCCESS) { - MACH_LOG(ERROR, result) << "task_policy_set TASK_CATEGORY_POLICY"; - return false; - } - - return true; -} - -} // namespace base
diff --git a/base/process/process_posix.cc b/base/process/process_posix.cc index 57a4f67..3cc9182 100644 --- a/base/process/process_posix.cc +++ b/base/process/process_posix.cc
@@ -258,19 +258,6 @@ } // static -Process Process::DeprecatedGetProcessFromHandle(ProcessHandle handle) { - DCHECK_NE(handle, GetCurrentProcessHandle()); - return Process(handle); -} - -#if !defined(OS_LINUX) && !defined(OS_MACOSX) && !defined(OS_AIX) -// static -bool Process::CanBackgroundProcesses() { - return false; -} -#endif // !defined(OS_LINUX) && !defined(OS_MACOSX) && !defined(OS_AIX) - -// static void Process::TerminateCurrentProcessImmediately(int exit_code) { _exit(exit_code); } @@ -346,22 +333,6 @@ void Process::Exited(int exit_code) const {} -#if !defined(OS_LINUX) && !defined(OS_MACOSX) && !defined(OS_AIX) -bool Process::IsProcessBackgrounded() const { - // See SetProcessBackgrounded(). - DCHECK(IsValid()); - return false; -} - -bool Process::SetProcessBackgrounded(bool value) { - // Not implemented for POSIX systems other than Linux and Mac. With POSIX, if - // we were to lower the process priority we wouldn't be able to raise it back - // to its initial priority. - NOTIMPLEMENTED(); - return false; -} -#endif // !defined(OS_LINUX) && !defined(OS_MACOSX) && !defined(OS_AIX) - int Process::GetPriority() const { DCHECK(IsValid()); return getpriority(PRIO_PROCESS, process_);
diff --git a/base/process/process_win.cc b/base/process/process_win.cc index 48f598f..f5bd59e 100644 --- a/base/process/process_win.cc +++ b/base/process/process_win.cc
@@ -65,23 +65,6 @@ } // static -Process Process::DeprecatedGetProcessFromHandle(ProcessHandle handle) { - DCHECK_NE(handle, ::GetCurrentProcess()); - ProcessHandle out_handle; - if (!::DuplicateHandle(GetCurrentProcess(), handle, - GetCurrentProcess(), &out_handle, - 0, FALSE, DUPLICATE_SAME_ACCESS)) { - return Process(); - } - return Process(out_handle); -} - -// static -bool Process::CanBackgroundProcesses() { - return true; -} - -// static void Process::TerminateCurrentProcessImmediately(int exit_code) { ::TerminateProcess(GetCurrentProcess(), exit_code); // There is some ambiguity over whether the call above can return. Rather than @@ -182,31 +165,6 @@ void Process::Exited(int exit_code) const { } -bool Process::IsProcessBackgrounded() const { - DCHECK(IsValid()); - DWORD priority = GetPriority(); - if (priority == 0) - return false; // Failure case. - return ((priority == BELOW_NORMAL_PRIORITY_CLASS) || - (priority == IDLE_PRIORITY_CLASS)); -} - -bool Process::SetProcessBackgrounded(bool value) { - DCHECK(IsValid()); - // Vista and above introduce a real background mode, which not only - // sets the priority class on the threads but also on the IO generated - // by it. Unfortunately it can only be set for the calling process. - DWORD priority; - if (is_current()) { - priority = value ? PROCESS_MODE_BACKGROUND_BEGIN : - PROCESS_MODE_BACKGROUND_END; - } else { - priority = value ? IDLE_PRIORITY_CLASS : NORMAL_PRIORITY_CLASS; - } - - return (::SetPriorityClass(Handle(), priority) != 0); -} - int Process::GetPriority() const { DCHECK(IsValid()); return ::GetPriorityClass(Handle());
diff --git a/base/rand_util.cc b/base/rand_util.cc deleted file mode 100644 index 5881ef2..0000000 --- a/base/rand_util.cc +++ /dev/null
@@ -1,82 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/rand_util.h" - -#include <limits.h> -#include <math.h> -#include <stdint.h> - -#include <algorithm> -#include <limits> - -#include "base/logging.h" -#include "base/strings/string_util.h" - -namespace base { - -uint64_t RandUint64() { - uint64_t number; - RandBytes(&number, sizeof(number)); - return number; -} - -int RandInt(int min, int max) { - DCHECK_LE(min, max); - - uint64_t range = static_cast<uint64_t>(max) - min + 1; - // |range| is at most UINT_MAX + 1, so the result of RandGenerator(range) - // is at most UINT_MAX. Hence it's safe to cast it from uint64_t to int64_t. - int result = - static_cast<int>(min + static_cast<int64_t>(base::RandGenerator(range))); - DCHECK_GE(result, min); - DCHECK_LE(result, max); - return result; -} - -double RandDouble() { - return BitsToOpenEndedUnitInterval(base::RandUint64()); -} - -double BitsToOpenEndedUnitInterval(uint64_t bits) { - // We try to get maximum precision by masking out as many bits as will fit - // in the target type's mantissa, and raising it to an appropriate power to - // produce output in the range [0, 1). For IEEE 754 doubles, the mantissa - // is expected to accommodate 53 bits. - - static_assert(std::numeric_limits<double>::radix == 2, - "otherwise use scalbn"); - static const int kBits = std::numeric_limits<double>::digits; - uint64_t random_bits = bits & ((UINT64_C(1) << kBits) - 1); - double result = ldexp(static_cast<double>(random_bits), -1 * kBits); - DCHECK_GE(result, 0.0); - DCHECK_LT(result, 1.0); - return result; -} - -uint64_t RandGenerator(uint64_t range) { - DCHECK_GT(range, 0u); - // We must discard random results above this number, as they would - // make the random generator non-uniform (consider e.g. if - // MAX_UINT64 was 7 and |range| was 5, then a result of 1 would be twice - // as likely as a result of 3 or 4). - uint64_t max_acceptable_value = - (std::numeric_limits<uint64_t>::max() / range) * range - 1; - - uint64_t value; - do { - value = base::RandUint64(); - } while (value > max_acceptable_value); - - return value % range; -} - -std::string RandBytesAsString(size_t length) { - DCHECK_GT(length, 0u); - std::string result; - RandBytes(WriteInto(&result, length + 1), length); - return result; -} - -} // namespace base
diff --git a/base/rand_util.h b/base/rand_util.h deleted file mode 100644 index 32c8fc7..0000000 --- a/base/rand_util.h +++ /dev/null
@@ -1,78 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_RAND_UTIL_H_ -#define BASE_RAND_UTIL_H_ - -#include <stddef.h> -#include <stdint.h> - -#include <algorithm> -#include <string> - -#include "base/base_export.h" -#include "build_config.h" - -namespace base { - -// Returns a random number in range [0, UINT64_MAX]. Thread-safe. -BASE_EXPORT uint64_t RandUint64(); - -// Returns a random number between min and max (inclusive). Thread-safe. -BASE_EXPORT int RandInt(int min, int max); - -// Returns a random number in range [0, range). Thread-safe. -BASE_EXPORT uint64_t RandGenerator(uint64_t range); - -// Returns a random double in range [0, 1). Thread-safe. -BASE_EXPORT double RandDouble(); - -// Given input |bits|, convert with maximum precision to a double in -// the range [0, 1). Thread-safe. -BASE_EXPORT double BitsToOpenEndedUnitInterval(uint64_t bits); - -// Fills |output_length| bytes of |output| with random data. Thread-safe. -// -// Although implementations are required to use a cryptographically secure -// random number source, code outside of base/ that relies on this should use -// crypto::RandBytes instead to ensure the requirement is easily discoverable. -BASE_EXPORT void RandBytes(void* output, size_t output_length); - -// Fills a string of length |length| with random data and returns it. -// |length| should be nonzero. Thread-safe. -// -// Note that this is a variation of |RandBytes| with a different return type. -// The returned string is likely not ASCII/UTF-8. Use with care. -// -// Although implementations are required to use a cryptographically secure -// random number source, code outside of base/ that relies on this should use -// crypto::RandBytes instead to ensure the requirement is easily discoverable. -BASE_EXPORT std::string RandBytesAsString(size_t length); - -// An STL UniformRandomBitGenerator backed by RandUint64. -// TODO(tzik): Consider replacing this with a faster implementation. -class RandomBitGenerator { - public: - using result_type = uint64_t; - static constexpr result_type min() { return 0; } - static constexpr result_type max() { return UINT64_MAX; } - result_type operator()() const { return RandUint64(); } - - RandomBitGenerator() = default; - ~RandomBitGenerator() = default; -}; - -// Shuffles [first, last) randomly. Thread-safe. -template <typename Itr> -void RandomShuffle(Itr first, Itr last) { - std::shuffle(first, last, RandomBitGenerator()); -} - -#if defined(OS_POSIX) && !defined(OS_FUCHSIA) -BASE_EXPORT int GetUrandomFD(); -#endif - -} // namespace base - -#endif // BASE_RAND_UTIL_H_
diff --git a/base/rand_util_nacl.cc b/base/rand_util_nacl.cc deleted file mode 100644 index b26b408..0000000 --- a/base/rand_util_nacl.cc +++ /dev/null
@@ -1,27 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/rand_util.h" - -#include <nacl/nacl_random.h> -#include <stddef.h> -#include <stdint.h> - -#include "base/logging.h" - -namespace base { - -void RandBytes(void* output, size_t output_length) { - char* output_ptr = static_cast<char*>(output); - while (output_length > 0) { - size_t nread; - const int error = nacl_secure_random(output_ptr, output_length, &nread); - CHECK_EQ(error, 0); - CHECK_LE(nread, output_length); - output_ptr += nread; - output_length -= nread; - } -} - -} // namespace base
diff --git a/base/rand_util_posix.cc b/base/rand_util_posix.cc deleted file mode 100644 index 13ecaf5..0000000 --- a/base/rand_util_posix.cc +++ /dev/null
@@ -1,57 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/rand_util.h" - -#include <errno.h> -#include <fcntl.h> -#include <stddef.h> -#include <stdint.h> -#include <unistd.h> - -#include "base/files/file_util.h" -#include "base/logging.h" -#include "base/posix/eintr_wrapper.h" - -namespace { - -// We keep the file descriptor for /dev/urandom around so we don't need to -// reopen it (which is expensive), and since we may not even be able to reopen -// it if we are later put in a sandbox. This class wraps the file descriptor so -// we can use LazyInstance to handle opening it on the first access. -class URandomFd { - public: - URandomFd() : fd_(HANDLE_EINTR(open("/dev/urandom", O_RDONLY | O_CLOEXEC))) { - DCHECK_GE(fd_, 0) << "Cannot open /dev/urandom: " << errno; - } - - ~URandomFd() { close(fd_); } - - int fd() const { return fd_; } - - private: - const int fd_; -}; - -URandomFd* GetInstance() { - static URandomFd* instance = new URandomFd; - return instance; -} - -} // namespace - -namespace base { - -void RandBytes(void* output, size_t output_length) { - const int urandom_fd = GetInstance()->fd(); - const bool success = - ReadFromFD(urandom_fd, static_cast<char*>(output), output_length); - CHECK(success); -} - -int GetUrandomFD(void) { - return GetInstance()->fd(); -} - -} // namespace base
diff --git a/base/rand_util_win.cc b/base/rand_util_win.cc deleted file mode 100644 index e85c216..0000000 --- a/base/rand_util_win.cc +++ /dev/null
@@ -1,38 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/rand_util.h" - -#include <windows.h> -#include <stddef.h> -#include <stdint.h> - -// #define needed to link in RtlGenRandom(), a.k.a. SystemFunction036. See the -// "Community Additions" comment on MSDN here: -// http://msdn.microsoft.com/en-us/library/windows/desktop/aa387694.aspx -#define SystemFunction036 NTAPI SystemFunction036 -#include <NTSecAPI.h> -#undef SystemFunction036 - -#include <algorithm> -#include <limits> - -#include "base/logging.h" - -namespace base { - -void RandBytes(void* output, size_t output_length) { - char* output_ptr = static_cast<char*>(output); - while (output_length > 0) { - const ULONG output_bytes_this_pass = static_cast<ULONG>(std::min( - output_length, static_cast<size_t>(std::numeric_limits<ULONG>::max()))); - const bool success = - RtlGenRandom(output_ptr, output_bytes_this_pass) != FALSE; - CHECK(success); - output_length -= output_bytes_this_pass; - output_ptr += output_bytes_this_pass; - } -} - -} // namespace base
diff --git a/base/scoped_observer.h b/base/scoped_observer.h deleted file mode 100644 index 7f1d6fb..0000000 --- a/base/scoped_observer.h +++ /dev/null
@@ -1,63 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_SCOPED_OBSERVER_H_ -#define BASE_SCOPED_OBSERVER_H_ - -#include <stddef.h> - -#include <algorithm> -#include <vector> - -#include "base/logging.h" -#include "base/macros.h" -#include "base/stl_util.h" - -// ScopedObserver is used to keep track of the set of sources an object has -// attached itself to as an observer. When ScopedObserver is destroyed it -// removes the object as an observer from all sources it has been added to. -template <class Source, class Observer> -class ScopedObserver { - public: - explicit ScopedObserver(Observer* observer) : observer_(observer) {} - - ~ScopedObserver() { - RemoveAll(); - } - - // Adds the object passed to the constructor as an observer on |source|. - void Add(Source* source) { - sources_.push_back(source); - source->AddObserver(observer_); - } - - // Remove the object passed to the constructor as an observer from |source|. - void Remove(Source* source) { - auto it = std::find(sources_.begin(), sources_.end(), source); - DCHECK(it != sources_.end()); - sources_.erase(it); - source->RemoveObserver(observer_); - } - - void RemoveAll() { - for (size_t i = 0; i < sources_.size(); ++i) - sources_[i]->RemoveObserver(observer_); - sources_.clear(); - } - - bool IsObserving(Source* source) const { - return base::ContainsValue(sources_, source); - } - - bool IsObservingSources() const { return !sources_.empty(); } - - private: - Observer* observer_; - - std::vector<Source*> sources_; - - DISALLOW_COPY_AND_ASSIGN(ScopedObserver); -}; - -#endif // BASE_SCOPED_OBSERVER_H_
diff --git a/base/strings/OWNERS b/base/strings/OWNERS deleted file mode 100644 index 5381872..0000000 --- a/base/strings/OWNERS +++ /dev/null
@@ -1,2 +0,0 @@ -per-file safe_sprintf*=jln@chromium.org -per-file safe_sprintf*=mdempsky@chromium.org
diff --git a/base/strings/latin1_string_conversions.cc b/base/strings/latin1_string_conversions.cc deleted file mode 100644 index dca62ce..0000000 --- a/base/strings/latin1_string_conversions.cc +++ /dev/null
@@ -1,19 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/strings/latin1_string_conversions.h" - -namespace base { - -string16 Latin1OrUTF16ToUTF16(size_t length, - const Latin1Char* latin1, - const char16* utf16) { - if (!length) - return string16(); - if (latin1) - return string16(latin1, latin1 + length); - return string16(utf16, utf16 + length); -} - -} // namespace base
diff --git a/base/strings/latin1_string_conversions.h b/base/strings/latin1_string_conversions.h deleted file mode 100644 index 42113ef..0000000 --- a/base/strings/latin1_string_conversions.h +++ /dev/null
@@ -1,34 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_STRINGS_LATIN1_STRING_CONVERSIONS_H_ -#define BASE_STRINGS_LATIN1_STRING_CONVERSIONS_H_ - -#include <stddef.h> - -#include <string> - -#include "base/base_export.h" -#include "base/strings/string16.h" - -namespace base { - -// This definition of Latin1Char matches the definition of LChar in Blink. We -// use unsigned char rather than char to make less tempting to mix and match -// Latin-1 and UTF-8 characters.. -typedef unsigned char Latin1Char; - -// This somewhat odd function is designed to help us convert from Blink Strings -// to string16. A Blink string is either backed by an array of Latin-1 -// characters or an array of UTF-16 characters. This function is called by -// WebString::operator string16() to convert one or the other character array -// to string16. This function is defined here rather than in WebString.h to -// avoid binary bloat in all the callers of the conversion operator. -BASE_EXPORT string16 Latin1OrUTF16ToUTF16(size_t length, - const Latin1Char* latin1, - const char16* utf16); - -} // namespace base - -#endif // BASE_STRINGS_LATIN1_STRING_CONVERSIONS_H_
diff --git a/base/strings/nullable_string16.cc b/base/strings/nullable_string16.cc deleted file mode 100644 index 076b282..0000000 --- a/base/strings/nullable_string16.cc +++ /dev/null
@@ -1,33 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/strings/nullable_string16.h" - -#include <ostream> -#include <utility> - -namespace base { -NullableString16::NullableString16() = default; -NullableString16::NullableString16(const NullableString16& other) = default; -NullableString16::NullableString16(NullableString16&& other) = default; - -NullableString16::NullableString16(const string16& string, bool is_null) { - if (!is_null) - string_.emplace(string); -} - -NullableString16::NullableString16(Optional<string16> optional_string16) - : string_(std::move(optional_string16)) {} - -NullableString16::~NullableString16() = default; -NullableString16& NullableString16::operator=(const NullableString16& other) = - default; -NullableString16& NullableString16::operator=(NullableString16&& other) = - default; - -std::ostream& operator<<(std::ostream& out, const NullableString16& value) { - return value.is_null() ? out << "(null)" : out << value.string(); -} - -} // namespace base
diff --git a/base/strings/nullable_string16.h b/base/strings/nullable_string16.h deleted file mode 100644 index abddee0..0000000 --- a/base/strings/nullable_string16.h +++ /dev/null
@@ -1,55 +0,0 @@ -// Copyright (c) 2010 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_STRINGS_NULLABLE_STRING16_H_ -#define BASE_STRINGS_NULLABLE_STRING16_H_ - -#include <iosfwd> - -#include "base/base_export.h" -#include "base/optional.h" -#include "base/strings/string16.h" -#include "base/strings/string_util.h" - -namespace base { - -// This class is a simple wrapper for string16 which also contains a null -// state. This should be used only where the difference between null and -// empty is meaningful. -class BASE_EXPORT NullableString16 { - public: - NullableString16(); - NullableString16(const NullableString16& other); - NullableString16(NullableString16&& other); - NullableString16(const string16& string, bool is_null); - explicit NullableString16(Optional<string16> optional_string16); - ~NullableString16(); - - NullableString16& operator=(const NullableString16& other); - NullableString16& operator=(NullableString16&& other); - - const string16& string() const { - return string_ ? *string_ : EmptyString16(); - } - bool is_null() const { return !string_; } - const Optional<string16>& as_optional_string16() const { return string_; } - - private: - Optional<string16> string_; -}; - -inline bool operator==(const NullableString16& a, const NullableString16& b) { - return a.as_optional_string16() == b.as_optional_string16(); -} - -inline bool operator!=(const NullableString16& a, const NullableString16& b) { - return !(a == b); -} - -BASE_EXPORT std::ostream& operator<<(std::ostream& out, - const NullableString16& value); - -} // namespace base - -#endif // BASE_STRINGS_NULLABLE_STRING16_H_
diff --git a/base/strings/old_utf_string_conversions.cc b/base/strings/old_utf_string_conversions.cc deleted file mode 100644 index b6edb29..0000000 --- a/base/strings/old_utf_string_conversions.cc +++ /dev/null
@@ -1,262 +0,0 @@ -// Copyright (c) 2010 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/strings/old_utf_string_conversions.h" - -#include <stdint.h> - -#include "base/strings/string_piece.h" -#include "base/strings/string_util.h" -#include "base/strings/utf_string_conversion_utils.h" -#include "build_config.h" - -namespace base_old { - -using base::IsStringASCII; -using base::ReadUnicodeCharacter; -using base::WriteUnicodeCharacter; - -template<typename CHAR> -void PrepareForUTF8Output(const CHAR* src, - size_t src_len, - std::string* output) { - output->clear(); - if (src_len == 0) - return; - if (src[0] < 0x80) { - // Assume that the entire input will be ASCII. - output->reserve(src_len); - } else { - // Assume that the entire input is non-ASCII and will have 3 bytes per char. - output->reserve(src_len * 3); - } -} - -template<typename STRING> -void PrepareForUTF16Or32Output(const char* src, - size_t src_len, - STRING* output) { - output->clear(); - if (src_len == 0) - return; - if (static_cast<unsigned char>(src[0]) < 0x80) { - // Assume the input is all ASCII, which means 1:1 correspondence. - output->reserve(src_len); - } else { - // Otherwise assume that the UTF-8 sequences will have 2 bytes for each - // character. - output->reserve(src_len / 2); - } -} - -namespace { - -// Generalized Unicode converter ----------------------------------------------- - -// Converts the given source Unicode character type to the given destination -// Unicode character type as a STL string. The given input buffer and size -// determine the source, and the given output STL string will be replaced by -// the result. -template <typename SRC_CHAR, typename DEST_STRING> -bool ConvertUnicode(const SRC_CHAR* src, size_t src_len, DEST_STRING* output) { - // ICU requires 32-bit numbers. - bool success = true; - int32_t src_len32 = static_cast<int32_t>(src_len); - for (int32_t i = 0; i < src_len32; i++) { - uint32_t code_point; - if (ReadUnicodeCharacter(src, src_len32, &i, &code_point)) { - WriteUnicodeCharacter(code_point, output); - } else { - WriteUnicodeCharacter(0xFFFD, output); - success = false; - } - } - - return success; -} - -} // namespace - -// UTF-8 <-> Wide -------------------------------------------------------------- - -bool WideToUTF8(const wchar_t* src, size_t src_len, std::string* output) { - if (IsStringASCII(std::wstring(src, src_len))) { - output->assign(src, src + src_len); - return true; - } else { - PrepareForUTF8Output(src, src_len, output); - return ConvertUnicode(src, src_len, output); - } -} - -std::string WideToUTF8(const std::wstring& wide) { - if (IsStringASCII(wide)) { - return std::string(wide.data(), wide.data() + wide.length()); - } - - std::string ret; - PrepareForUTF8Output(wide.data(), wide.length(), &ret); - ConvertUnicode(wide.data(), wide.length(), &ret); - return ret; -} - -bool UTF8ToWide(const char* src, size_t src_len, std::wstring* output) { - if (IsStringASCII(StringPiece(src, src_len))) { - output->assign(src, src + src_len); - return true; - } else { - PrepareForUTF16Or32Output(src, src_len, output); - return ConvertUnicode(src, src_len, output); - } -} - -std::wstring UTF8ToWide(StringPiece utf8) { - if (IsStringASCII(utf8)) { - return std::wstring(utf8.begin(), utf8.end()); - } - - std::wstring ret; - PrepareForUTF16Or32Output(utf8.data(), utf8.length(), &ret); - ConvertUnicode(utf8.data(), utf8.length(), &ret); - return ret; -} - -// UTF-16 <-> Wide ------------------------------------------------------------- - -#if defined(WCHAR_T_IS_UTF16) - -// When wide == UTF-16, then conversions are a NOP. -bool WideToUTF16(const wchar_t* src, size_t src_len, string16* output) { - output->assign(src, src_len); - return true; -} - -string16 WideToUTF16(const std::wstring& wide) { - return wide; -} - -bool UTF16ToWide(const char16* src, size_t src_len, std::wstring* output) { - output->assign(src, src_len); - return true; -} - -std::wstring UTF16ToWide(const string16& utf16) { - return utf16; -} - -#elif defined(WCHAR_T_IS_UTF32) - -bool WideToUTF16(const wchar_t* src, size_t src_len, string16* output) { - output->clear(); - // Assume that normally we won't have any non-BMP characters so the counts - // will be the same. - output->reserve(src_len); - return ConvertUnicode(src, src_len, output); -} - -string16 WideToUTF16(const std::wstring& wide) { - string16 ret; - WideToUTF16(wide.data(), wide.length(), &ret); - return ret; -} - -bool UTF16ToWide(const char16* src, size_t src_len, std::wstring* output) { - output->clear(); - // Assume that normally we won't have any non-BMP characters so the counts - // will be the same. - output->reserve(src_len); - return ConvertUnicode(src, src_len, output); -} - -std::wstring UTF16ToWide(const string16& utf16) { - std::wstring ret; - UTF16ToWide(utf16.data(), utf16.length(), &ret); - return ret; -} - -#endif // defined(WCHAR_T_IS_UTF32) - -// UTF16 <-> UTF8 -------------------------------------------------------------- - -#if defined(WCHAR_T_IS_UTF32) - -bool UTF8ToUTF16(const char* src, size_t src_len, string16* output) { - if (IsStringASCII(StringPiece(src, src_len))) { - output->assign(src, src + src_len); - return true; - } else { - PrepareForUTF16Or32Output(src, src_len, output); - return ConvertUnicode(src, src_len, output); - } -} - -string16 UTF8ToUTF16(StringPiece utf8) { - if (IsStringASCII(utf8)) { - return string16(utf8.begin(), utf8.end()); - } - - string16 ret; - PrepareForUTF16Or32Output(utf8.data(), utf8.length(), &ret); - // Ignore the success flag of this call, it will do the best it can for - // invalid input, which is what we want here. - ConvertUnicode(utf8.data(), utf8.length(), &ret); - return ret; -} - -bool UTF16ToUTF8(const char16* src, size_t src_len, std::string* output) { - if (IsStringASCII(StringPiece16(src, src_len))) { - output->assign(src, src + src_len); - return true; - } else { - PrepareForUTF8Output(src, src_len, output); - return ConvertUnicode(src, src_len, output); - } -} - -std::string UTF16ToUTF8(StringPiece16 utf16) { - std::string ret; - // Ignore the success flag of this call, it will do the best it can for - // invalid input, which is what we want here. - UTF16ToUTF8(utf16.data(), utf16.length(), &ret); - return ret; -} - -#elif defined(WCHAR_T_IS_UTF16) -// Easy case since we can use the "wide" versions we already wrote above. - -bool UTF8ToUTF16(const char* src, size_t src_len, string16* output) { - return UTF8ToWide(src, src_len, output); -} - -string16 UTF8ToUTF16(StringPiece utf8) { - return UTF8ToWide(utf8); -} - -bool UTF16ToUTF8(const char16* src, size_t src_len, std::string* output) { - return WideToUTF8(src, src_len, output); -} - -std::string UTF16ToUTF8(StringPiece16 utf16) { - if (IsStringASCII(utf16)) - return std::string(utf16.data(), utf16.data() + utf16.length()); - - std::string ret; - PrepareForUTF8Output(utf16.data(), utf16.length(), &ret); - ConvertUnicode(utf16.data(), utf16.length(), &ret); - return ret; -} - -#endif - -string16 ASCIIToUTF16(StringPiece ascii) { - DCHECK(IsStringASCII(ascii)) << ascii; - return string16(ascii.begin(), ascii.end()); -} - -std::string UTF16ToASCII(StringPiece16 utf16) { - DCHECK(IsStringASCII(utf16)) << UTF16ToUTF8(utf16); - return std::string(utf16.begin(), utf16.end()); -} - -} // namespace base_old
diff --git a/base/strings/old_utf_string_conversions.h b/base/strings/old_utf_string_conversions.h deleted file mode 100644 index 2f0c6c5..0000000 --- a/base/strings/old_utf_string_conversions.h +++ /dev/null
@@ -1,64 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_STRINGS_OLD_UTF_STRING_CONVERSIONS_H_ -#define BASE_STRINGS_OLD_UTF_STRING_CONVERSIONS_H_ - -#include <stddef.h> - -#include <string> - -#include "base/base_export.h" -#include "base/strings/string16.h" -#include "base/strings/string_piece.h" - -namespace base_old { - -using base::char16; -using base::string16; -using base::StringPiece16; -using base::StringPiece; - -// These convert between UTF-8, -16, and -32 strings. They are potentially slow, -// so avoid unnecessary conversions. The low-level versions return a boolean -// indicating whether the conversion was 100% valid. In this case, it will still -// do the best it can and put the result in the output buffer. The versions that -// return strings ignore this error and just return the best conversion -// possible. -BASE_EXPORT bool WideToUTF8(const wchar_t* src, - size_t src_len, - std::string* output); -BASE_EXPORT std::string WideToUTF8(const std::wstring& wide); -BASE_EXPORT bool UTF8ToWide(const char* src, - size_t src_len, - std::wstring* output); -BASE_EXPORT std::wstring UTF8ToWide(StringPiece utf8); - -BASE_EXPORT bool WideToUTF16(const wchar_t* src, - size_t src_len, - string16* output); -BASE_EXPORT string16 WideToUTF16(const std::wstring& wide); -BASE_EXPORT bool UTF16ToWide(const char16* src, - size_t src_len, - std::wstring* output); -BASE_EXPORT std::wstring UTF16ToWide(const string16& utf16); - -BASE_EXPORT bool UTF8ToUTF16(const char* src, size_t src_len, string16* output); -BASE_EXPORT string16 UTF8ToUTF16(StringPiece utf8); -BASE_EXPORT bool UTF16ToUTF8(const char16* src, - size_t src_len, - std::string* output); -BASE_EXPORT std::string UTF16ToUTF8(StringPiece16 utf16); - -// This converts an ASCII string, typically a hardcoded constant, to a UTF16 -// string. -BASE_EXPORT string16 ASCIIToUTF16(StringPiece ascii); - -// Converts to 7-bit ASCII by truncating. The result must be known to be ASCII -// beforehand. -BASE_EXPORT std::string UTF16ToASCII(StringPiece16 utf16); - -} // namespace base_old - -#endif // BASE_STRINGS_OLD_UTF_STRING_CONVERSIONS_H_
diff --git a/base/strings/pattern.cc b/base/strings/pattern.cc deleted file mode 100644 index f3de0af..0000000 --- a/base/strings/pattern.cc +++ /dev/null
@@ -1,155 +0,0 @@ -// Copyright 2015 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/strings/pattern.h" - -#include "base/third_party/icu/icu_utf.h" - -namespace base { - -namespace { - -constexpr bool IsWildcard(base_icu::UChar32 character) { - return character == '*' || character == '?'; -} - -// Searches for the next subpattern of |pattern| in |string|, up to the given -// |maximum_distance|. The subpattern extends from the start of |pattern| up to -// the first wildcard character (or the end of the string). If the value of -// |maximum_distance| is negative, the maximum distance is considered infinite. -template <typename CHAR, typename NEXT> -constexpr bool SearchForChars(const CHAR** pattern, - const CHAR* pattern_end, - const CHAR** string, - const CHAR* string_end, - int maximum_distance, - NEXT next) { - const CHAR* pattern_start = *pattern; - const CHAR* string_start = *string; - bool escape = false; - while (true) { - if (*pattern == pattern_end) { - // If this is the end of the pattern, only accept the end of the string; - // anything else falls through to the mismatch case. - if (*string == string_end) - return true; - } else { - // If we have found a wildcard, we're done. - if (!escape && IsWildcard(**pattern)) - return true; - - // Check if the escape character is found. If so, skip it and move to the - // next character. - if (!escape && **pattern == '\\') { - escape = true; - next(pattern, pattern_end); - continue; - } - - escape = false; - - if (*string == string_end) - return false; - - // Check if the chars match, if so, increment the ptrs. - const CHAR* pattern_next = *pattern; - const CHAR* string_next = *string; - base_icu::UChar32 pattern_char = next(&pattern_next, pattern_end); - if (pattern_char == next(&string_next, string_end) && - pattern_char != CBU_SENTINEL) { - *pattern = pattern_next; - *string = string_next; - continue; - } - } - - // Mismatch. If we have reached the maximum distance, return false, - // otherwise restart at the beginning of the pattern with the next character - // in the string. - // TODO(bauerb): This is a naive implementation of substring search, which - // could be implemented with a more efficient algorithm, e.g. - // Knuth-Morris-Pratt (at the expense of requiring preprocessing). - if (maximum_distance == 0) - return false; - - // Because unlimited distance is represented as -1, this will never reach 0 - // and therefore fail the match above. - maximum_distance--; - *pattern = pattern_start; - next(&string_start, string_end); - *string = string_start; - } -} - -// Consumes consecutive wildcard characters (? or *). Returns the maximum number -// of characters matched by the sequence of wildcards, or -1 if the wildcards -// match an arbitrary number of characters (which is the case if it contains at -// least one *). -template <typename CHAR, typename NEXT> -constexpr int EatWildcards(const CHAR** pattern, const CHAR* end, NEXT next) { - int num_question_marks = 0; - bool has_asterisk = false; - while (*pattern != end) { - if (**pattern == '?') { - num_question_marks++; - } else if (**pattern == '*') { - has_asterisk = true; - } else { - break; - } - - next(pattern, end); - } - return has_asterisk ? -1 : num_question_marks; -} - -template <typename CHAR, typename NEXT> -constexpr bool MatchPatternT(const CHAR* eval, - const CHAR* eval_end, - const CHAR* pattern, - const CHAR* pattern_end, - NEXT next) { - do { - int maximum_wildcard_length = EatWildcards(&pattern, pattern_end, next); - if (!SearchForChars(&pattern, pattern_end, &eval, eval_end, - maximum_wildcard_length, next)) { - return false; - } - } while (pattern != pattern_end); - return true; -} - -struct NextCharUTF8 { - base_icu::UChar32 operator()(const char** p, const char* end) { - base_icu::UChar32 c; - int offset = 0; - CBU8_NEXT(*p, offset, end - *p, c); - *p += offset; - return c; - } -}; - -struct NextCharUTF16 { - base_icu::UChar32 operator()(const char16** p, const char16* end) { - base_icu::UChar32 c; - int offset = 0; - CBU16_NEXT(*p, offset, end - *p, c); - *p += offset; - return c; - } -}; - -} // namespace - -bool MatchPattern(StringPiece eval, StringPiece pattern) { - return MatchPatternT(eval.data(), eval.data() + eval.size(), pattern.data(), - pattern.data() + pattern.size(), NextCharUTF8()); -} - -bool MatchPattern(StringPiece16 eval, StringPiece16 pattern) { - return MatchPatternT(eval.data(), eval.data() + eval.size(), pattern.data(), - pattern.data() + pattern.size(), NextCharUTF16()); -} - -} // namespace base
diff --git a/base/strings/pattern.h b/base/strings/pattern.h deleted file mode 100644 index b5172ab..0000000 --- a/base/strings/pattern.h +++ /dev/null
@@ -1,23 +0,0 @@ -// Copyright 2015 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_STRINGS_PATTERN_H_ -#define BASE_STRINGS_PATTERN_H_ - -#include "base/base_export.h" -#include "base/strings/string_piece.h" - -namespace base { - -// Returns true if the |string| passed in matches the |pattern|. The pattern -// string can contain wildcards like * and ?. -// -// The backslash character (\) is an escape character for * and ?. -// ? matches 0 or 1 character, while * matches 0 or more characters. -BASE_EXPORT bool MatchPattern(StringPiece string, StringPiece pattern); -BASE_EXPORT bool MatchPattern(StringPiece16 string, StringPiece16 pattern); - -} // namespace base - -#endif // BASE_STRINGS_PATTERN_H_
diff --git a/base/strings/safe_sprintf.cc b/base/strings/safe_sprintf.cc deleted file mode 100644 index 8c6e8ca..0000000 --- a/base/strings/safe_sprintf.cc +++ /dev/null
@@ -1,686 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/strings/safe_sprintf.h" - -#include <errno.h> -#include <string.h> - -#include <limits> - -#include "base/macros.h" -#include "build_config.h" - -#if !defined(NDEBUG) -// In debug builds, we use RAW_CHECK() to print useful error messages, if -// SafeSPrintf() is called with broken arguments. -// As our contract promises that SafeSPrintf() can be called from any -// restricted run-time context, it is not actually safe to call logging -// functions from it; and we only ever do so for debug builds and hope for the -// best. We should _never_ call any logging function other than RAW_CHECK(), -// and we should _never_ include any logging code that is active in production -// builds. Most notably, we should not include these logging functions in -// unofficial release builds, even though those builds would otherwise have -// DCHECKS() enabled. -// In other words; please do not remove the #ifdef around this #include. -// Instead, in production builds we opt for returning a degraded result, -// whenever an error is encountered. -// E.g. The broken function call -// SafeSPrintf("errno = %d (%x)", errno, strerror(errno)) -// will print something like -// errno = 13, (%x) -// instead of -// errno = 13 (Access denied) -// In most of the anticipated use cases, that's probably the preferred -// behavior. -#include "base/logging.h" -#define DEBUG_CHECK RAW_CHECK -#else -#define DEBUG_CHECK(x) do { if (x) { } } while (0) -#endif - -namespace base { -namespace strings { - -// The code in this file is extremely careful to be async-signal-safe. -// -// Most obviously, we avoid calling any code that could dynamically allocate -// memory. Doing so would almost certainly result in bugs and dead-locks. -// We also avoid calling any other STL functions that could have unintended -// side-effects involving memory allocation or access to other shared -// resources. -// -// But on top of that, we also avoid calling other library functions, as many -// of them have the side-effect of calling getenv() (in order to deal with -// localization) or accessing errno. The latter sounds benign, but there are -// several execution contexts where it isn't even possible to safely read let -// alone write errno. -// -// The stated design goal of the SafeSPrintf() function is that it can be -// called from any context that can safely call C or C++ code (i.e. anything -// that doesn't require assembly code). -// -// For a brief overview of some but not all of the issues with async-signal- -// safety, refer to: -// http://pubs.opengroup.org/onlinepubs/009695399/functions/xsh_chap02_04.html - -namespace { -const size_t kSSizeMaxConst = ((size_t)(ssize_t)-1) >> 1; - -const char kUpCaseHexDigits[] = "0123456789ABCDEF"; -const char kDownCaseHexDigits[] = "0123456789abcdef"; -} - -#if defined(NDEBUG) -// We would like to define kSSizeMax as std::numeric_limits<ssize_t>::max(), -// but C++ doesn't allow us to do that for constants. Instead, we have to -// use careful casting and shifting. We later use a static_assert to -// verify that this worked correctly. -namespace { -const size_t kSSizeMax = kSSizeMaxConst; -} -#else // defined(NDEBUG) -// For efficiency, we really need kSSizeMax to be a constant. But for unit -// tests, it should be adjustable. This allows us to verify edge cases without -// having to fill the entire available address space. As a compromise, we make -// kSSizeMax adjustable in debug builds, and then only compile that particular -// part of the unit test in debug builds. -namespace { -static size_t kSSizeMax = kSSizeMaxConst; -} - -namespace internal { -void SetSafeSPrintfSSizeMaxForTest(size_t max) { - kSSizeMax = max; -} - -size_t GetSafeSPrintfSSizeMaxForTest() { - return kSSizeMax; -} -} -#endif // defined(NDEBUG) - -namespace { -class Buffer { - public: - // |buffer| is caller-allocated storage that SafeSPrintf() writes to. It - // has |size| bytes of writable storage. It is the caller's responsibility - // to ensure that the buffer is at least one byte in size, so that it fits - // the trailing NUL that will be added by the destructor. The buffer also - // must be smaller or equal to kSSizeMax in size. - Buffer(char* buffer, size_t size) - : buffer_(buffer), - size_(size - 1), // Account for trailing NUL byte - count_(0) { -// MSVS2013's standard library doesn't mark max() as constexpr yet. cl.exe -// supports static_cast but doesn't really implement constexpr yet so it doesn't -// complain, but clang does. -#if __cplusplus >= 201103 && !(defined(__clang__) && defined(OS_WIN)) - static_assert(kSSizeMaxConst == - static_cast<size_t>(std::numeric_limits<ssize_t>::max()), - "kSSizeMaxConst should be the max value of an ssize_t"); -#endif - DEBUG_CHECK(size > 0); - DEBUG_CHECK(size <= kSSizeMax); - } - - ~Buffer() { - // The code calling the constructor guaranteed that there was enough space - // to store a trailing NUL -- and in debug builds, we are actually - // verifying this with DEBUG_CHECK()s in the constructor. So, we can - // always unconditionally write the NUL byte in the destructor. We do not - // need to adjust the count_, as SafeSPrintf() copies snprintf() in not - // including the NUL byte in its return code. - *GetInsertionPoint() = '\000'; - } - - // Returns true, iff the buffer is filled all the way to |kSSizeMax-1|. The - // caller can now stop adding more data, as GetCount() has reached its - // maximum possible value. - inline bool OutOfAddressableSpace() const { - return count_ == static_cast<size_t>(kSSizeMax - 1); - } - - // Returns the number of bytes that would have been emitted to |buffer_| - // if it was sized sufficiently large. This number can be larger than - // |size_|, if the caller provided an insufficiently large output buffer. - // But it will never be bigger than |kSSizeMax-1|. - inline ssize_t GetCount() const { - DEBUG_CHECK(count_ < kSSizeMax); - return static_cast<ssize_t>(count_); - } - - // Emits one |ch| character into the |buffer_| and updates the |count_| of - // characters that are currently supposed to be in the buffer. - // Returns "false", iff the buffer was already full. - // N.B. |count_| increases even if no characters have been written. This is - // needed so that GetCount() can return the number of bytes that should - // have been allocated for the |buffer_|. - inline bool Out(char ch) { - if (size_ >= 1 && count_ < size_) { - buffer_[count_] = ch; - return IncrementCountByOne(); - } - // |count_| still needs to be updated, even if the buffer has been - // filled completely. This allows SafeSPrintf() to return the number of - // bytes that should have been emitted. - IncrementCountByOne(); - return false; - } - - // Inserts |padding|-|len| bytes worth of padding into the |buffer_|. - // |count_| will also be incremented by the number of bytes that were meant - // to be emitted. The |pad| character is typically either a ' ' space - // or a '0' zero, but other non-NUL values are legal. - // Returns "false", iff the the |buffer_| filled up (i.e. |count_| - // overflowed |size_|) at any time during padding. - inline bool Pad(char pad, size_t padding, size_t len) { - DEBUG_CHECK(pad); - DEBUG_CHECK(padding <= kSSizeMax); - for (; padding > len; --padding) { - if (!Out(pad)) { - if (--padding) { - IncrementCount(padding-len); - } - return false; - } - } - return true; - } - - // POSIX doesn't define any async-signal-safe function for converting - // an integer to ASCII. Define our own version. - // - // This also gives us the ability to make the function a little more - // powerful and have it deal with |padding|, with truncation, and with - // predicting the length of the untruncated output. - // - // IToASCII() converts an integer |i| to ASCII. - // - // Unlike similar functions in the standard C library, it never appends a - // NUL character. This is left for the caller to do. - // - // While the function signature takes a signed int64_t, the code decides at - // run-time whether to treat the argument as signed (int64_t) or as unsigned - // (uint64_t) based on the value of |sign|. - // - // It supports |base|s 2 through 16. Only a |base| of 10 is allowed to have - // a |sign|. Otherwise, |i| is treated as unsigned. - // - // For bases larger than 10, |upcase| decides whether lower-case or upper- - // case letters should be used to designate digits greater than 10. - // - // Padding can be done with either '0' zeros or ' ' spaces. Padding has to - // be positive and will always be applied to the left of the output. - // - // Prepends a |prefix| to the number (e.g. "0x"). This prefix goes to - // the left of |padding|, if |pad| is '0'; and to the right of |padding| - // if |pad| is ' '. - // - // Returns "false", if the |buffer_| overflowed at any time. - bool IToASCII(bool sign, bool upcase, int64_t i, int base, - char pad, size_t padding, const char* prefix); - - private: - // Increments |count_| by |inc| unless this would cause |count_| to - // overflow |kSSizeMax-1|. Returns "false", iff an overflow was detected; - // it then clamps |count_| to |kSSizeMax-1|. - inline bool IncrementCount(size_t inc) { - // "inc" is either 1 or a "padding" value. Padding is clamped at - // run-time to at most kSSizeMax-1. So, we know that "inc" is always in - // the range 1..kSSizeMax-1. - // This allows us to compute "kSSizeMax - 1 - inc" without incurring any - // integer overflows. - DEBUG_CHECK(inc <= kSSizeMax - 1); - if (count_ > kSSizeMax - 1 - inc) { - count_ = kSSizeMax - 1; - return false; - } else { - count_ += inc; - return true; - } - } - - // Convenience method for the common case of incrementing |count_| by one. - inline bool IncrementCountByOne() { - return IncrementCount(1); - } - - // Return the current insertion point into the buffer. This is typically - // at |buffer_| + |count_|, but could be before that if truncation - // happened. It always points to one byte past the last byte that was - // successfully placed into the |buffer_|. - inline char* GetInsertionPoint() const { - size_t idx = count_; - if (idx > size_) { - idx = size_; - } - return buffer_ + idx; - } - - // User-provided buffer that will receive the fully formatted output string. - char* buffer_; - - // Number of bytes that are available in the buffer excluding the trailing - // NUL byte that will be added by the destructor. - const size_t size_; - - // Number of bytes that would have been emitted to the buffer, if the buffer - // was sufficiently big. This number always excludes the trailing NUL byte - // and it is guaranteed to never grow bigger than kSSizeMax-1. - size_t count_; - - DISALLOW_COPY_AND_ASSIGN(Buffer); -}; - - -bool Buffer::IToASCII(bool sign, bool upcase, int64_t i, int base, - char pad, size_t padding, const char* prefix) { - // Sanity check for parameters. None of these should ever fail, but see - // above for the rationale why we can't call CHECK(). - DEBUG_CHECK(base >= 2); - DEBUG_CHECK(base <= 16); - DEBUG_CHECK(!sign || base == 10); - DEBUG_CHECK(pad == '0' || pad == ' '); - DEBUG_CHECK(padding <= kSSizeMax); - DEBUG_CHECK(!(sign && prefix && *prefix)); - - // Handle negative numbers, if the caller indicated that |i| should be - // treated as a signed number; otherwise treat |i| as unsigned (even if the - // MSB is set!) - // Details are tricky, because of limited data-types, but equivalent pseudo- - // code would look like: - // if (sign && i < 0) - // prefix = "-"; - // num = abs(i); - int minint = 0; - uint64_t num; - if (sign && i < 0) { - prefix = "-"; - - // Turn our number positive. - if (i == std::numeric_limits<int64_t>::min()) { - // The most negative integer needs special treatment. - minint = 1; - num = static_cast<uint64_t>(-(i + 1)); - } else { - // "Normal" negative numbers are easy. - num = static_cast<uint64_t>(-i); - } - } else { - num = static_cast<uint64_t>(i); - } - - // If padding with '0' zero, emit the prefix or '-' character now. Otherwise, - // make the prefix accessible in reverse order, so that we can later output - // it right between padding and the number. - // We cannot choose the easier approach of just reversing the number, as that - // fails in situations where we need to truncate numbers that have padding - // and/or prefixes. - const char* reverse_prefix = nullptr; - if (prefix && *prefix) { - if (pad == '0') { - while (*prefix) { - if (padding) { - --padding; - } - Out(*prefix++); - } - prefix = nullptr; - } else { - for (reverse_prefix = prefix; *reverse_prefix; ++reverse_prefix) { - } - } - } else - prefix = nullptr; - const size_t prefix_length = reverse_prefix - prefix; - - // Loop until we have converted the entire number. Output at least one - // character (i.e. '0'). - size_t start = count_; - size_t discarded = 0; - bool started = false; - do { - // Make sure there is still enough space left in our output buffer. - if (count_ >= size_) { - if (start < size_) { - // It is rare that we need to output a partial number. But if asked - // to do so, we will still make sure we output the correct number of - // leading digits. - // Since we are generating the digits in reverse order, we actually - // have to discard digits in the order that we have already emitted - // them. This is essentially equivalent to: - // memmove(buffer_ + start, buffer_ + start + 1, size_ - start - 1) - for (char* move = buffer_ + start, *end = buffer_ + size_ - 1; - move < end; - ++move) { - *move = move[1]; - } - ++discarded; - --count_; - } else if (count_ - size_ > 1) { - // Need to increment either |count_| or |discarded| to make progress. - // The latter is more efficient, as it eventually triggers fast - // handling of padding. But we have to ensure we don't accidentally - // change the overall state (i.e. switch the state-machine from - // discarding to non-discarding). |count_| needs to always stay - // bigger than |size_|. - --count_; - ++discarded; - } - } - - // Output the next digit and (if necessary) compensate for the most - // negative integer needing special treatment. This works because, - // no matter the bit width of the integer, the lowest-most decimal - // integer always ends in 2, 4, 6, or 8. - if (!num && started) { - if (reverse_prefix > prefix) { - Out(*--reverse_prefix); - } else { - Out(pad); - } - } else { - started = true; - Out((upcase ? kUpCaseHexDigits : kDownCaseHexDigits)[num%base + minint]); - } - - minint = 0; - num /= base; - - // Add padding, if requested. - if (padding > 0) { - --padding; - - // Performance optimization for when we are asked to output excessive - // padding, but our output buffer is limited in size. Even if we output - // a 64bit number in binary, we would never write more than 64 plus - // prefix non-padding characters. So, once this limit has been passed, - // any further state change can be computed arithmetically; we know that - // by this time, our entire final output consists of padding characters - // that have all already been output. - if (discarded > 8*sizeof(num) + prefix_length) { - IncrementCount(padding); - padding = 0; - } - } - } while (num || padding || (reverse_prefix > prefix)); - - // Conversion to ASCII actually resulted in the digits being in reverse - // order. We can't easily generate them in forward order, as we can't tell - // the number of characters needed until we are done converting. - // So, now, we reverse the string (except for the possible '-' sign). - char* front = buffer_ + start; - char* back = GetInsertionPoint(); - while (--back > front) { - char ch = *back; - *back = *front; - *front++ = ch; - } - - IncrementCount(discarded); - return !discarded; -} - -} // anonymous namespace - -namespace internal { - -ssize_t SafeSNPrintf(char* buf, size_t sz, const char* fmt, const Arg* args, - const size_t max_args) { - // Make sure that at least one NUL byte can be written, and that the buffer - // never overflows kSSizeMax. Not only does that use up most or all of the - // address space, it also would result in a return code that cannot be - // represented. - if (static_cast<ssize_t>(sz) < 1) { - return -1; - } else if (sz > kSSizeMax) { - sz = kSSizeMax; - } - - // Iterate over format string and interpret '%' arguments as they are - // encountered. - Buffer buffer(buf, sz); - size_t padding; - char pad; - for (unsigned int cur_arg = 0; *fmt && !buffer.OutOfAddressableSpace(); ) { - if (*fmt++ == '%') { - padding = 0; - pad = ' '; - char ch = *fmt++; - format_character_found: - switch (ch) { - case '0': case '1': case '2': case '3': case '4': - case '5': case '6': case '7': case '8': case '9': - // Found a width parameter. Convert to an integer value and store in - // "padding". If the leading digit is a zero, change the padding - // character from a space ' ' to a zero '0'. - pad = ch == '0' ? '0' : ' '; - for (;;) { - // The maximum allowed padding fills all the available address - // space and leaves just enough space to insert the trailing NUL. - const size_t max_padding = kSSizeMax - 1; - if (padding > max_padding/10 || - 10*padding > max_padding - (ch - '0')) { - DEBUG_CHECK(padding <= max_padding/10 && - 10*padding <= max_padding - (ch - '0')); - // Integer overflow detected. Skip the rest of the width until - // we find the format character, then do the normal error handling. - padding_overflow: - padding = max_padding; - while ((ch = *fmt++) >= '0' && ch <= '9') { - } - if (cur_arg < max_args) { - ++cur_arg; - } - goto fail_to_expand; - } - padding = 10*padding + ch - '0'; - if (padding > max_padding) { - // This doesn't happen for "sane" values of kSSizeMax. But once - // kSSizeMax gets smaller than about 10, our earlier range checks - // are incomplete. Unittests do trigger this artificial corner - // case. - DEBUG_CHECK(padding <= max_padding); - goto padding_overflow; - } - ch = *fmt++; - if (ch < '0' || ch > '9') { - // Reached the end of the width parameter. This is where the format - // character is found. - goto format_character_found; - } - } - break; - case 'c': { // Output an ASCII character. - // Check that there are arguments left to be inserted. - if (cur_arg >= max_args) { - DEBUG_CHECK(cur_arg < max_args); - goto fail_to_expand; - } - - // Check that the argument has the expected type. - const Arg& arg = args[cur_arg++]; - if (arg.type != Arg::INT && arg.type != Arg::UINT) { - DEBUG_CHECK(arg.type == Arg::INT || arg.type == Arg::UINT); - goto fail_to_expand; - } - - // Apply padding, if needed. - buffer.Pad(' ', padding, 1); - - // Convert the argument to an ASCII character and output it. - char as_char = static_cast<char>(arg.integer.i); - if (!as_char) { - goto end_of_output_buffer; - } - buffer.Out(as_char); - break; } - case 'd': // Output a possibly signed decimal value. - case 'o': // Output an unsigned octal value. - case 'x': // Output an unsigned hexadecimal value. - case 'X': - case 'p': { // Output a pointer value. - // Check that there are arguments left to be inserted. - if (cur_arg >= max_args) { - DEBUG_CHECK(cur_arg < max_args); - goto fail_to_expand; - } - - const Arg& arg = args[cur_arg++]; - int64_t i; - const char* prefix = nullptr; - if (ch != 'p') { - // Check that the argument has the expected type. - if (arg.type != Arg::INT && arg.type != Arg::UINT) { - DEBUG_CHECK(arg.type == Arg::INT || arg.type == Arg::UINT); - goto fail_to_expand; - } - i = arg.integer.i; - - if (ch != 'd') { - // The Arg() constructor automatically performed sign expansion on - // signed parameters. This is great when outputting a %d decimal - // number, but can result in unexpected leading 0xFF bytes when - // outputting a %x hexadecimal number. Mask bits, if necessary. - // We have to do this here, instead of in the Arg() constructor, as - // the Arg() constructor cannot tell whether we will output a %d - // or a %x. Only the latter should experience masking. - if (arg.integer.width < sizeof(int64_t)) { - i &= (1LL << (8*arg.integer.width)) - 1; - } - } - } else { - // Pointer values require an actual pointer or a string. - if (arg.type == Arg::POINTER) { - i = reinterpret_cast<uintptr_t>(arg.ptr); - } else if (arg.type == Arg::STRING) { - i = reinterpret_cast<uintptr_t>(arg.str); - } else if (arg.type == Arg::INT && - arg.integer.width == sizeof(NULL) && - arg.integer.i == 0) { // Allow C++'s version of NULL - i = 0; - } else { - DEBUG_CHECK(arg.type == Arg::POINTER || arg.type == Arg::STRING); - goto fail_to_expand; - } - - // Pointers always include the "0x" prefix. - prefix = "0x"; - } - - // Use IToASCII() to convert to ASCII representation. For decimal - // numbers, optionally print a sign. For hexadecimal numbers, - // distinguish between upper and lower case. %p addresses are always - // printed as upcase. Supports base 8, 10, and 16. Prints padding - // and/or prefixes, if so requested. - buffer.IToASCII(ch == 'd' && arg.type == Arg::INT, - ch != 'x', i, - ch == 'o' ? 8 : ch == 'd' ? 10 : 16, - pad, padding, prefix); - break; } - case 's': { - // Check that there are arguments left to be inserted. - if (cur_arg >= max_args) { - DEBUG_CHECK(cur_arg < max_args); - goto fail_to_expand; - } - - // Check that the argument has the expected type. - const Arg& arg = args[cur_arg++]; - const char *s; - if (arg.type == Arg::STRING) { - s = arg.str ? arg.str : "<NULL>"; - } else if (arg.type == Arg::INT && arg.integer.width == sizeof(NULL) && - arg.integer.i == 0) { // Allow C++'s version of NULL - s = "<NULL>"; - } else { - DEBUG_CHECK(arg.type == Arg::STRING); - goto fail_to_expand; - } - - // Apply padding, if needed. This requires us to first check the - // length of the string that we are outputting. - if (padding) { - size_t len = 0; - for (const char* src = s; *src++; ) { - ++len; - } - buffer.Pad(' ', padding, len); - } - - // Printing a string involves nothing more than copying it into the - // output buffer and making sure we don't output more bytes than - // available space; Out() takes care of doing that. - for (const char* src = s; *src; ) { - buffer.Out(*src++); - } - break; } - case '%': - // Quoted percent '%' character. - goto copy_verbatim; - fail_to_expand: - // C++ gives us tools to do type checking -- something that snprintf() - // could never really do. So, whenever we see arguments that don't - // match up with the format string, we refuse to output them. But - // since we have to be extremely conservative about being async- - // signal-safe, we are limited in the type of error handling that we - // can do in production builds (in debug builds we can use - // DEBUG_CHECK() and hope for the best). So, all we do is pass the - // format string unchanged. That should eventually get the user's - // attention; and in the meantime, it hopefully doesn't lose too much - // data. - default: - // Unknown or unsupported format character. Just copy verbatim to - // output. - buffer.Out('%'); - DEBUG_CHECK(ch); - if (!ch) { - goto end_of_format_string; - } - buffer.Out(ch); - break; - } - } else { - copy_verbatim: - buffer.Out(fmt[-1]); - } - } - end_of_format_string: - end_of_output_buffer: - return buffer.GetCount(); -} - -} // namespace internal - -ssize_t SafeSNPrintf(char* buf, size_t sz, const char* fmt) { - // Make sure that at least one NUL byte can be written, and that the buffer - // never overflows kSSizeMax. Not only does that use up most or all of the - // address space, it also would result in a return code that cannot be - // represented. - if (static_cast<ssize_t>(sz) < 1) { - return -1; - } else if (sz > kSSizeMax) { - sz = kSSizeMax; - } - - Buffer buffer(buf, sz); - - // In the slow-path, we deal with errors by copying the contents of - // "fmt" unexpanded. This means, if there are no arguments passed, the - // SafeSPrintf() function always degenerates to a version of strncpy() that - // de-duplicates '%' characters. - const char* src = fmt; - for (; *src; ++src) { - buffer.Out(*src); - DEBUG_CHECK(src[0] != '%' || src[1] == '%'); - if (src[0] == '%' && src[1] == '%') { - ++src; - } - } - return buffer.GetCount(); -} - -} // namespace strings -} // namespace base
diff --git a/base/strings/safe_sprintf.h b/base/strings/safe_sprintf.h deleted file mode 100644 index 56a6eaf..0000000 --- a/base/strings/safe_sprintf.h +++ /dev/null
@@ -1,246 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_STRINGS_SAFE_SPRINTF_H_ -#define BASE_STRINGS_SAFE_SPRINTF_H_ - -#include "build_config.h" - -#include <stddef.h> -#include <stdint.h> -#include <stdlib.h> - -#if defined(OS_POSIX) || defined(OS_FUCHSIA) -// For ssize_t -#include <unistd.h> -#endif - -#include "base/base_export.h" - -namespace base { -namespace strings { - -#if defined(COMPILER_MSVC) -// Define ssize_t inside of our namespace. -#if defined(_WIN64) -typedef __int64 ssize_t; -#else -typedef long ssize_t; -#endif -#endif - -// SafeSPrintf() is a type-safe and completely self-contained version of -// snprintf(). -// -// SafeSNPrintf() is an alternative function signature that can be used when -// not dealing with fixed-sized buffers. When possible, SafeSPrintf() should -// always be used instead of SafeSNPrintf() -// -// These functions allow for formatting complicated messages from contexts that -// require strict async-signal-safety. In fact, it is safe to call them from -// any low-level execution context, as they are guaranteed to make no library -// or system calls. It deliberately never touches "errno", either. -// -// The only exception to this rule is that in debug builds the code calls -// RAW_CHECK() to help diagnose problems when the format string does not -// match the rest of the arguments. In release builds, no CHECK()s are used, -// and SafeSPrintf() instead returns an output string that expands only -// those arguments that match their format characters. Mismatched arguments -// are ignored. -// -// The code currently only supports a subset of format characters: -// %c, %o, %d, %x, %X, %p, and %s. -// -// SafeSPrintf() aims to be as liberal as reasonably possible. Integer-like -// values of arbitrary width can be passed to all of the format characters -// that expect integers. Thus, it is explicitly legal to pass an "int" to -// "%c", and output will automatically look at the LSB only. It is also -// explicitly legal to pass either signed or unsigned values, and the format -// characters will automatically interpret the arguments accordingly. -// -// It is still not legal to mix-and-match integer-like values with pointer -// values. For instance, you cannot pass a pointer to %x, nor can you pass an -// integer to %p. -// -// The one exception is "0" zero being accepted by "%p". This works-around -// the problem of C++ defining NULL as an integer-like value. -// -// All format characters take an optional width parameter. This must be a -// positive integer. For %d, %o, %x, %X and %p, if the width starts with -// a leading '0', padding is done with '0' instead of ' ' characters. -// -// There are a few features of snprintf()-style format strings, that -// SafeSPrintf() does not support at this time. -// -// If an actual user showed up, there is no particularly strong reason they -// couldn't be added. But that assumes that the trade-offs between complexity -// and utility are favorable. -// -// For example, adding support for negative padding widths, and for %n are all -// likely to be viewed positively. They are all clearly useful, low-risk, easy -// to test, don't jeopardize the async-signal-safety of the code, and overall -// have little impact on other parts of SafeSPrintf() function. -// -// On the other hands, adding support for alternate forms, positional -// arguments, grouping, wide characters, localization or floating point numbers -// are all unlikely to ever be added. -// -// SafeSPrintf() and SafeSNPrintf() mimic the behavior of snprintf() and they -// return the number of bytes needed to store the untruncated output. This -// does *not* include the terminating NUL byte. -// -// They return -1, iff a fatal error happened. This typically can only happen, -// if the buffer size is a) negative, or b) zero (i.e. not even the NUL byte -// can be written). The return value can never be larger than SSIZE_MAX-1. -// This ensures that the caller can always add one to the signed return code -// in order to determine the amount of storage that needs to be allocated. -// -// While the code supports type checking and while it is generally very careful -// to avoid printing incorrect values, it tends to be conservative in printing -// as much as possible, even when given incorrect parameters. Typically, in -// case of an error, the format string will not be expanded. (i.e. something -// like SafeSPrintf(buf, "%p %d", 1, 2) results in "%p 2"). See above for -// the use of RAW_CHECK() in debug builds, though. -// -// Basic example: -// char buf[20]; -// base::strings::SafeSPrintf(buf, "The answer: %2d", 42); -// -// Example with dynamically sized buffer (async-signal-safe). This code won't -// work on Visual studio, as it requires dynamically allocating arrays on the -// stack. Consider picking a smaller value for |kMaxSize| if stack size is -// limited and known. On the other hand, if the parameters to SafeSNPrintf() -// are trusted and not controllable by the user, you can consider eliminating -// the check for |kMaxSize| altogether. The current value of SSIZE_MAX is -// essentially a no-op that just illustrates how to implement an upper bound: -// const size_t kInitialSize = 128; -// const size_t kMaxSize = std::numeric_limits<ssize_t>::max(); -// size_t size = kInitialSize; -// for (;;) { -// char buf[size]; -// size = SafeSNPrintf(buf, size, "Error message \"%s\"\n", err) + 1; -// if (sizeof(buf) < kMaxSize && size > kMaxSize) { -// size = kMaxSize; -// continue; -// } else if (size > sizeof(buf)) -// continue; -// write(2, buf, size-1); -// break; -// } - -namespace internal { -// Helpers that use C++ overloading, templates, and specializations to deduce -// and record type information from function arguments. This allows us to -// later write a type-safe version of snprintf(). - -struct Arg { - enum Type { INT, UINT, STRING, POINTER }; - - // Any integer-like value. - Arg(signed char c) : type(INT) { - integer.i = c; - integer.width = sizeof(char); - } - Arg(unsigned char c) : type(UINT) { - integer.i = c; - integer.width = sizeof(char); - } - Arg(signed short j) : type(INT) { - integer.i = j; - integer.width = sizeof(short); - } - Arg(unsigned short j) : type(UINT) { - integer.i = j; - integer.width = sizeof(short); - } - Arg(signed int j) : type(INT) { - integer.i = j; - integer.width = sizeof(int); - } - Arg(unsigned int j) : type(UINT) { - integer.i = j; - integer.width = sizeof(int); - } - Arg(signed long j) : type(INT) { - integer.i = j; - integer.width = sizeof(long); - } - Arg(unsigned long j) : type(UINT) { - integer.i = j; - integer.width = sizeof(long); - } - Arg(signed long long j) : type(INT) { - integer.i = j; - integer.width = sizeof(long long); - } - Arg(unsigned long long j) : type(UINT) { - integer.i = j; - integer.width = sizeof(long long); - } - - // A C-style text string. - Arg(const char* s) : str(s), type(STRING) { } - Arg(char* s) : str(s), type(STRING) { } - - // Any pointer value that can be cast to a "void*". - template<class T> Arg(T* p) : ptr((void*)p), type(POINTER) { } - - union { - // An integer-like value. - struct { - int64_t i; - unsigned char width; - } integer; - - // A C-style text string. - const char* str; - - // A pointer to an arbitrary object. - const void* ptr; - }; - const enum Type type; -}; - -// This is the internal function that performs the actual formatting of -// an snprintf()-style format string. -BASE_EXPORT ssize_t SafeSNPrintf(char* buf, size_t sz, const char* fmt, - const Arg* args, size_t max_args); - -#if !defined(NDEBUG) -// In debug builds, allow unit tests to artificially lower the kSSizeMax -// constant that is used as a hard upper-bound for all buffers. In normal -// use, this constant should always be std::numeric_limits<ssize_t>::max(). -BASE_EXPORT void SetSafeSPrintfSSizeMaxForTest(size_t max); -BASE_EXPORT size_t GetSafeSPrintfSSizeMaxForTest(); -#endif - -} // namespace internal - -template<typename... Args> -ssize_t SafeSNPrintf(char* buf, size_t N, const char* fmt, Args... args) { - // Use Arg() object to record type information and then copy arguments to an - // array to make it easier to iterate over them. - const internal::Arg arg_array[] = { args... }; - return internal::SafeSNPrintf(buf, N, fmt, arg_array, sizeof...(args)); -} - -template<size_t N, typename... Args> -ssize_t SafeSPrintf(char (&buf)[N], const char* fmt, Args... args) { - // Use Arg() object to record type information and then copy arguments to an - // array to make it easier to iterate over them. - const internal::Arg arg_array[] = { args... }; - return internal::SafeSNPrintf(buf, N, fmt, arg_array, sizeof...(args)); -} - -// Fast-path when we don't actually need to substitute any arguments. -BASE_EXPORT ssize_t SafeSNPrintf(char* buf, size_t N, const char* fmt); -template<size_t N> -inline ssize_t SafeSPrintf(char (&buf)[N], const char* fmt) { - return SafeSNPrintf(buf, N, fmt); -} - -} // namespace strings -} // namespace base - -#endif // BASE_STRINGS_SAFE_SPRINTF_H_
diff --git a/base/strings/strcat.cc b/base/strings/strcat.cc deleted file mode 100644 index 3d5b2ca..0000000 --- a/base/strings/strcat.cc +++ /dev/null
@@ -1,81 +0,0 @@ -// Copyright 2017 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/strings/strcat.h" - -namespace base { - -namespace { - -// Reserves an additional amount of size in the given string, growing by at -// least 2x. Used by StrAppend(). -// -// The "at least 2x" growing rule duplicates the exponential growth of -// std::string. The problem is that most implementations of reserve() will grow -// exactly to the requested amount instead of exponentially growing like would -// happen when appending normally. If we didn't do this, an append after the -// call to StrAppend() would definitely cause a reallocation, and loops with -// StrAppend() calls would have O(n^2) complexity to execute. Instead, we want -// StrAppend() to have the same semantics as std::string::append(). -// -// If the string is empty, we assume that exponential growth is not necessary. -template <typename String> -void ReserveAdditional(String* str, typename String::size_type additional) { - str->reserve(std::max(str->size() + additional, str->size() * 2)); -} - -template <typename DestString, typename InputString> -void StrAppendT(DestString* dest, span<const InputString> pieces) { - size_t additional_size = 0; - for (const auto& cur : pieces) - additional_size += cur.size(); - ReserveAdditional(dest, additional_size); - - for (const auto& cur : pieces) - dest->append(cur.data(), cur.size()); -} - -} // namespace - -std::string StrCat(span<const StringPiece> pieces) { - std::string result; - StrAppendT(&result, pieces); - return result; -} - -string16 StrCat(span<const StringPiece16> pieces) { - string16 result; - StrAppendT(&result, pieces); - return result; -} - -std::string StrCat(span<const std::string> pieces) { - std::string result; - StrAppendT(&result, pieces); - return result; -} - -string16 StrCat(span<const string16> pieces) { - string16 result; - StrAppendT(&result, pieces); - return result; -} - -void StrAppend(std::string* dest, span<const StringPiece> pieces) { - StrAppendT(dest, pieces); -} - -void StrAppend(string16* dest, span<const StringPiece16> pieces) { - StrAppendT(dest, pieces); -} - -void StrAppend(std::string* dest, span<const std::string> pieces) { - StrAppendT(dest, pieces); -} - -void StrAppend(string16* dest, span<const string16> pieces) { - StrAppendT(dest, pieces); -} - -} // namespace base
diff --git a/base/strings/strcat.h b/base/strings/strcat.h deleted file mode 100644 index b2fcaae..0000000 --- a/base/strings/strcat.h +++ /dev/null
@@ -1,99 +0,0 @@ -// Copyright 2017 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_STRINGS_STRCAT_H_ -#define BASE_STRINGS_STRCAT_H_ - -#include <initializer_list> - -#include "base/base_export.h" -#include "base/compiler_specific.h" -#include "base/containers/span.h" -#include "base/strings/string_piece.h" -#include "build_config.h" - -#if defined(OS_WIN) -// To resolve a conflict with Win32 API StrCat macro. -#include "base/win/windows_types.h" -#endif - -namespace base { - -// StrCat ---------------------------------------------------------------------- -// -// StrCat is a function to perform concatenation on a sequence of strings. -// It is preferrable to a sequence of "a + b + c" because it is both faster and -// generates less code. -// -// std::string result = base::StrCat({"foo ", result, "\nfoo ", bar}); -// -// To join an array of strings with a separator, see base::JoinString in -// base/strings/string_util.h. -// -// MORE INFO -// -// StrCat can see all arguments at once, so it can allocate one return buffer -// of exactly the right size and copy once, as opposed to a sequence of -// operator+ which generates a series of temporary strings, copying as it goes. -// And by using StringPiece arguments, StrCat can avoid creating temporary -// string objects for char* constants. -// -// ALTERNATIVES -// -// Internal Google / Abseil has a similar StrCat function. That version takes -// an overloaded number of arguments instead of initializer list (overflowing -// to initializer list for many arguments). We don't have any legacy -// requirements and using only initializer_list is simpler and generates -// roughly the same amount of code at the call sites. -// -// Abseil's StrCat also allows numbers by using an intermediate class that can -// be implicitly constructed from either a string or various number types. This -// class formats the numbers into a static buffer for increased performance, -// and the call sites look nice. -// -// As-written Abseil's helper class for numbers generates slightly more code -// than the raw StringPiece version. We can de-inline the helper class' -// constructors which will cause the StringPiece constructors to be de-inlined -// for this call and generate slightly less code. This is something we can -// explore more in the future. - -BASE_EXPORT std::string StrCat(span<const StringPiece> pieces); -BASE_EXPORT string16 StrCat(span<const StringPiece16> pieces); -BASE_EXPORT std::string StrCat(span<const std::string> pieces); -BASE_EXPORT string16 StrCat(span<const string16> pieces); - -// Initializer list forwards to the array version. -inline std::string StrCat(std::initializer_list<StringPiece> pieces) { - return StrCat(make_span(pieces.begin(), pieces.size())); -} -inline string16 StrCat(std::initializer_list<StringPiece16> pieces) { - return StrCat(make_span(pieces.begin(), pieces.size())); -} - -// StrAppend ------------------------------------------------------------------- -// -// Appends a sequence of strings to a destination. Prefer: -// StrAppend(&foo, ...); -// over: -// foo += StrCat(...); -// because it avoids a temporary string allocation and copy. - -BASE_EXPORT void StrAppend(std::string* dest, span<const StringPiece> pieces); -BASE_EXPORT void StrAppend(string16* dest, span<const StringPiece16> pieces); -BASE_EXPORT void StrAppend(std::string* dest, span<const std::string> pieces); -BASE_EXPORT void StrAppend(string16* dest, span<const string16> pieces); - -// Initializer list forwards to the array version. -inline void StrAppend(std::string* dest, - std::initializer_list<StringPiece> pieces) { - return StrAppend(dest, make_span(pieces.begin(), pieces.size())); -} -inline void StrAppend(string16* dest, - std::initializer_list<StringPiece16> pieces) { - return StrAppend(dest, make_span(pieces.begin(), pieces.size())); -} - -} // namespace base - -#endif // BASE_STRINGS_STRCAT_H_
diff --git a/base/strings/string_number_conversions_fuzzer.cc b/base/strings/string_number_conversions_fuzzer.cc deleted file mode 100644 index 2fed7de..0000000 --- a/base/strings/string_number_conversions_fuzzer.cc +++ /dev/null
@@ -1,67 +0,0 @@ -// Copyright 2015 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include <stddef.h> -#include <stdint.h> - -#include <string> -#include <vector> - -#include "base/strings/string_number_conversions.h" - -// Entry point for LibFuzzer. -extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) { - base::StringPiece string_piece_input(reinterpret_cast<const char*>(data), - size); - std::string string_input(reinterpret_cast<const char*>(data), size); - - int out_int; - base::StringToInt(string_piece_input, &out_int); - unsigned out_uint; - base::StringToUint(string_piece_input, &out_uint); - int64_t out_int64; - base::StringToInt64(string_piece_input, &out_int64); - uint64_t out_uint64; - base::StringToUint64(string_piece_input, &out_uint64); - size_t out_size; - base::StringToSizeT(string_piece_input, &out_size); - - // Test for StringPiece16 if size is even. - if (size % 2 == 0) { - base::StringPiece16 string_piece_input16( - reinterpret_cast<const base::char16*>(data), size / 2); - - base::StringToInt(string_piece_input16, &out_int); - base::StringToUint(string_piece_input16, &out_uint); - base::StringToInt64(string_piece_input16, &out_int64); - base::StringToUint64(string_piece_input16, &out_uint64); - base::StringToSizeT(string_piece_input16, &out_size); - } - - double out_double; - base::StringToDouble(string_input, &out_double); - - base::HexStringToInt(string_piece_input, &out_int); - base::HexStringToUInt(string_piece_input, &out_uint); - base::HexStringToInt64(string_piece_input, &out_int64); - base::HexStringToUInt64(string_piece_input, &out_uint64); - std::vector<uint8_t> out_bytes; - base::HexStringToBytes(string_piece_input, &out_bytes); - - base::HexEncode(data, size); - - // Convert the numbers back to strings. - base::NumberToString(out_int); - base::NumberToString16(out_int); - base::NumberToString(out_uint); - base::NumberToString16(out_uint); - base::NumberToString(out_int64); - base::NumberToString16(out_int64); - base::NumberToString(out_uint64); - base::NumberToString16(out_uint64); - base::NumberToString(out_double); - base::NumberToString16(out_double); - - return 0; -}
diff --git a/base/strings/string_tokenizer_fuzzer.cc b/base/strings/string_tokenizer_fuzzer.cc deleted file mode 100644 index 917041b..0000000 --- a/base/strings/string_tokenizer_fuzzer.cc +++ /dev/null
@@ -1,56 +0,0 @@ -// Copyright 2015 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include <stddef.h> -#include <stdint.h> - -#include <string> - -#include "base/strings/string_tokenizer.h" - -void GetAllTokens(base::StringTokenizer& t) { - while (t.GetNext()) { - (void)t.token(); - } -} - -// Entry point for LibFuzzer. -extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) { - uint8_t size_t_bytes = sizeof(size_t); - if (size < size_t_bytes + 1) { - return 0; - } - - // Calculate pattern size based on remaining bytes, otherwise fuzzing is - // inefficient with bailouts in most cases. - size_t pattern_size = - *reinterpret_cast<const size_t*>(data) % (size - size_t_bytes); - - std::string pattern(reinterpret_cast<const char*>(data + size_t_bytes), - pattern_size); - std::string input( - reinterpret_cast<const char*>(data + size_t_bytes + pattern_size), - size - pattern_size - size_t_bytes); - - // Allow quote_chars and options to be set. Otherwise full coverage - // won't be possible since IsQuote, FullGetNext and other functions - // won't be called. - base::StringTokenizer t(input, pattern); - GetAllTokens(t); - - base::StringTokenizer t_quote(input, pattern); - t_quote.set_quote_chars("\""); - GetAllTokens(t_quote); - - base::StringTokenizer t_options(input, pattern); - t_options.set_options(base::StringTokenizer::RETURN_DELIMS); - GetAllTokens(t_options); - - base::StringTokenizer t_quote_and_options(input, pattern); - t_quote_and_options.set_quote_chars("\""); - t_quote_and_options.set_options(base::StringTokenizer::RETURN_DELIMS); - GetAllTokens(t_quote_and_options); - - return 0; -}
diff --git a/base/strings/utf_string_conversions_fuzzer.cc b/base/strings/utf_string_conversions_fuzzer.cc deleted file mode 100644 index 37d4be2..0000000 --- a/base/strings/utf_string_conversions_fuzzer.cc +++ /dev/null
@@ -1,56 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/strings/string_util.h" -#include "base/strings/utf_string_conversions.h" - -std::string output_std_string; -std::wstring output_std_wstring; -base::string16 output_string16; - -// Entry point for LibFuzzer. -extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) { - base::StringPiece string_piece_input(reinterpret_cast<const char*>(data), - size); - - base::UTF8ToWide(string_piece_input); - base::UTF8ToWide(reinterpret_cast<const char*>(data), size, - &output_std_wstring); - base::UTF8ToUTF16(string_piece_input); - base::UTF8ToUTF16(reinterpret_cast<const char*>(data), size, - &output_string16); - - // Test for char16. - if (size % 2 == 0) { - base::StringPiece16 string_piece_input16( - reinterpret_cast<const base::char16*>(data), size / 2); - base::UTF16ToWide(output_string16); - base::UTF16ToWide(reinterpret_cast<const base::char16*>(data), size / 2, - &output_std_wstring); - base::UTF16ToUTF8(string_piece_input16); - base::UTF16ToUTF8(reinterpret_cast<const base::char16*>(data), size / 2, - &output_std_string); - } - - // Test for wchar_t. - size_t wchar_t_size = sizeof(wchar_t); - if (size % wchar_t_size == 0) { - base::WideToUTF8(output_std_wstring); - base::WideToUTF8(reinterpret_cast<const wchar_t*>(data), - size / wchar_t_size, &output_std_string); - base::WideToUTF16(output_std_wstring); - base::WideToUTF16(reinterpret_cast<const wchar_t*>(data), - size / wchar_t_size, &output_string16); - } - - // Test for ASCII. This condition is needed to avoid hitting instant CHECK - // failures. - if (base::IsStringASCII(string_piece_input)) { - output_string16 = base::ASCIIToUTF16(string_piece_input); - base::StringPiece16 string_piece_input16(output_string16); - base::UTF16ToASCII(string_piece_input16); - } - - return 0; -}
diff --git a/base/strings/utf_string_conversions_regression_fuzzer.cc b/base/strings/utf_string_conversions_regression_fuzzer.cc deleted file mode 100644 index ca6b4a2..0000000 --- a/base/strings/utf_string_conversions_regression_fuzzer.cc +++ /dev/null
@@ -1,105 +0,0 @@ -// Copyright (c) 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/logging.h" -#include "base/strings/old_utf_string_conversions.h" -#include "base/strings/utf_string_conversions.h" - -namespace { - -void UTF8ToCheck(const uint8_t* data, size_t size) { - const auto* src = reinterpret_cast<const char*>(data); - const size_t src_len = size; - - // UTF16 - { - base::string16 new_out; - bool new_res = base::UTF8ToUTF16(src, src_len, &new_out); - - base::string16 old_out; - bool old_res = base_old::UTF8ToUTF16(src, src_len, &old_out); - - CHECK(new_res == old_res); - CHECK(new_out == old_out); - } - - // Wide - { - std::wstring new_out; - bool new_res = base::UTF8ToWide(src, src_len, &new_out); - - std::wstring old_out; - bool old_res = base_old::UTF8ToWide(src, src_len, &old_out); - - CHECK(new_res == old_res); - CHECK(new_out == old_out); - } -} - -void UTF16ToCheck(const uint8_t* data, size_t size) { - const auto* src = reinterpret_cast<const base::char16*>(data); - const size_t src_len = size / 2; - - // UTF8 - { - std::string new_out; - bool new_res = base::UTF16ToUTF8(src, src_len, &new_out); - - std::string old_out; - bool old_res = base_old::UTF16ToUTF8(src, src_len, &old_out); - - CHECK(new_res == old_res); - CHECK(new_out == old_out); - } - - // Wide - { - std::wstring new_out; - bool new_res = base::UTF16ToWide(src, src_len, &new_out); - - std::wstring old_out; - bool old_res = base_old::UTF16ToWide(src, src_len, &old_out); - - CHECK(new_res == old_res); - CHECK(new_out == old_out); - } -} - -void WideToCheck(const uint8_t* data, size_t size) { - const auto* src = reinterpret_cast<const wchar_t*>(data); - const size_t src_len = size / 4; // It's OK even if Wide is 16bit. - - // UTF8 - { - std::string new_out; - bool new_res = base::WideToUTF8(src, src_len, &new_out); - - std::string old_out; - bool old_res = base_old::WideToUTF8(src, src_len, &old_out); - - CHECK(new_res == old_res); - CHECK(new_out == old_out); - } - - // UTF16 - { - base::string16 new_out; - bool new_res = base::WideToUTF16(src, src_len, &new_out); - - base::string16 old_out; - bool old_res = base_old::WideToUTF16(src, src_len, &old_out); - - CHECK(new_res == old_res); - CHECK(new_out == old_out); - } -} - -} // namespace - -extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) { - UTF8ToCheck(data, size); - UTF16ToCheck(data, size); - WideToCheck(data, size); - return 0; -}
diff --git a/base/synchronization/atomic_flag.cc b/base/synchronization/atomic_flag.cc deleted file mode 100644 index 6cc0e87..0000000 --- a/base/synchronization/atomic_flag.cc +++ /dev/null
@@ -1,26 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/synchronization/atomic_flag.h" - -#include "base/logging.h" - -namespace base { - -AtomicFlag::AtomicFlag() { -} - -void AtomicFlag::Set() { - base::subtle::Release_Store(&flag_, 1); -} - -bool AtomicFlag::IsSet() const { - return base::subtle::Acquire_Load(&flag_) != 0; -} - -void AtomicFlag::UnsafeResetForTesting() { - base::subtle::Release_Store(&flag_, 0); -} - -} // namespace base
diff --git a/base/synchronization/atomic_flag.h b/base/synchronization/atomic_flag.h deleted file mode 100644 index d033054..0000000 --- a/base/synchronization/atomic_flag.h +++ /dev/null
@@ -1,42 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_SYNCHRONIZATION_ATOMIC_FLAG_H_ -#define BASE_SYNCHRONIZATION_ATOMIC_FLAG_H_ - -#include "base/atomicops.h" -#include "base/base_export.h" -#include "base/macros.h" - -namespace base { - -// A flag that can safely be set from one thread and read from other threads. -// -// This class IS NOT intended for synchronization between threads. -class BASE_EXPORT AtomicFlag { - public: - AtomicFlag(); - ~AtomicFlag() = default; - - // Set the flag. Must always be called from the same sequence. - void Set(); - - // Returns true iff the flag was set. If this returns true, the current thread - // is guaranteed to be synchronized with all memory operations on the sequence - // which invoked Set() up until at least the first call to Set() on it. - bool IsSet() const; - - // Resets the flag. Be careful when using this: callers might not expect - // IsSet() to return false after returning true once. - void UnsafeResetForTesting(); - - private: - base::subtle::Atomic32 flag_ = 0; - - DISALLOW_COPY_AND_ASSIGN(AtomicFlag); -}; - -} // namespace base - -#endif // BASE_SYNCHRONIZATION_ATOMIC_FLAG_H_
diff --git a/base/synchronization/cancellation_flag.h b/base/synchronization/cancellation_flag.h deleted file mode 100644 index 39094e2..0000000 --- a/base/synchronization/cancellation_flag.h +++ /dev/null
@@ -1,20 +0,0 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_SYNCHRONIZATION_CANCELLATION_FLAG_H_ -#define BASE_SYNCHRONIZATION_CANCELLATION_FLAG_H_ - -#include "base/synchronization/atomic_flag.h" - -namespace base { - -// Use inheritance instead of "using" to allow forward declaration of "class -// CancellationFlag". -// TODO(fdoray): Replace CancellationFlag with AtomicFlag throughout the -// codebase and delete this file. crbug.com/630251 -class CancellationFlag : public AtomicFlag {}; - -} // namespace base - -#endif // BASE_SYNCHRONIZATION_CANCELLATION_FLAG_H_
diff --git a/base/synchronization/spin_wait.h b/base/synchronization/spin_wait.h deleted file mode 100644 index 9b147cd..0000000 --- a/base/synchronization/spin_wait.h +++ /dev/null
@@ -1,50 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -// This file provides a macro ONLY for use in testing. -// DO NOT USE IN PRODUCTION CODE. There are much better ways to wait. - -// This code is very helpful in testing multi-threaded code, without depending -// on almost any primitives. This is especially helpful if you are testing -// those primitive multi-threaded constructs. - -// We provide a simple one argument spin wait (for 1 second), and a generic -// spin wait (for longer periods of time). - -#ifndef BASE_SYNCHRONIZATION_SPIN_WAIT_H_ -#define BASE_SYNCHRONIZATION_SPIN_WAIT_H_ - -#include "base/threading/platform_thread.h" -#include "base/time/time.h" - -// Provide a macro that will wait no longer than 1 second for an asynchronous -// change is the value of an expression. -// A typical use would be: -// -// SPIN_FOR_1_SECOND_OR_UNTIL_TRUE(0 == f(x)); -// -// The expression will be evaluated repeatedly until it is true, or until -// the time (1 second) expires. -// Since tests generally have a 5 second watch dog timer, this spin loop is -// typically used to get the padding needed on a given test platform to assure -// that the test passes, even if load varies, and external events vary. - -#define SPIN_FOR_1_SECOND_OR_UNTIL_TRUE(expression) \ - SPIN_FOR_TIMEDELTA_OR_UNTIL_TRUE(base::TimeDelta::FromSeconds(1), \ - (expression)) - -#define SPIN_FOR_TIMEDELTA_OR_UNTIL_TRUE(delta, expression) do { \ - base::TimeTicks start = base::TimeTicks::Now(); \ - const base::TimeDelta kTimeout = delta; \ - while (!(expression)) { \ - if (kTimeout < base::TimeTicks::Now() - start) { \ - EXPECT_LE((base::TimeTicks::Now() - start).InMilliseconds(), \ - kTimeout.InMilliseconds()) << "Timed out"; \ - break; \ - } \ - base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(50)); \ - } \ - } while (0) - -#endif // BASE_SYNCHRONIZATION_SPIN_WAIT_H_
diff --git a/base/synchronization/waitable_event_perftest.cc b/base/synchronization/waitable_event_perftest.cc deleted file mode 100644 index 1888077..0000000 --- a/base/synchronization/waitable_event_perftest.cc +++ /dev/null
@@ -1,178 +0,0 @@ -// Copyright 2017 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/synchronization/waitable_event.h" - -#include <numeric> - -#include "base/threading/simple_thread.h" -#include "testing/gtest/include/gtest/gtest.h" -#include "testing/perf/perf_test.h" - -namespace base { - -namespace { - -class TraceWaitableEvent { - public: - TraceWaitableEvent(size_t samples) - : event_(WaitableEvent::ResetPolicy::AUTOMATIC, - WaitableEvent::InitialState::NOT_SIGNALED), - samples_(samples) { - signal_times_.reserve(samples); - wait_times_.reserve(samples); - } - - ~TraceWaitableEvent() = default; - - void Signal() { - TimeTicks start = TimeTicks::Now(); - event_.Signal(); - signal_times_.push_back(TimeTicks::Now() - start); - } - - void Wait() { - TimeTicks start = TimeTicks::Now(); - event_.Wait(); - wait_times_.push_back(TimeTicks::Now() - start); - } - - bool TimedWaitUntil(const TimeTicks& end_time) { - TimeTicks start = TimeTicks::Now(); - bool signaled = event_.TimedWaitUntil(end_time); - wait_times_.push_back(TimeTicks::Now() - start); - return signaled; - } - - bool IsSignaled() { return event_.IsSignaled(); } - - const std::vector<TimeDelta>& signal_times() const { return signal_times_; } - const std::vector<TimeDelta>& wait_times() const { return wait_times_; } - size_t samples() const { return samples_; } - - private: - WaitableEvent event_; - - std::vector<TimeDelta> signal_times_; - std::vector<TimeDelta> wait_times_; - - const size_t samples_; - - DISALLOW_COPY_AND_ASSIGN(TraceWaitableEvent); -}; - -class SignalerThread : public SimpleThread { - public: - SignalerThread(TraceWaitableEvent* waiter, TraceWaitableEvent* signaler) - : SimpleThread("WaitableEventPerfTest signaler"), - waiter_(waiter), - signaler_(signaler) {} - - ~SignalerThread() override = default; - - void Run() override { - while (!stop_event_.IsSignaled()) { - if (waiter_) - waiter_->Wait(); - if (signaler_) - signaler_->Signal(); - } - } - - // Signals the thread to stop on the next iteration of its loop (which - // will happen immediately if no |waiter_| is present or is signaled. - void RequestStop() { stop_event_.Signal(); } - - private: - WaitableEvent stop_event_{WaitableEvent::ResetPolicy::MANUAL, - WaitableEvent::InitialState::NOT_SIGNALED}; - TraceWaitableEvent* waiter_; - TraceWaitableEvent* signaler_; - DISALLOW_COPY_AND_ASSIGN(SignalerThread); -}; - -void PrintPerfWaitableEvent(const TraceWaitableEvent* event, - const std::string& modifier, - const std::string& trace) { - TimeDelta signal_time = std::accumulate( - event->signal_times().begin(), event->signal_times().end(), TimeDelta()); - TimeDelta wait_time = std::accumulate(event->wait_times().begin(), - event->wait_times().end(), TimeDelta()); - perf_test::PrintResult( - "signal_time", modifier, trace, - static_cast<size_t>(signal_time.InNanoseconds()) / event->samples(), - "ns/sample", true); - perf_test::PrintResult( - "wait_time", modifier, trace, - static_cast<size_t>(wait_time.InNanoseconds()) / event->samples(), - "ns/sample", true); -} - -} // namespace - -TEST(WaitableEventPerfTest, SingleThread) { - const size_t kSamples = 1000; - - TraceWaitableEvent event(kSamples); - - for (size_t i = 0; i < kSamples; ++i) { - event.Signal(); - event.Wait(); - } - - PrintPerfWaitableEvent(&event, "", "singlethread-1000-samples"); -} - -TEST(WaitableEventPerfTest, MultipleThreads) { - const size_t kSamples = 1000; - - TraceWaitableEvent waiter(kSamples); - TraceWaitableEvent signaler(kSamples); - - // The other thread will wait and signal on the respective opposite events. - SignalerThread thread(&signaler, &waiter); - thread.Start(); - - for (size_t i = 0; i < kSamples; ++i) { - signaler.Signal(); - waiter.Wait(); - } - - // Signal the stop event and then make sure the signaler event it is - // waiting on is also signaled. - thread.RequestStop(); - signaler.Signal(); - - thread.Join(); - - PrintPerfWaitableEvent(&waiter, "_waiter", "multithread-1000-samples"); - PrintPerfWaitableEvent(&signaler, "_signaler", "multithread-1000-samples"); -} - -TEST(WaitableEventPerfTest, Throughput) { - // Reserve a lot of sample space. - const size_t kCapacity = 500000; - TraceWaitableEvent event(kCapacity); - - SignalerThread thread(nullptr, &event); - thread.Start(); - - TimeTicks end_time = TimeTicks::Now() + TimeDelta::FromSeconds(1); - size_t count = 0; - while (event.TimedWaitUntil(end_time)) { - ++count; - } - - thread.RequestStop(); - thread.Join(); - - perf_test::PrintResult("counts", "", "throughput", count, "signals", true); - PrintPerfWaitableEvent(&event, "", "throughput"); - - // Make sure that allocation didn't happen during the test. - EXPECT_LE(event.signal_times().capacity(), kCapacity); - EXPECT_LE(event.wait_times().capacity(), kCapacity); -} - -} // namespace base
diff --git a/base/task/OWNERS b/base/task/OWNERS deleted file mode 100644 index 0f3ad5e..0000000 --- a/base/task/OWNERS +++ /dev/null
@@ -1,6 +0,0 @@ -fdoray@chromium.org -gab@chromium.org -robliao@chromium.org - -# TEAM: scheduler-dev@chromium.org -# COMPONENT: Internals>TaskScheduler
diff --git a/base/task/README.md b/base/task/README.md deleted file mode 100644 index 0db116a..0000000 --- a/base/task/README.md +++ /dev/null
@@ -1,12 +0,0 @@ -This directory has the following layout (WIP): -- base/task/: public APIs for posting tasks and managing task queues. -- base/task/task_scheduler/: implementation of the TaskScheduler. -- base/task/sequence_manager/: implementation of the SequenceManager. - -Apart from embedders explicitly managing a TaskScheduler and/or SequenceManager -instance(s) for their process/threads, the vast majority of users should only -need APIs in base/task/. - -Documentation: -- [Threading and tasks](https://chromium.googlesource.com/chromium/src/+/lkcr/docs/threading_and_tasks.md) -- [Callbacks](https://chromium.googlesource.com/chromium/src/+/lkcr/docs/callback.md)
diff --git a/base/task/cancelable_task_tracker.cc b/base/task/cancelable_task_tracker.cc deleted file mode 100644 index f304da8..0000000 --- a/base/task/cancelable_task_tracker.cc +++ /dev/null
@@ -1,176 +0,0 @@ -// Copyright 2014 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/task/cancelable_task_tracker.h" - -#include <stddef.h> - -#include <utility> - -#include "base/bind.h" -#include "base/bind_helpers.h" -#include "base/callback_helpers.h" -#include "base/location.h" -#include "base/memory/ref_counted.h" -#include "base/synchronization/cancellation_flag.h" -#include "base/task_runner.h" -#include "base/threading/sequenced_task_runner_handle.h" - -namespace base { - -namespace { - -void RunIfNotCanceled(const CancellationFlag* flag, OnceClosure task) { - if (!flag->IsSet()) - std::move(task).Run(); -} - -void RunIfNotCanceledThenUntrack(const CancellationFlag* flag, - OnceClosure task, - OnceClosure untrack) { - RunIfNotCanceled(flag, std::move(task)); - std::move(untrack).Run(); -} - -bool IsCanceled(const CancellationFlag* flag, - ScopedClosureRunner* cleanup_runner) { - return flag->IsSet(); -} - -void RunAndDeleteFlag(OnceClosure closure, const CancellationFlag* flag) { - std::move(closure).Run(); - delete flag; -} - -void RunOrPostToTaskRunner(TaskRunner* task_runner, OnceClosure closure) { - if (task_runner->RunsTasksInCurrentSequence()) - std::move(closure).Run(); - else - task_runner->PostTask(FROM_HERE, std::move(closure)); -} - -} // namespace - -// static -const CancelableTaskTracker::TaskId CancelableTaskTracker::kBadTaskId = 0; - -CancelableTaskTracker::CancelableTaskTracker() - : next_id_(1),weak_factory_(this) {} - -CancelableTaskTracker::~CancelableTaskTracker() { - DCHECK(sequence_checker_.CalledOnValidSequence()); - - TryCancelAll(); -} - -CancelableTaskTracker::TaskId CancelableTaskTracker::PostTask( - TaskRunner* task_runner, - const Location& from_here, - OnceClosure task) { - DCHECK(sequence_checker_.CalledOnValidSequence()); - - return PostTaskAndReply(task_runner, from_here, std::move(task), DoNothing()); -} - -CancelableTaskTracker::TaskId CancelableTaskTracker::PostTaskAndReply( - TaskRunner* task_runner, - const Location& from_here, - OnceClosure task, - OnceClosure reply) { - DCHECK(sequence_checker_.CalledOnValidSequence()); - - // We need a SequencedTaskRunnerHandle to run |reply|. - DCHECK(SequencedTaskRunnerHandle::IsSet()); - - // Owned by reply callback below. - CancellationFlag* flag = new CancellationFlag(); - - TaskId id = next_id_; - next_id_++; // int64_t is big enough that we ignore the potential overflow. - - OnceClosure untrack_closure = - BindOnce(&CancelableTaskTracker::Untrack, weak_factory_.GetWeakPtr(), id); - bool success = task_runner->PostTaskAndReply( - from_here, BindOnce(&RunIfNotCanceled, flag, std::move(task)), - BindOnce(&RunIfNotCanceledThenUntrack, Owned(flag), std::move(reply), - std::move(untrack_closure))); - - if (!success) - return kBadTaskId; - - Track(id, flag); - return id; -} - -CancelableTaskTracker::TaskId CancelableTaskTracker::NewTrackedTaskId( - IsCanceledCallback* is_canceled_cb) { - DCHECK(sequence_checker_.CalledOnValidSequence()); - DCHECK(SequencedTaskRunnerHandle::IsSet()); - - TaskId id = next_id_; - next_id_++; // int64_t is big enough that we ignore the potential overflow. - - // Will be deleted by |untrack_and_delete_flag| after Untrack(). - CancellationFlag* flag = new CancellationFlag(); - - OnceClosure untrack_and_delete_flag = BindOnce( - &RunAndDeleteFlag, - BindOnce(&CancelableTaskTracker::Untrack, weak_factory_.GetWeakPtr(), id), - flag); - - // Will always run |untrack_and_delete_flag| on current sequence. - ScopedClosureRunner* untrack_and_delete_flag_runner = - new ScopedClosureRunner(BindOnce( - &RunOrPostToTaskRunner, RetainedRef(SequencedTaskRunnerHandle::Get()), - std::move(untrack_and_delete_flag))); - - *is_canceled_cb = - Bind(&IsCanceled, flag, Owned(untrack_and_delete_flag_runner)); - - Track(id, flag); - return id; -} - -void CancelableTaskTracker::TryCancel(TaskId id) { - DCHECK(sequence_checker_.CalledOnValidSequence()); - - const auto it = task_flags_.find(id); - if (it == task_flags_.end()) { - // Two possibilities: - // - // 1. The task has already been untracked. - // 2. The TaskId is bad or unknown. - // - // Since this function is best-effort, it's OK to ignore these. - return; - } - it->second->Set(); -} - -void CancelableTaskTracker::TryCancelAll() { - DCHECK(sequence_checker_.CalledOnValidSequence()); - for (const auto& it : task_flags_) - it.second->Set(); - weak_factory_.InvalidateWeakPtrs(); - task_flags_.clear(); -} - -bool CancelableTaskTracker::HasTrackedTasks() const { - DCHECK(sequence_checker_.CalledOnValidSequence()); - return !task_flags_.empty(); -} - -void CancelableTaskTracker::Track(TaskId id, CancellationFlag* flag) { - DCHECK(sequence_checker_.CalledOnValidSequence()); - bool success = task_flags_.insert(std::make_pair(id, flag)).second; - DCHECK(success); -} - -void CancelableTaskTracker::Untrack(TaskId id) { - DCHECK(sequence_checker_.CalledOnValidSequence()); - size_t num = task_flags_.erase(id); - DCHECK_EQ(1u, num); -} - -} // namespace base
diff --git a/base/task/cancelable_task_tracker.h b/base/task/cancelable_task_tracker.h deleted file mode 100644 index e5e6b5e..0000000 --- a/base/task/cancelable_task_tracker.h +++ /dev/null
@@ -1,158 +0,0 @@ -// Copyright 2014 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -// CancelableTaskTracker posts tasks (in the form of a Closure) to a -// TaskRunner, and is able to cancel the task later if it's not needed -// anymore. On destruction, CancelableTaskTracker will cancel all -// tracked tasks. -// -// Each cancelable task can be associated with a reply (also a Closure). After -// the task is run on the TaskRunner, |reply| will be posted back to -// originating TaskRunner. -// -// NOTE: -// -// CancelableCallback (base/cancelable_callback.h) and WeakPtr binding are -// preferred solutions for canceling a task. However, they don't support -// cancelation from another sequence. This is sometimes a performance critical -// requirement. E.g. We need to cancel database lookup task on DB thread when -// user changes inputed text. If it is performance critical to do a best effort -// cancelation of a task, then CancelableTaskTracker is appropriate, otherwise -// use one of the other mechanisms. -// -// THREAD-SAFETY: -// -// 1. A CancelableTaskTracker object must be created, used, and destroyed on a -// single sequence. -// -// 2. It's safe to destroy a CancelableTaskTracker while there are outstanding -// tasks. This is commonly used to cancel all outstanding tasks. -// -// 3. The task is deleted on the target sequence, and the reply are deleted on -// the originating sequence. -// -// 4. IsCanceledCallback can be run or deleted on any sequence. -#ifndef BASE_TASK_CANCELABLE_TASK_TRACKER_H_ -#define BASE_TASK_CANCELABLE_TASK_TRACKER_H_ - -#include <stdint.h> - -#include <utility> - -#include "base/base_export.h" -#include "base/bind.h" -#include "base/callback.h" -#include "base/containers/small_map.h" -#include "base/macros.h" -#include "base/memory/weak_ptr.h" -#include "base/post_task_and_reply_with_result_internal.h" -#include "base/sequence_checker.h" - -namespace base { - -class CancellationFlag; -class Location; -class TaskRunner; - -class BASE_EXPORT CancelableTaskTracker { - public: - // All values except kBadTaskId are valid. - typedef int64_t TaskId; - static const TaskId kBadTaskId; - - typedef Callback<bool()> IsCanceledCallback; - - CancelableTaskTracker(); - - // Cancels all tracked tasks. - ~CancelableTaskTracker(); - - TaskId PostTask(TaskRunner* task_runner, - const Location& from_here, - OnceClosure task); - - TaskId PostTaskAndReply(TaskRunner* task_runner, - const Location& from_here, - OnceClosure task, - OnceClosure reply); - - template <typename TaskReturnType, typename ReplyArgType> - TaskId PostTaskAndReplyWithResult(TaskRunner* task_runner, - const Location& from_here, - OnceCallback<TaskReturnType()> task, - OnceCallback<void(ReplyArgType)> reply) { - TaskReturnType* result = new TaskReturnType(); - return PostTaskAndReply( - task_runner, from_here, - BindOnce(&internal::ReturnAsParamAdapter<TaskReturnType>, - std::move(task), Unretained(result)), - BindOnce(&internal::ReplyAdapter<TaskReturnType, ReplyArgType>, - std::move(reply), Owned(result))); - } - - // Callback version of PostTaskWithTraitsAndReplyWithResult above. - // Though RepeatingCallback is convertible to OnceCallback, we need this since - // we can not use template deduction and object conversion at once on the - // overload resolution. - // TODO(tzik): Update all callers of the Callback version to use OnceCallback. - template <typename TaskReturnType, typename ReplyArgType> - TaskId PostTaskAndReplyWithResult(TaskRunner* task_runner, - const Location& from_here, - Callback<TaskReturnType()> task, - Callback<void(ReplyArgType)> reply) { - return PostTaskAndReplyWithResult( - task_runner, from_here, - static_cast<OnceCallback<TaskReturnType()>>(std::move(task)), - static_cast<OnceCallback<void(ReplyArgType)>>(std::move(reply))); - } - - // Creates a tracked TaskId and an associated IsCanceledCallback. Client can - // later call TryCancel() with the returned TaskId, and run |is_canceled_cb| - // from any thread to check whether the TaskId is canceled. - // - // The returned task ID is tracked until the last copy of - // |is_canceled_cb| is destroyed. - // - // Note. This function is used to address some special cancelation requirement - // in existing code. You SHOULD NOT need this function in new code. - TaskId NewTrackedTaskId(IsCanceledCallback* is_canceled_cb); - - // After calling this function, |task| and |reply| will not run. If the - // cancelation happens when |task| is running or has finished running, |reply| - // will not run. If |reply| is running or has finished running, cancellation - // is a noop. - // - // Note. It's OK to cancel a |task| for more than once. The later calls are - // noops. - void TryCancel(TaskId id); - - // It's OK to call this function for more than once. The later calls are - // noops. - void TryCancelAll(); - - // Returns true iff there are in-flight tasks that are still being - // tracked. - bool HasTrackedTasks() const; - - private: - void Track(TaskId id, CancellationFlag* flag); - void Untrack(TaskId id); - - // Typically the number of tasks are 0-2 and occationally 3-4. But since - // this is a general API that could be used in unexpected ways, use a - // small_map instead of a flat_map to avoid falling over if there are many - // tasks. - small_map<std::map<TaskId, CancellationFlag*>, 4> task_flags_; - - TaskId next_id_; - SequenceChecker sequence_checker_; - - WeakPtrFactory<CancelableTaskTracker> weak_factory_; - - DISALLOW_COPY_AND_ASSIGN(CancelableTaskTracker); -}; - -} // namespace base - -#endif // BASE_TASK_CANCELABLE_TASK_TRACKER_H_
diff --git a/base/task/sequence_manager/OWNERS b/base/task/sequence_manager/OWNERS deleted file mode 100644 index ac6eae8..0000000 --- a/base/task/sequence_manager/OWNERS +++ /dev/null
@@ -1,6 +0,0 @@ -altimin@chromium.org -alexclarke@chromium.org -skyostil@chromium.org - -# TEAM: scheduler-dev@chromium.org -# Component: Blink>Scheduling
diff --git a/base/task/task_scheduler/OWNERS b/base/task/task_scheduler/OWNERS deleted file mode 100644 index 0f3ad5e..0000000 --- a/base/task/task_scheduler/OWNERS +++ /dev/null
@@ -1,6 +0,0 @@ -fdoray@chromium.org -gab@chromium.org -robliao@chromium.org - -# TEAM: scheduler-dev@chromium.org -# COMPONENT: Internals>TaskScheduler
diff --git a/base/third_party/nspr/LICENSE b/base/third_party/nspr/LICENSE deleted file mode 100644 index eba7b77..0000000 --- a/base/third_party/nspr/LICENSE +++ /dev/null
@@ -1,35 +0,0 @@ -/* ***** BEGIN LICENSE BLOCK ***** - * Version: MPL 1.1/GPL 2.0/LGPL 2.1 - * - * The contents of this file are subject to the Mozilla Public License Version - * 1.1 (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * http://www.mozilla.org/MPL/ - * - * Software distributed under the License is distributed on an "AS IS" basis, - * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License - * for the specific language governing rights and limitations under the - * License. - * - * The Original Code is the Netscape Portable Runtime (NSPR). - * - * The Initial Developer of the Original Code is - * Netscape Communications Corporation. - * Portions created by the Initial Developer are Copyright (C) 1998-2000 - * the Initial Developer. All Rights Reserved. - * - * Contributor(s): - * - * Alternatively, the contents of this file may be used under the terms of - * either the GNU General Public License Version 2 or later (the "GPL"), or - * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"), - * in which case the provisions of the GPL or the LGPL are applicable instead - * of those above. If you wish to allow use of your version of this file only - * under the terms of either the GPL or the LGPL, and not to allow others to - * use your version of this file under the terms of the MPL, indicate your - * decision by deleting the provisions above and replace them with the notice - * and other provisions required by the GPL or the LGPL. If you do not delete - * the provisions above, a recipient may use your version of this file under - * the terms of any one of the MPL, the GPL or the LGPL. - * - * ***** END LICENSE BLOCK ***** */
diff --git a/base/third_party/nspr/OWNERS b/base/third_party/nspr/OWNERS deleted file mode 100644 index 20ba660..0000000 --- a/base/third_party/nspr/OWNERS +++ /dev/null
@@ -1,2 +0,0 @@ -rsleevi@chromium.org -wtc@chromium.org
diff --git a/base/third_party/nspr/README.chromium b/base/third_party/nspr/README.chromium deleted file mode 100644 index 3659a2c..0000000 --- a/base/third_party/nspr/README.chromium +++ /dev/null
@@ -1,3 +0,0 @@ -Name: Netscape Portable Runtime (NSPR) -URL: http://www.mozilla.org/projects/nspr/ -License: MPL 1.1/GPL 2.0/LGPL 2.1
diff --git a/base/third_party/nspr/prtime.cc b/base/third_party/nspr/prtime.cc deleted file mode 100644 index 8a3f7c0..0000000 --- a/base/third_party/nspr/prtime.cc +++ /dev/null
@@ -1,1186 +0,0 @@ -/* Portions are Copyright (C) 2011 Google Inc */ -/* ***** BEGIN LICENSE BLOCK ***** - * Version: MPL 1.1/GPL 2.0/LGPL 2.1 - * - * The contents of this file are subject to the Mozilla Public License Version - * 1.1 (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * http://www.mozilla.org/MPL/ - * - * Software distributed under the License is distributed on an "AS IS" basis, - * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License - * for the specific language governing rights and limitations under the - * License. - * - * The Original Code is the Netscape Portable Runtime (NSPR). - * - * The Initial Developer of the Original Code is - * Netscape Communications Corporation. - * Portions created by the Initial Developer are Copyright (C) 1998-2000 - * the Initial Developer. All Rights Reserved. - * - * Contributor(s): - * - * Alternatively, the contents of this file may be used under the terms of - * either the GNU General Public License Version 2 or later (the "GPL"), or - * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"), - * in which case the provisions of the GPL or the LGPL are applicable instead - * of those above. If you wish to allow use of your version of this file only - * under the terms of either the GPL or the LGPL, and not to allow others to - * use your version of this file under the terms of the MPL, indicate your - * decision by deleting the provisions above and replace them with the notice - * and other provisions required by the GPL or the LGPL. If you do not delete - * the provisions above, a recipient may use your version of this file under - * the terms of any one of the MPL, the GPL or the LGPL. - * - * ***** END LICENSE BLOCK ***** */ - -/* - * prtime.cc -- - * NOTE: The original nspr file name is prtime.c - * - * NSPR date and time functions - * - * CVS revision 3.37 - */ - -/* - * The following functions were copied from the NSPR prtime.c file. - * PR_ParseTimeString - * We inlined the new PR_ParseTimeStringToExplodedTime function to avoid - * copying PR_ExplodeTime and PR_LocalTimeParameters. (The PR_ExplodeTime - * and PR_ImplodeTime calls cancel each other out.) - * PR_NormalizeTime - * PR_GMTParameters - * PR_ImplodeTime - * Upstream implementation from - * http://lxr.mozilla.org/nspr/source/pr/src/misc/prtime.c#221 - * All types and macros are defined in the base/third_party/prtime.h file. - * These have been copied from the following nspr files. We have only copied - * over the types we need. - * 1. prtime.h - * 2. prtypes.h - * 3. prlong.h - * - * Unit tests are in base/time/pr_time_unittest.cc. - */ - -#include <limits.h> - -#include "base/logging.h" -#include "base/third_party/nspr/prtime.h" -#include "build_config.h" - -#include <errno.h> /* for EINVAL */ -#include <time.h> - -/* - * The COUNT_LEAPS macro counts the number of leap years passed by - * till the start of the given year Y. At the start of the year 4 - * A.D. the number of leap years passed by is 0, while at the start of - * the year 5 A.D. this count is 1. The number of years divisible by - * 100 but not divisible by 400 (the non-leap years) is deducted from - * the count to get the correct number of leap years. - * - * The COUNT_DAYS macro counts the number of days since 01/01/01 till the - * start of the given year Y. The number of days at the start of the year - * 1 is 0 while the number of days at the start of the year 2 is 365 - * (which is ((2)-1) * 365) and so on. The reference point is 01/01/01 - * midnight 00:00:00. - */ - -#define COUNT_LEAPS(Y) (((Y)-1) / 4 - ((Y)-1) / 100 + ((Y)-1) / 400) -#define COUNT_DAYS(Y) (((Y)-1) * 365 + COUNT_LEAPS(Y)) -#define DAYS_BETWEEN_YEARS(A, B) (COUNT_DAYS(B) - COUNT_DAYS(A)) - -/* Implements the Unix localtime_r() function for windows */ -#if defined(OS_WIN) -static void localtime_r(const time_t* secs, struct tm* time) { - (void) localtime_s(time, secs); -} -#endif - -/* - * Static variables used by functions in this file - */ - -/* - * The following array contains the day of year for the last day of - * each month, where index 1 is January, and day 0 is January 1. - */ - -static const int lastDayOfMonth[2][13] = { - {-1, 30, 58, 89, 119, 150, 180, 211, 242, 272, 303, 333, 364}, - {-1, 30, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334, 365} -}; - -/* - * The number of days in a month - */ - -static const PRInt8 nDays[2][12] = { - {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}, - {31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31} -}; - -/* - *------------------------------------------------------------------------ - * - * PR_ImplodeTime -- - * - * Cf. time_t mktime(struct tm *tp) - * Note that 1 year has < 2^25 seconds. So an PRInt32 is large enough. - * - *------------------------------------------------------------------------ - */ -PRTime -PR_ImplodeTime(const PRExplodedTime *exploded) -{ - PRExplodedTime copy; - PRTime retVal; - PRInt64 secPerDay, usecPerSec; - PRInt64 temp; - PRInt64 numSecs64; - PRInt32 numDays; - PRInt32 numSecs; - - /* Normalize first. Do this on our copy */ - copy = *exploded; - PR_NormalizeTime(©, PR_GMTParameters); - - numDays = DAYS_BETWEEN_YEARS(1970, copy.tm_year); - - numSecs = copy.tm_yday * 86400 + copy.tm_hour * 3600 + copy.tm_min * 60 + - copy.tm_sec; - - LL_I2L(temp, numDays); - LL_I2L(secPerDay, 86400); - LL_MUL(temp, temp, secPerDay); - LL_I2L(numSecs64, numSecs); - LL_ADD(numSecs64, numSecs64, temp); - - /* apply the GMT and DST offsets */ - LL_I2L(temp, copy.tm_params.tp_gmt_offset); - LL_SUB(numSecs64, numSecs64, temp); - LL_I2L(temp, copy.tm_params.tp_dst_offset); - LL_SUB(numSecs64, numSecs64, temp); - - LL_I2L(usecPerSec, 1000000L); - LL_MUL(temp, numSecs64, usecPerSec); - LL_I2L(retVal, copy.tm_usec); - LL_ADD(retVal, retVal, temp); - - return retVal; -} - -/* - *------------------------------------------------------------------------- - * - * IsLeapYear -- - * - * Returns 1 if the year is a leap year, 0 otherwise. - * - *------------------------------------------------------------------------- - */ - -static int IsLeapYear(PRInt16 year) -{ - if ((year % 4 == 0 && year % 100 != 0) || year % 400 == 0) - return 1; - else - return 0; -} - -/* - * 'secOffset' should be less than 86400 (i.e., a day). - * 'time' should point to a normalized PRExplodedTime. - */ - -static void -ApplySecOffset(PRExplodedTime *time, PRInt32 secOffset) -{ - time->tm_sec += secOffset; - - /* Note that in this implementation we do not count leap seconds */ - if (time->tm_sec < 0 || time->tm_sec >= 60) { - time->tm_min += time->tm_sec / 60; - time->tm_sec %= 60; - if (time->tm_sec < 0) { - time->tm_sec += 60; - time->tm_min--; - } - } - - if (time->tm_min < 0 || time->tm_min >= 60) { - time->tm_hour += time->tm_min / 60; - time->tm_min %= 60; - if (time->tm_min < 0) { - time->tm_min += 60; - time->tm_hour--; - } - } - - if (time->tm_hour < 0) { - /* Decrement mday, yday, and wday */ - time->tm_hour += 24; - time->tm_mday--; - time->tm_yday--; - if (time->tm_mday < 1) { - time->tm_month--; - if (time->tm_month < 0) { - time->tm_month = 11; - time->tm_year--; - if (IsLeapYear(time->tm_year)) - time->tm_yday = 365; - else - time->tm_yday = 364; - } - time->tm_mday = nDays[IsLeapYear(time->tm_year)][time->tm_month]; - } - time->tm_wday--; - if (time->tm_wday < 0) - time->tm_wday = 6; - } else if (time->tm_hour > 23) { - /* Increment mday, yday, and wday */ - time->tm_hour -= 24; - time->tm_mday++; - time->tm_yday++; - if (time->tm_mday > - nDays[IsLeapYear(time->tm_year)][time->tm_month]) { - time->tm_mday = 1; - time->tm_month++; - if (time->tm_month > 11) { - time->tm_month = 0; - time->tm_year++; - time->tm_yday = 0; - } - } - time->tm_wday++; - if (time->tm_wday > 6) - time->tm_wday = 0; - } -} - -void -PR_NormalizeTime(PRExplodedTime *time, PRTimeParamFn params) -{ - int daysInMonth; - PRInt32 numDays; - - /* Get back to GMT */ - time->tm_sec -= time->tm_params.tp_gmt_offset - + time->tm_params.tp_dst_offset; - time->tm_params.tp_gmt_offset = 0; - time->tm_params.tp_dst_offset = 0; - - /* Now normalize GMT */ - - if (time->tm_usec < 0 || time->tm_usec >= 1000000) { - time->tm_sec += time->tm_usec / 1000000; - time->tm_usec %= 1000000; - if (time->tm_usec < 0) { - time->tm_usec += 1000000; - time->tm_sec--; - } - } - - /* Note that we do not count leap seconds in this implementation */ - if (time->tm_sec < 0 || time->tm_sec >= 60) { - time->tm_min += time->tm_sec / 60; - time->tm_sec %= 60; - if (time->tm_sec < 0) { - time->tm_sec += 60; - time->tm_min--; - } - } - - if (time->tm_min < 0 || time->tm_min >= 60) { - time->tm_hour += time->tm_min / 60; - time->tm_min %= 60; - if (time->tm_min < 0) { - time->tm_min += 60; - time->tm_hour--; - } - } - - if (time->tm_hour < 0 || time->tm_hour >= 24) { - time->tm_mday += time->tm_hour / 24; - time->tm_hour %= 24; - if (time->tm_hour < 0) { - time->tm_hour += 24; - time->tm_mday--; - } - } - - /* Normalize month and year before mday */ - if (time->tm_month < 0 || time->tm_month >= 12) { - time->tm_year += static_cast<PRInt16>(time->tm_month / 12); - time->tm_month %= 12; - if (time->tm_month < 0) { - time->tm_month += 12; - time->tm_year--; - } - } - - /* Now that month and year are in proper range, normalize mday */ - - if (time->tm_mday < 1) { - /* mday too small */ - do { - /* the previous month */ - time->tm_month--; - if (time->tm_month < 0) { - time->tm_month = 11; - time->tm_year--; - } - time->tm_mday += nDays[IsLeapYear(time->tm_year)][time->tm_month]; - } while (time->tm_mday < 1); - } else { - daysInMonth = nDays[IsLeapYear(time->tm_year)][time->tm_month]; - while (time->tm_mday > daysInMonth) { - /* mday too large */ - time->tm_mday -= daysInMonth; - time->tm_month++; - if (time->tm_month > 11) { - time->tm_month = 0; - time->tm_year++; - } - daysInMonth = nDays[IsLeapYear(time->tm_year)][time->tm_month]; - } - } - - /* Recompute yday and wday */ - time->tm_yday = static_cast<PRInt16>(time->tm_mday + - lastDayOfMonth[IsLeapYear(time->tm_year)][time->tm_month]); - - numDays = DAYS_BETWEEN_YEARS(1970, time->tm_year) + time->tm_yday; - time->tm_wday = (numDays + 4) % 7; - if (time->tm_wday < 0) { - time->tm_wday += 7; - } - - /* Recompute time parameters */ - - time->tm_params = params(time); - - ApplySecOffset(time, time->tm_params.tp_gmt_offset - + time->tm_params.tp_dst_offset); -} - -/* - *------------------------------------------------------------------------ - * - * PR_GMTParameters -- - * - * Returns the PRTimeParameters for Greenwich Mean Time. - * Trivially, both the tp_gmt_offset and tp_dst_offset fields are 0. - * - *------------------------------------------------------------------------ - */ - -PRTimeParameters -PR_GMTParameters(const PRExplodedTime *gmt) -{ - PRTimeParameters retVal = { 0, 0 }; - return retVal; -} - -/* - * The following code implements PR_ParseTimeString(). It is based on - * ns/lib/xp/xp_time.c, revision 1.25, by Jamie Zawinski <jwz@netscape.com>. - */ - -/* - * We only recognize the abbreviations of a small subset of time zones - * in North America, Europe, and Japan. - * - * PST/PDT: Pacific Standard/Daylight Time - * MST/MDT: Mountain Standard/Daylight Time - * CST/CDT: Central Standard/Daylight Time - * EST/EDT: Eastern Standard/Daylight Time - * AST: Atlantic Standard Time - * NST: Newfoundland Standard Time - * GMT: Greenwich Mean Time - * BST: British Summer Time - * MET: Middle Europe Time - * EET: Eastern Europe Time - * JST: Japan Standard Time - */ - -typedef enum -{ - TT_UNKNOWN, - - TT_SUN, TT_MON, TT_TUE, TT_WED, TT_THU, TT_FRI, TT_SAT, - - TT_JAN, TT_FEB, TT_MAR, TT_APR, TT_MAY, TT_JUN, - TT_JUL, TT_AUG, TT_SEP, TT_OCT, TT_NOV, TT_DEC, - - TT_PST, TT_PDT, TT_MST, TT_MDT, TT_CST, TT_CDT, TT_EST, TT_EDT, - TT_AST, TT_NST, TT_GMT, TT_BST, TT_MET, TT_EET, TT_JST -} TIME_TOKEN; - -/* - * This parses a time/date string into a PRTime - * (microseconds after "1-Jan-1970 00:00:00 GMT"). - * It returns PR_SUCCESS on success, and PR_FAILURE - * if the time/date string can't be parsed. - * - * Many formats are handled, including: - * - * 14 Apr 89 03:20:12 - * 14 Apr 89 03:20 GMT - * Fri, 17 Mar 89 4:01:33 - * Fri, 17 Mar 89 4:01 GMT - * Mon Jan 16 16:12 PDT 1989 - * Mon Jan 16 16:12 +0130 1989 - * 6 May 1992 16:41-JST (Wednesday) - * 22-AUG-1993 10:59:12.82 - * 22-AUG-1993 10:59pm - * 22-AUG-1993 12:59am - * 22-AUG-1993 12:59 PM - * Friday, August 04, 1995 3:54 PM - * 06/21/95 04:24:34 PM - * 20/06/95 21:07 - * 95-06-08 19:32:48 EDT - * 1995-06-17T23:11:25.342156Z - * - * If the input string doesn't contain a description of the timezone, - * we consult the `default_to_gmt' to decide whether the string should - * be interpreted relative to the local time zone (PR_FALSE) or GMT (PR_TRUE). - * The correct value for this argument depends on what standard specified - * the time string which you are parsing. - */ - -PRStatus -PR_ParseTimeString( - const char *string, - PRBool default_to_gmt, - PRTime *result_imploded) -{ - PRExplodedTime tm; - PRExplodedTime *result = &tm; - TIME_TOKEN dotw = TT_UNKNOWN; - TIME_TOKEN month = TT_UNKNOWN; - TIME_TOKEN zone = TT_UNKNOWN; - int zone_offset = -1; - int dst_offset = 0; - int date = -1; - PRInt32 year = -1; - int hour = -1; - int min = -1; - int sec = -1; - int usec = -1; - - const char *rest = string; - - int iterations = 0; - - PR_ASSERT(string && result); - if (!string || !result) return PR_FAILURE; - - while (*rest) - { - - if (iterations++ > 1000) - { - return PR_FAILURE; - } - - switch (*rest) - { - case 'a': case 'A': - if (month == TT_UNKNOWN && - (rest[1] == 'p' || rest[1] == 'P') && - (rest[2] == 'r' || rest[2] == 'R')) - month = TT_APR; - else if (zone == TT_UNKNOWN && - (rest[1] == 's' || rest[1] == 'S') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_AST; - else if (month == TT_UNKNOWN && - (rest[1] == 'u' || rest[1] == 'U') && - (rest[2] == 'g' || rest[2] == 'G')) - month = TT_AUG; - break; - case 'b': case 'B': - if (zone == TT_UNKNOWN && - (rest[1] == 's' || rest[1] == 'S') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_BST; - break; - case 'c': case 'C': - if (zone == TT_UNKNOWN && - (rest[1] == 'd' || rest[1] == 'D') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_CDT; - else if (zone == TT_UNKNOWN && - (rest[1] == 's' || rest[1] == 'S') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_CST; - break; - case 'd': case 'D': - if (month == TT_UNKNOWN && - (rest[1] == 'e' || rest[1] == 'E') && - (rest[2] == 'c' || rest[2] == 'C')) - month = TT_DEC; - break; - case 'e': case 'E': - if (zone == TT_UNKNOWN && - (rest[1] == 'd' || rest[1] == 'D') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_EDT; - else if (zone == TT_UNKNOWN && - (rest[1] == 'e' || rest[1] == 'E') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_EET; - else if (zone == TT_UNKNOWN && - (rest[1] == 's' || rest[1] == 'S') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_EST; - break; - case 'f': case 'F': - if (month == TT_UNKNOWN && - (rest[1] == 'e' || rest[1] == 'E') && - (rest[2] == 'b' || rest[2] == 'B')) - month = TT_FEB; - else if (dotw == TT_UNKNOWN && - (rest[1] == 'r' || rest[1] == 'R') && - (rest[2] == 'i' || rest[2] == 'I')) - dotw = TT_FRI; - break; - case 'g': case 'G': - if (zone == TT_UNKNOWN && - (rest[1] == 'm' || rest[1] == 'M') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_GMT; - break; - case 'j': case 'J': - if (month == TT_UNKNOWN && - (rest[1] == 'a' || rest[1] == 'A') && - (rest[2] == 'n' || rest[2] == 'N')) - month = TT_JAN; - else if (zone == TT_UNKNOWN && - (rest[1] == 's' || rest[1] == 'S') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_JST; - else if (month == TT_UNKNOWN && - (rest[1] == 'u' || rest[1] == 'U') && - (rest[2] == 'l' || rest[2] == 'L')) - month = TT_JUL; - else if (month == TT_UNKNOWN && - (rest[1] == 'u' || rest[1] == 'U') && - (rest[2] == 'n' || rest[2] == 'N')) - month = TT_JUN; - break; - case 'm': case 'M': - if (month == TT_UNKNOWN && - (rest[1] == 'a' || rest[1] == 'A') && - (rest[2] == 'r' || rest[2] == 'R')) - month = TT_MAR; - else if (month == TT_UNKNOWN && - (rest[1] == 'a' || rest[1] == 'A') && - (rest[2] == 'y' || rest[2] == 'Y')) - month = TT_MAY; - else if (zone == TT_UNKNOWN && - (rest[1] == 'd' || rest[1] == 'D') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_MDT; - else if (zone == TT_UNKNOWN && - (rest[1] == 'e' || rest[1] == 'E') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_MET; - else if (dotw == TT_UNKNOWN && - (rest[1] == 'o' || rest[1] == 'O') && - (rest[2] == 'n' || rest[2] == 'N')) - dotw = TT_MON; - else if (zone == TT_UNKNOWN && - (rest[1] == 's' || rest[1] == 'S') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_MST; - break; - case 'n': case 'N': - if (month == TT_UNKNOWN && - (rest[1] == 'o' || rest[1] == 'O') && - (rest[2] == 'v' || rest[2] == 'V')) - month = TT_NOV; - else if (zone == TT_UNKNOWN && - (rest[1] == 's' || rest[1] == 'S') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_NST; - break; - case 'o': case 'O': - if (month == TT_UNKNOWN && - (rest[1] == 'c' || rest[1] == 'C') && - (rest[2] == 't' || rest[2] == 'T')) - month = TT_OCT; - break; - case 'p': case 'P': - if (zone == TT_UNKNOWN && - (rest[1] == 'd' || rest[1] == 'D') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_PDT; - else if (zone == TT_UNKNOWN && - (rest[1] == 's' || rest[1] == 'S') && - (rest[2] == 't' || rest[2] == 'T')) - zone = TT_PST; - break; - case 's': case 'S': - if (dotw == TT_UNKNOWN && - (rest[1] == 'a' || rest[1] == 'A') && - (rest[2] == 't' || rest[2] == 'T')) - dotw = TT_SAT; - else if (month == TT_UNKNOWN && - (rest[1] == 'e' || rest[1] == 'E') && - (rest[2] == 'p' || rest[2] == 'P')) - month = TT_SEP; - else if (dotw == TT_UNKNOWN && - (rest[1] == 'u' || rest[1] == 'U') && - (rest[2] == 'n' || rest[2] == 'N')) - dotw = TT_SUN; - break; - case 't': case 'T': - if (dotw == TT_UNKNOWN && - (rest[1] == 'h' || rest[1] == 'H') && - (rest[2] == 'u' || rest[2] == 'U')) - dotw = TT_THU; - else if (dotw == TT_UNKNOWN && - (rest[1] == 'u' || rest[1] == 'U') && - (rest[2] == 'e' || rest[2] == 'E')) - dotw = TT_TUE; - break; - case 'u': case 'U': - if (zone == TT_UNKNOWN && - (rest[1] == 't' || rest[1] == 'T') && - !(rest[2] >= 'A' && rest[2] <= 'Z') && - !(rest[2] >= 'a' && rest[2] <= 'z')) - /* UT is the same as GMT but UTx is not. */ - zone = TT_GMT; - break; - case 'w': case 'W': - if (dotw == TT_UNKNOWN && - (rest[1] == 'e' || rest[1] == 'E') && - (rest[2] == 'd' || rest[2] == 'D')) - dotw = TT_WED; - break; - - case '+': case '-': - { - const char *end; - int sign; - if (zone_offset != -1) - { - /* already got one... */ - rest++; - break; - } - if (zone != TT_UNKNOWN && zone != TT_GMT) - { - /* GMT+0300 is legal, but PST+0300 is not. */ - rest++; - break; - } - - sign = ((*rest == '+') ? 1 : -1); - rest++; /* move over sign */ - end = rest; - while (*end >= '0' && *end <= '9') - end++; - if (rest == end) /* no digits here */ - break; - - if ((end - rest) == 4) - /* offset in HHMM */ - zone_offset = (((((rest[0]-'0')*10) + (rest[1]-'0')) * 60) + - (((rest[2]-'0')*10) + (rest[3]-'0'))); - else if ((end - rest) == 2) - /* offset in hours */ - zone_offset = (((rest[0]-'0')*10) + (rest[1]-'0')) * 60; - else if ((end - rest) == 1) - /* offset in hours */ - zone_offset = (rest[0]-'0') * 60; - else - /* 3 or >4 */ - break; - - zone_offset *= sign; - zone = TT_GMT; - break; - } - - case '0': case '1': case '2': case '3': case '4': - case '5': case '6': case '7': case '8': case '9': - { - int tmp_hour = -1; - int tmp_min = -1; - int tmp_sec = -1; - int tmp_usec = -1; - const char *end = rest + 1; - while (*end >= '0' && *end <= '9') - end++; - - /* end is now the first character after a range of digits. */ - - if (*end == ':') - { - if (hour >= 0 && min >= 0) /* already got it */ - break; - - /* We have seen "[0-9]+:", so this is probably HH:MM[:SS] */ - if ((end - rest) > 2) - /* it is [0-9][0-9][0-9]+: */ - break; - else if ((end - rest) == 2) - tmp_hour = ((rest[0]-'0')*10 + - (rest[1]-'0')); - else - tmp_hour = (rest[0]-'0'); - - /* move over the colon, and parse minutes */ - - rest = ++end; - while (*end >= '0' && *end <= '9') - end++; - - if (end == rest) - /* no digits after first colon? */ - break; - else if ((end - rest) > 2) - /* it is [0-9][0-9][0-9]+: */ - break; - else if ((end - rest) == 2) - tmp_min = ((rest[0]-'0')*10 + - (rest[1]-'0')); - else - tmp_min = (rest[0]-'0'); - - /* now go for seconds */ - rest = end; - if (*rest == ':') - rest++; - end = rest; - while (*end >= '0' && *end <= '9') - end++; - - if (end == rest) - /* no digits after second colon - that's ok. */ - ; - else if ((end - rest) > 2) - /* it is [0-9][0-9][0-9]+: */ - break; - else if ((end - rest) == 2) - tmp_sec = ((rest[0]-'0')*10 + - (rest[1]-'0')); - else - tmp_sec = (rest[0]-'0'); - - /* fractional second */ - rest = end; - if (*rest == '.') - { - rest++; - end++; - tmp_usec = 0; - /* use up to 6 digits, skip over the rest */ - while (*end >= '0' && *end <= '9') - { - if (end - rest < 6) - tmp_usec = tmp_usec * 10 + *end - '0'; - end++; - } - int ndigits = end - rest; - while (ndigits++ < 6) - tmp_usec *= 10; - rest = end; - } - - if (*rest == 'Z') - { - zone = TT_GMT; - rest++; - } - else if (tmp_hour <= 12) - { - /* If we made it here, we've parsed hour and min, - and possibly sec, so the current token is a time. - Now skip over whitespace and see if there's an AM - or PM directly following the time. - */ - const char *s = end; - while (*s && (*s == ' ' || *s == '\t')) - s++; - if ((s[0] == 'p' || s[0] == 'P') && - (s[1] == 'm' || s[1] == 'M')) - /* 10:05pm == 22:05, and 12:05pm == 12:05 */ - tmp_hour = (tmp_hour == 12 ? 12 : tmp_hour + 12); - else if (tmp_hour == 12 && - (s[0] == 'a' || s[0] == 'A') && - (s[1] == 'm' || s[1] == 'M')) - /* 12:05am == 00:05 */ - tmp_hour = 0; - } - - hour = tmp_hour; - min = tmp_min; - sec = tmp_sec; - usec = tmp_usec; - rest = end; - break; - } - else if ((*end == '/' || *end == '-') && - end[1] >= '0' && end[1] <= '9') - { - /* Perhaps this is 6/16/95, 16/6/95, 6-16-95, or 16-6-95 - or even 95-06-05 or 1995-06-22. - */ - int n1, n2, n3; - const char *s; - - if (month != TT_UNKNOWN) - /* if we saw a month name, this can't be. */ - break; - - s = rest; - - n1 = (*s++ - '0'); /* first 1, 2 or 4 digits */ - if (*s >= '0' && *s <= '9') - { - n1 = n1*10 + (*s++ - '0'); - - if (*s >= '0' && *s <= '9') /* optional digits 3 and 4 */ - { - n1 = n1*10 + (*s++ - '0'); - if (*s < '0' || *s > '9') - break; - n1 = n1*10 + (*s++ - '0'); - } - } - - if (*s != '/' && *s != '-') /* slash */ - break; - s++; - - if (*s < '0' || *s > '9') /* second 1 or 2 digits */ - break; - n2 = (*s++ - '0'); - if (*s >= '0' && *s <= '9') - n2 = n2*10 + (*s++ - '0'); - - if (*s != '/' && *s != '-') /* slash */ - break; - s++; - - if (*s < '0' || *s > '9') /* third 1, 2, 4, or 5 digits */ - break; - n3 = (*s++ - '0'); - if (*s >= '0' && *s <= '9') - n3 = n3*10 + (*s++ - '0'); - - if (*s >= '0' && *s <= '9') /* optional digits 3, 4, and 5 */ - { - n3 = n3*10 + (*s++ - '0'); - if (*s < '0' || *s > '9') - break; - n3 = n3*10 + (*s++ - '0'); - if (*s >= '0' && *s <= '9') - n3 = n3*10 + (*s++ - '0'); - } - - if (*s == 'T' && s[1] >= '0' && s[1] <= '9') - /* followed by ISO 8601 T delimiter and number is ok */ - ; - else if ((*s >= '0' && *s <= '9') || - (*s >= 'A' && *s <= 'Z') || - (*s >= 'a' && *s <= 'z')) - /* but other alphanumerics are not ok */ - break; - - /* Ok, we parsed three multi-digit numbers, with / or - - between them. Now decide what the hell they are - (DD/MM/YY or MM/DD/YY or [YY]YY/MM/DD.) - */ - - if (n1 > 31 || n1 == 0) /* must be [YY]YY/MM/DD */ - { - if (n2 > 12) break; - if (n3 > 31) break; - year = n1; - if (year < 70) - year += 2000; - else if (year < 100) - year += 1900; - month = (TIME_TOKEN)(n2 + ((int)TT_JAN) - 1); - date = n3; - rest = s; - break; - } - - if (n1 > 12 && n2 > 12) /* illegal */ - { - rest = s; - break; - } - - if (n3 < 70) - n3 += 2000; - else if (n3 < 100) - n3 += 1900; - - if (n1 > 12) /* must be DD/MM/YY */ - { - date = n1; - month = (TIME_TOKEN)(n2 + ((int)TT_JAN) - 1); - year = n3; - } - else /* assume MM/DD/YY */ - { - /* #### In the ambiguous case, should we consult the - locale to find out the local default? */ - month = (TIME_TOKEN)(n1 + ((int)TT_JAN) - 1); - date = n2; - year = n3; - } - rest = s; - } - else if ((*end >= 'A' && *end <= 'Z') || - (*end >= 'a' && *end <= 'z')) - /* Digits followed by non-punctuation - what's that? */ - ; - else if ((end - rest) == 5) /* five digits is a year */ - year = (year < 0 - ? ((rest[0]-'0')*10000L + - (rest[1]-'0')*1000L + - (rest[2]-'0')*100L + - (rest[3]-'0')*10L + - (rest[4]-'0')) - : year); - else if ((end - rest) == 4) /* four digits is a year */ - year = (year < 0 - ? ((rest[0]-'0')*1000L + - (rest[1]-'0')*100L + - (rest[2]-'0')*10L + - (rest[3]-'0')) - : year); - else if ((end - rest) == 2) /* two digits - date or year */ - { - int n = ((rest[0]-'0')*10 + - (rest[1]-'0')); - /* If we don't have a date (day of the month) and we see a number - less than 32, then assume that is the date. - - Otherwise, if we have a date and not a year, assume this is the - year. If it is less than 70, then assume it refers to the 21st - century. If it is two digits (>= 70), assume it refers to this - century. Otherwise, assume it refers to an unambiguous year. - - The world will surely end soon. - */ - if (date < 0 && n < 32) - date = n; - else if (year < 0) - { - if (n < 70) - year = 2000 + n; - else if (n < 100) - year = 1900 + n; - else - year = n; - } - /* else what the hell is this. */ - } - else if ((end - rest) == 1) /* one digit - date */ - date = (date < 0 ? (rest[0]-'0') : date); - /* else, three or more than five digits - what's that? */ - - break; - } /* case '0' .. '9' */ - } /* switch */ - - /* Skip to the end of this token, whether we parsed it or not. - Tokens are delimited by whitespace, or ,;-+/()[] but explicitly not .: - 'T' is also treated as delimiter when followed by a digit (ISO 8601). - */ - while (*rest && - *rest != ' ' && *rest != '\t' && - *rest != ',' && *rest != ';' && - *rest != '-' && *rest != '+' && - *rest != '/' && - *rest != '(' && *rest != ')' && *rest != '[' && *rest != ']' && - !(*rest == 'T' && rest[1] >= '0' && rest[1] <= '9') - ) - rest++; - /* skip over uninteresting chars. */ - SKIP_MORE: - while (*rest == ' ' || *rest == '\t' || - *rest == ',' || *rest == ';' || *rest == '/' || - *rest == '(' || *rest == ')' || *rest == '[' || *rest == ']') - rest++; - - /* "-" is ignored at the beginning of a token if we have not yet - parsed a year (e.g., the second "-" in "30-AUG-1966"), or if - the character after the dash is not a digit. */ - if (*rest == '-' && ((rest > string && - isalpha((unsigned char)rest[-1]) && year < 0) || - rest[1] < '0' || rest[1] > '9')) - { - rest++; - goto SKIP_MORE; - } - - /* Skip T that may precede ISO 8601 time. */ - if (*rest == 'T' && rest[1] >= '0' && rest[1] <= '9') - rest++; - } /* while */ - - if (zone != TT_UNKNOWN && zone_offset == -1) - { - switch (zone) - { - case TT_PST: zone_offset = -8 * 60; break; - case TT_PDT: zone_offset = -8 * 60; dst_offset = 1 * 60; break; - case TT_MST: zone_offset = -7 * 60; break; - case TT_MDT: zone_offset = -7 * 60; dst_offset = 1 * 60; break; - case TT_CST: zone_offset = -6 * 60; break; - case TT_CDT: zone_offset = -6 * 60; dst_offset = 1 * 60; break; - case TT_EST: zone_offset = -5 * 60; break; - case TT_EDT: zone_offset = -5 * 60; dst_offset = 1 * 60; break; - case TT_AST: zone_offset = -4 * 60; break; - case TT_NST: zone_offset = -3 * 60 - 30; break; - case TT_GMT: zone_offset = 0 * 60; break; - case TT_BST: zone_offset = 0 * 60; dst_offset = 1 * 60; break; - case TT_MET: zone_offset = 1 * 60; break; - case TT_EET: zone_offset = 2 * 60; break; - case TT_JST: zone_offset = 9 * 60; break; - default: - PR_ASSERT (0); - break; - } - } - - /* If we didn't find a year, month, or day-of-the-month, we can't - possibly parse this, and in fact, mktime() will do something random - (I'm seeing it return "Tue Feb 5 06:28:16 2036", which is no doubt - a numerologically significant date... */ - if (month == TT_UNKNOWN || date == -1 || year == -1 || year > PR_INT16_MAX) - return PR_FAILURE; - - memset(result, 0, sizeof(*result)); - if (usec != -1) - result->tm_usec = usec; - if (sec != -1) - result->tm_sec = sec; - if (min != -1) - result->tm_min = min; - if (hour != -1) - result->tm_hour = hour; - if (date != -1) - result->tm_mday = date; - if (month != TT_UNKNOWN) - result->tm_month = (((int)month) - ((int)TT_JAN)); - if (year != -1) - result->tm_year = static_cast<PRInt16>(year); - if (dotw != TT_UNKNOWN) - result->tm_wday = static_cast<PRInt8>(((int)dotw) - ((int)TT_SUN)); - /* - * Mainly to compute wday and yday, but normalized time is also required - * by the check below that works around a Visual C++ 2005 mktime problem. - */ - PR_NormalizeTime(result, PR_GMTParameters); - /* The remaining work is to set the gmt and dst offsets in tm_params. */ - - if (zone == TT_UNKNOWN && default_to_gmt) - { - /* No zone was specified, so pretend the zone was GMT. */ - zone = TT_GMT; - zone_offset = 0; - } - - if (zone_offset == -1) - { - /* no zone was specified, and we're to assume that everything - is local. */ - struct tm localTime; - time_t secs; - - PR_ASSERT(result->tm_month > -1 && - result->tm_mday > 0 && - result->tm_hour > -1 && - result->tm_min > -1 && - result->tm_sec > -1); - - /* - * To obtain time_t from a tm structure representing the local - * time, we call mktime(). However, we need to see if we are - * on 1-Jan-1970 or before. If we are, we can't call mktime() - * because mktime() will crash on win16. In that case, we - * calculate zone_offset based on the zone offset at - * 00:00:00, 2 Jan 1970 GMT, and subtract zone_offset from the - * date we are parsing to transform the date to GMT. We also - * do so if mktime() returns (time_t) -1 (time out of range). - */ - - /* month, day, hours, mins and secs are always non-negative - so we dont need to worry about them. */ - if (result->tm_year >= 1970) - { - localTime.tm_sec = result->tm_sec; - localTime.tm_min = result->tm_min; - localTime.tm_hour = result->tm_hour; - localTime.tm_mday = result->tm_mday; - localTime.tm_mon = result->tm_month; - localTime.tm_year = result->tm_year - 1900; - /* Set this to -1 to tell mktime "I don't care". If you set - it to 0 or 1, you are making assertions about whether the - date you are handing it is in daylight savings mode or not; - and if you're wrong, it will "fix" it for you. */ - localTime.tm_isdst = -1; - -#if _MSC_VER == 1400 /* 1400 = Visual C++ 2005 (8.0) */ - /* - * mktime will return (time_t) -1 if the input is a date - * after 23:59:59, December 31, 3000, US Pacific Time (not - * UTC as documented): - * http://msdn.microsoft.com/en-us/library/d1y53h2a(VS.80).aspx - * But if the year is 3001, mktime also invokes the invalid - * parameter handler, causing the application to crash. This - * problem has been reported in - * http://connect.microsoft.com/VisualStudio/feedback/ViewFeedback.aspx?FeedbackID=266036. - * We avoid this crash by not calling mktime if the date is - * out of range. To use a simple test that works in any time - * zone, we consider year 3000 out of range as well. (See - * bug 480740.) - */ - if (result->tm_year >= 3000) { - /* Emulate what mktime would have done. */ - errno = EINVAL; - secs = (time_t) -1; - } else { - secs = mktime(&localTime); - } -#else - secs = mktime(&localTime); -#endif - if (secs != (time_t) -1) - { - *result_imploded = (PRInt64)secs * PR_USEC_PER_SEC; - *result_imploded += result->tm_usec; - return PR_SUCCESS; - } - } - - /* So mktime() can't handle this case. We assume the - zone_offset for the date we are parsing is the same as - the zone offset on 00:00:00 2 Jan 1970 GMT. */ - secs = 86400; - localtime_r(&secs, &localTime); - zone_offset = localTime.tm_min - + 60 * localTime.tm_hour - + 1440 * (localTime.tm_mday - 2); - } - - result->tm_params.tp_gmt_offset = zone_offset * 60; - result->tm_params.tp_dst_offset = dst_offset * 60; - - *result_imploded = PR_ImplodeTime(result); - return PR_SUCCESS; -}
diff --git a/base/third_party/nspr/prtime.h b/base/third_party/nspr/prtime.h deleted file mode 100644 index 20bae38..0000000 --- a/base/third_party/nspr/prtime.h +++ /dev/null
@@ -1,263 +0,0 @@ -/* Portions are Copyright (C) 2011 Google Inc */ -/* ***** BEGIN LICENSE BLOCK ***** - * Version: MPL 1.1/GPL 2.0/LGPL 2.1 - * - * The contents of this file are subject to the Mozilla Public License Version - * 1.1 (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * http://www.mozilla.org/MPL/ - * - * Software distributed under the License is distributed on an "AS IS" basis, - * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License - * for the specific language governing rights and limitations under the - * License. - * - * The Original Code is the Netscape Portable Runtime (NSPR). - * - * The Initial Developer of the Original Code is - * Netscape Communications Corporation. - * Portions created by the Initial Developer are Copyright (C) 1998-2000 - * the Initial Developer. All Rights Reserved. - * - * Contributor(s): - * - * Alternatively, the contents of this file may be used under the terms of - * either the GNU General Public License Version 2 or later (the "GPL"), or - * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"), - * in which case the provisions of the GPL or the LGPL are applicable instead - * of those above. If you wish to allow use of your version of this file only - * under the terms of either the GPL or the LGPL, and not to allow others to - * use your version of this file under the terms of the MPL, indicate your - * decision by deleting the provisions above and replace them with the notice - * and other provisions required by the GPL or the LGPL. If you do not delete - * the provisions above, a recipient may use your version of this file under - * the terms of any one of the MPL, the GPL or the LGPL. - * - * ***** END LICENSE BLOCK ***** */ - -/* - *--------------------------------------------------------------------------- - * - * prtime.h -- - * - * NSPR date and time functions - * CVS revision 3.10 - * This file contains definitions of NSPR's basic types required by - * prtime.cc. These types have been copied over from the following NSPR - * files prtime.h, prtypes.h(CVS revision 3.35), prlong.h(CVS revision 3.13) - * - *--------------------------------------------------------------------------- - */ - -#ifndef BASE_PRTIME_H__ -#define BASE_PRTIME_H__ - -#include <stdint.h> - -#include "base/base_export.h" - -typedef int8_t PRInt8; -typedef int16_t PRInt16; -typedef int32_t PRInt32; -typedef int64_t PRInt64; -typedef int PRIntn; - -typedef PRIntn PRBool; -#define PR_TRUE 1 -#define PR_FALSE 0 - -typedef enum { PR_FAILURE = -1, PR_SUCCESS = 0 } PRStatus; - -#define PR_ASSERT DCHECK -#define PR_CALLBACK -#define PR_INT16_MAX 32767 -#define NSPR_API(__type) extern __type - -/* - * Long-long (64-bit signed integer type) support macros used by - * PR_ImplodeTime(). - * See http://lxr.mozilla.org/nspr/source/pr/include/prlong.h - */ - -#define LL_I2L(l, i) ((l) = (PRInt64)(i)) -#define LL_MUL(r, a, b) ((r) = (a) * (b)) -#define LL_ADD(r, a, b) ((r) = (a) + (b)) -#define LL_SUB(r, a, b) ((r) = (a) - (b)) - -/**********************************************************************/ -/************************* TYPES AND CONSTANTS ************************/ -/**********************************************************************/ - -#define PR_MSEC_PER_SEC 1000UL -#define PR_USEC_PER_SEC 1000000UL -#define PR_NSEC_PER_SEC 1000000000UL -#define PR_USEC_PER_MSEC 1000UL -#define PR_NSEC_PER_MSEC 1000000UL - -/* - * PRTime -- - * - * NSPR represents basic time as 64-bit signed integers relative - * to midnight (00:00:00), January 1, 1970 Greenwich Mean Time (GMT). - * (GMT is also known as Coordinated Universal Time, UTC.) - * The units of time are in microseconds. Negative times are allowed - * to represent times prior to the January 1970 epoch. Such values are - * intended to be exported to other systems or converted to human - * readable form. - * - * Notes on porting: PRTime corresponds to time_t in ANSI C. NSPR 1.0 - * simply uses PRInt64. - */ - -typedef PRInt64 PRTime; - -/* - * Time zone and daylight saving time corrections applied to GMT to - * obtain the local time of some geographic location - */ - -typedef struct PRTimeParameters { - PRInt32 tp_gmt_offset; /* the offset from GMT in seconds */ - PRInt32 tp_dst_offset; /* contribution of DST in seconds */ -} PRTimeParameters; - -/* - * PRExplodedTime -- - * - * Time broken down into human-readable components such as year, month, - * day, hour, minute, second, and microsecond. Time zone and daylight - * saving time corrections may be applied. If they are applied, the - * offsets from the GMT must be saved in the 'tm_params' field so that - * all the information is available to reconstruct GMT. - * - * Notes on porting: PRExplodedTime corrresponds to struct tm in - * ANSI C, with the following differences: - * - an additional field tm_usec; - * - replacing tm_isdst by tm_params; - * - the month field is spelled tm_month, not tm_mon; - * - we use absolute year, AD, not the year since 1900. - * The corresponding type in NSPR 1.0 is called PRTime. Below is - * a table of date/time type correspondence in the three APIs: - * API time since epoch time in components - * ANSI C time_t struct tm - * NSPR 1.0 PRInt64 PRTime - * NSPR 2.0 PRTime PRExplodedTime - */ - -typedef struct PRExplodedTime { - PRInt32 tm_usec; /* microseconds past tm_sec (0-99999) */ - PRInt32 tm_sec; /* seconds past tm_min (0-61, accomodating - up to two leap seconds) */ - PRInt32 tm_min; /* minutes past tm_hour (0-59) */ - PRInt32 tm_hour; /* hours past tm_day (0-23) */ - PRInt32 tm_mday; /* days past tm_mon (1-31, note that it - starts from 1) */ - PRInt32 tm_month; /* months past tm_year (0-11, Jan = 0) */ - PRInt16 tm_year; /* absolute year, AD (note that we do not - count from 1900) */ - - PRInt8 tm_wday; /* calculated day of the week - (0-6, Sun = 0) */ - PRInt16 tm_yday; /* calculated day of the year - (0-365, Jan 1 = 0) */ - - PRTimeParameters tm_params; /* time parameters used by conversion */ -} PRExplodedTime; - -/* - * PRTimeParamFn -- - * - * A function of PRTimeParamFn type returns the time zone and - * daylight saving time corrections for some geographic location, - * given the current time in GMT. The input argument gmt should - * point to a PRExplodedTime that is in GMT, i.e., whose - * tm_params contains all 0's. - * - * For any time zone other than GMT, the computation is intended to - * consist of two steps: - * - Figure out the time zone correction, tp_gmt_offset. This number - * usually depends on the geographic location only. But it may - * also depend on the current time. For example, all of China - * is one time zone right now. But this situation may change - * in the future. - * - Figure out the daylight saving time correction, tp_dst_offset. - * This number depends on both the geographic location and the - * current time. Most of the DST rules are expressed in local - * current time. If so, one should apply the time zone correction - * to GMT before applying the DST rules. - */ - -typedef PRTimeParameters (PR_CALLBACK *PRTimeParamFn)(const PRExplodedTime *gmt); - -/**********************************************************************/ -/****************************** FUNCTIONS *****************************/ -/**********************************************************************/ - -NSPR_API(PRTime) -PR_ImplodeTime(const PRExplodedTime *exploded); - -/* - * Adjust exploded time to normalize field overflows after manipulation. - * Note that the following fields of PRExplodedTime should not be - * manipulated: - * - tm_month and tm_year: because the number of days in a month and - * number of days in a year are not constant, it is ambiguous to - * manipulate the month and year fields, although one may be tempted - * to. For example, what does "a month from January 31st" mean? - * - tm_wday and tm_yday: these fields are calculated by NSPR. Users - * should treat them as "read-only". - */ - -NSPR_API(void) PR_NormalizeTime( - PRExplodedTime *exploded, PRTimeParamFn params); - -/**********************************************************************/ -/*********************** TIME PARAMETER FUNCTIONS *********************/ -/**********************************************************************/ - -/* Time parameters that represent Greenwich Mean Time */ -NSPR_API(PRTimeParameters) PR_GMTParameters(const PRExplodedTime *gmt); - -/* - * This parses a time/date string into a PRTime - * (microseconds after "1-Jan-1970 00:00:00 GMT"). - * It returns PR_SUCCESS on success, and PR_FAILURE - * if the time/date string can't be parsed. - * - * Many formats are handled, including: - * - * 14 Apr 89 03:20:12 - * 14 Apr 89 03:20 GMT - * Fri, 17 Mar 89 4:01:33 - * Fri, 17 Mar 89 4:01 GMT - * Mon Jan 16 16:12 PDT 1989 - * Mon Jan 16 16:12 +0130 1989 - * 6 May 1992 16:41-JST (Wednesday) - * 22-AUG-1993 10:59:12.82 - * 22-AUG-1993 10:59pm - * 22-AUG-1993 12:59am - * 22-AUG-1993 12:59 PM - * Friday, August 04, 1995 3:54 PM - * 06/21/95 04:24:34 PM - * 20/06/95 21:07 - * 95-06-08 19:32:48 EDT - * 1995-06-17T23:11:25.342156Z - * - * If the input string doesn't contain a description of the timezone, - * we consult the `default_to_gmt' to decide whether the string should - * be interpreted relative to the local time zone (PR_FALSE) or GMT (PR_TRUE). - * The correct value for this argument depends on what standard specified - * the time string which you are parsing. - */ - -/* - * This is the only funtion that should be called from outside base, and only - * from the unit test. - */ - -BASE_EXPORT PRStatus PR_ParseTimeString ( - const char *string, - PRBool default_to_gmt, - PRTime *result); - -#endif // BASE_PRTIME_H__
diff --git a/base/threading/OWNERS b/base/threading/OWNERS deleted file mode 100644 index 4198e99..0000000 --- a/base/threading/OWNERS +++ /dev/null
@@ -1,2 +0,0 @@ -# For thread_resrictions.* -jam@chromium.org
diff --git a/base/threading/thread_collision_warner.cc b/base/threading/thread_collision_warner.cc deleted file mode 100644 index 547e11c..0000000 --- a/base/threading/thread_collision_warner.cc +++ /dev/null
@@ -1,64 +0,0 @@ -// Copyright (c) 2010 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/threading/thread_collision_warner.h" - -#include "base/logging.h" -#include "base/threading/platform_thread.h" - -namespace base { - -void DCheckAsserter::warn() { - NOTREACHED() << "Thread Collision"; -} - -static subtle::Atomic32 CurrentThread() { - const PlatformThreadId current_thread_id = PlatformThread::CurrentId(); - // We need to get the thread id into an atomic data type. This might be a - // truncating conversion, but any loss-of-information just increases the - // chance of a fault negative, not a false positive. - const subtle::Atomic32 atomic_thread_id = - static_cast<subtle::Atomic32>(current_thread_id); - - return atomic_thread_id; -} - -void ThreadCollisionWarner::EnterSelf() { - // If the active thread is 0 then I'll write the current thread ID - // if two or more threads arrive here only one will succeed to - // write on valid_thread_id_ the current thread ID. - subtle::Atomic32 current_thread_id = CurrentThread(); - - int previous_value = subtle::NoBarrier_CompareAndSwap(&valid_thread_id_, - 0, - current_thread_id); - if (previous_value != 0 && previous_value != current_thread_id) { - // gotcha! a thread is trying to use the same class and that is - // not current thread. - asserter_->warn(); - } - - subtle::NoBarrier_AtomicIncrement(&counter_, 1); -} - -void ThreadCollisionWarner::Enter() { - subtle::Atomic32 current_thread_id = CurrentThread(); - - if (subtle::NoBarrier_CompareAndSwap(&valid_thread_id_, - 0, - current_thread_id) != 0) { - // gotcha! another thread is trying to use the same class. - asserter_->warn(); - } - - subtle::NoBarrier_AtomicIncrement(&counter_, 1); -} - -void ThreadCollisionWarner::Leave() { - if (subtle::Barrier_AtomicIncrement(&counter_, -1) == 0) { - subtle::NoBarrier_Store(&valid_thread_id_, 0); - } -} - -} // namespace base
diff --git a/base/threading/thread_collision_warner.h b/base/threading/thread_collision_warner.h deleted file mode 100644 index b6993f6..0000000 --- a/base/threading/thread_collision_warner.h +++ /dev/null
@@ -1,245 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_THREADING_THREAD_COLLISION_WARNER_H_ -#define BASE_THREADING_THREAD_COLLISION_WARNER_H_ - -#include <memory> - -#include "base/atomicops.h" -#include "base/base_export.h" -#include "base/compiler_specific.h" -#include "base/macros.h" - -// A helper class alongside macros to be used to verify assumptions about thread -// safety of a class. -// -// Example: Queue implementation non thread-safe but still usable if clients -// are synchronized somehow. -// -// In this case the macro DFAKE_SCOPED_LOCK has to be -// used, it checks that if a thread is inside the push/pop then -// noone else is still inside the pop/push -// -// class NonThreadSafeQueue { -// public: -// ... -// void push(int) { DFAKE_SCOPED_LOCK(push_pop_); ... } -// int pop() { DFAKE_SCOPED_LOCK(push_pop_); ... } -// ... -// private: -// DFAKE_MUTEX(push_pop_); -// }; -// -// -// Example: Queue implementation non thread-safe but still usable if clients -// are synchronized somehow, it calls a method to "protect" from -// a "protected" method -// -// In this case the macro DFAKE_SCOPED_RECURSIVE_LOCK -// has to be used, it checks that if a thread is inside the push/pop -// then noone else is still inside the pop/push -// -// class NonThreadSafeQueue { -// public: -// void push(int) { -// DFAKE_SCOPED_LOCK(push_pop_); -// ... -// } -// int pop() { -// DFAKE_SCOPED_RECURSIVE_LOCK(push_pop_); -// bar(); -// ... -// } -// void bar() { DFAKE_SCOPED_RECURSIVE_LOCK(push_pop_); ... } -// ... -// private: -// DFAKE_MUTEX(push_pop_); -// }; -// -// -// Example: Queue implementation not usable even if clients are synchronized, -// so only one thread in the class life cycle can use the two members -// push/pop. -// -// In this case the macro DFAKE_SCOPED_LOCK_THREAD_LOCKED pins the -// specified -// critical section the first time a thread enters push or pop, from -// that time on only that thread is allowed to execute push or pop. -// -// class NonThreadSafeQueue { -// public: -// ... -// void push(int) { DFAKE_SCOPED_LOCK_THREAD_LOCKED(push_pop_); ... } -// int pop() { DFAKE_SCOPED_LOCK_THREAD_LOCKED(push_pop_); ... } -// ... -// private: -// DFAKE_MUTEX(push_pop_); -// }; -// -// -// Example: Class that has to be contructed/destroyed on same thread, it has -// a "shareable" method (with external synchronization) and a not -// shareable method (even with external synchronization). -// -// In this case 3 Critical sections have to be defined -// -// class ExoticClass { -// public: -// ExoticClass() { DFAKE_SCOPED_LOCK_THREAD_LOCKED(ctor_dtor_); ... } -// ~ExoticClass() { DFAKE_SCOPED_LOCK_THREAD_LOCKED(ctor_dtor_); ... } -// -// void Shareable() { DFAKE_SCOPED_LOCK(shareable_section_); ... } -// void NotShareable() { DFAKE_SCOPED_LOCK_THREAD_LOCKED(ctor_dtor_); ... } -// ... -// private: -// DFAKE_MUTEX(ctor_dtor_); -// DFAKE_MUTEX(shareable_section_); -// }; - - -#if !defined(NDEBUG) - -// Defines a class member that acts like a mutex. It is used only as a -// verification tool. -#define DFAKE_MUTEX(obj) \ - mutable base::ThreadCollisionWarner obj -// Asserts the call is never called simultaneously in two threads. Used at -// member function scope. -#define DFAKE_SCOPED_LOCK(obj) \ - base::ThreadCollisionWarner::ScopedCheck s_check_##obj(&obj) -// Asserts the call is never called simultaneously in two threads. Used at -// member function scope. Same as DFAKE_SCOPED_LOCK but allows recursive locks. -#define DFAKE_SCOPED_RECURSIVE_LOCK(obj) \ - base::ThreadCollisionWarner::ScopedRecursiveCheck sr_check_##obj(&obj) -// Asserts the code is always executed in the same thread. -#define DFAKE_SCOPED_LOCK_THREAD_LOCKED(obj) \ - base::ThreadCollisionWarner::Check check_##obj(&obj) - -#else - -#define DFAKE_MUTEX(obj) typedef void InternalFakeMutexType##obj -#define DFAKE_SCOPED_LOCK(obj) ((void)0) -#define DFAKE_SCOPED_RECURSIVE_LOCK(obj) ((void)0) -#define DFAKE_SCOPED_LOCK_THREAD_LOCKED(obj) ((void)0) - -#endif - -namespace base { - -// The class ThreadCollisionWarner uses an Asserter to notify the collision -// AsserterBase is the interfaces and DCheckAsserter is the default asserter -// used. During the unit tests is used another class that doesn't "DCHECK" -// in case of collision (check thread_collision_warner_unittests.cc) -struct BASE_EXPORT AsserterBase { - virtual ~AsserterBase() = default; - virtual void warn() = 0; -}; - -struct BASE_EXPORT DCheckAsserter : public AsserterBase { - ~DCheckAsserter() override = default; - void warn() override; -}; - -class BASE_EXPORT ThreadCollisionWarner { - public: - // The parameter asserter is there only for test purpose - explicit ThreadCollisionWarner(AsserterBase* asserter = new DCheckAsserter()) - : valid_thread_id_(0), - counter_(0), - asserter_(asserter) {} - - ~ThreadCollisionWarner() { - delete asserter_; - } - - // This class is meant to be used through the macro - // DFAKE_SCOPED_LOCK_THREAD_LOCKED - // it doesn't leave the critical section, as opposed to ScopedCheck, - // because the critical section being pinned is allowed to be used only - // from one thread - class BASE_EXPORT Check { - public: - explicit Check(ThreadCollisionWarner* warner) - : warner_(warner) { - warner_->EnterSelf(); - } - - ~Check() = default; - - private: - ThreadCollisionWarner* warner_; - - DISALLOW_COPY_AND_ASSIGN(Check); - }; - - // This class is meant to be used through the macro - // DFAKE_SCOPED_LOCK - class BASE_EXPORT ScopedCheck { - public: - explicit ScopedCheck(ThreadCollisionWarner* warner) - : warner_(warner) { - warner_->Enter(); - } - - ~ScopedCheck() { - warner_->Leave(); - } - - private: - ThreadCollisionWarner* warner_; - - DISALLOW_COPY_AND_ASSIGN(ScopedCheck); - }; - - // This class is meant to be used through the macro - // DFAKE_SCOPED_RECURSIVE_LOCK - class BASE_EXPORT ScopedRecursiveCheck { - public: - explicit ScopedRecursiveCheck(ThreadCollisionWarner* warner) - : warner_(warner) { - warner_->EnterSelf(); - } - - ~ScopedRecursiveCheck() { - warner_->Leave(); - } - - private: - ThreadCollisionWarner* warner_; - - DISALLOW_COPY_AND_ASSIGN(ScopedRecursiveCheck); - }; - - private: - // This method stores the current thread identifier and does a DCHECK - // if a another thread has already done it, it is safe if same thread - // calls this multiple time (recursion allowed). - void EnterSelf(); - - // Same as EnterSelf but recursion is not allowed. - void Enter(); - - // Removes the thread_id stored in order to allow other threads to - // call EnterSelf or Enter. - void Leave(); - - // This stores the thread id that is inside the critical section, if the - // value is 0 then no thread is inside. - volatile subtle::Atomic32 valid_thread_id_; - - // Counter to trace how many time a critical section was "pinned" - // (when allowed) in order to unpin it when counter_ reaches 0. - volatile subtle::Atomic32 counter_; - - // Here only for class unit tests purpose, during the test I need to not - // DCHECK but notify the collision with something else. - AsserterBase* asserter_; - - DISALLOW_COPY_AND_ASSIGN(ThreadCollisionWarner); -}; - -} // namespace base - -#endif // BASE_THREADING_THREAD_COLLISION_WARNER_H_
diff --git a/base/time/OWNERS b/base/time/OWNERS deleted file mode 100644 index ff0520a..0000000 --- a/base/time/OWNERS +++ /dev/null
@@ -1,3 +0,0 @@ -miu@chromium.org - -# COMPONENT: Internals>Core
diff --git a/base/time/default_tick_clock.cc b/base/time/default_tick_clock.cc deleted file mode 100644 index 188c3cf..0000000 --- a/base/time/default_tick_clock.cc +++ /dev/null
@@ -1,23 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/time/default_tick_clock.h" - -#include "base/no_destructor.h" - -namespace base { - -DefaultTickClock::~DefaultTickClock() = default; - -TimeTicks DefaultTickClock::NowTicks() const { - return TimeTicks::Now(); -} - -// static -const DefaultTickClock* DefaultTickClock::GetInstance() { - static const base::NoDestructor<DefaultTickClock> default_tick_clock; - return default_tick_clock.get(); -} - -} // namespace base
diff --git a/base/time/default_tick_clock.h b/base/time/default_tick_clock.h deleted file mode 100644 index 78f8a99..0000000 --- a/base/time/default_tick_clock.h +++ /dev/null
@@ -1,27 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_TIME_DEFAULT_TICK_CLOCK_H_ -#define BASE_TIME_DEFAULT_TICK_CLOCK_H_ - -#include "base/base_export.h" -#include "base/time/tick_clock.h" - -namespace base { - -// DefaultClock is a Clock implementation that uses TimeTicks::Now(). -class BASE_EXPORT DefaultTickClock : public TickClock { - public: - ~DefaultTickClock() override; - - // Simply returns TimeTicks::Now(). - TimeTicks NowTicks() const override; - - // Returns a shared instance of DefaultTickClock. This is thread-safe. - static const DefaultTickClock* GetInstance(); -}; - -} // namespace base - -#endif // BASE_TIME_DEFAULT_TICK_CLOCK_H_
diff --git a/base/time/tick_clock.cc b/base/time/tick_clock.cc deleted file mode 100644 index 79e396d..0000000 --- a/base/time/tick_clock.cc +++ /dev/null
@@ -1,11 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/time/tick_clock.h" - -namespace base { - -TickClock::~TickClock() = default; - -} // namespace base
diff --git a/base/time/tick_clock.h b/base/time/tick_clock.h deleted file mode 100644 index dc57354..0000000 --- a/base/time/tick_clock.h +++ /dev/null
@@ -1,40 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_TIME_TICK_CLOCK_H_ -#define BASE_TIME_TICK_CLOCK_H_ - -#include "base/base_export.h" -#include "base/time/time.h" - -namespace base { - -// A TickClock is an interface for objects that vend TimeTicks. It is -// intended to be able to test the behavior of classes with respect to -// non-decreasing time. -// -// See DefaultTickClock (base/time/default_tick_clock.h) for the default -// implementation that simply uses TimeTicks::Now(). -// -// (Other implementations that use TimeTicks::NowFromSystemTime() should -// be added as needed.) -// -// See SimpleTestTickClock (base/test/simple_test_tick_clock.h) for a -// simple test implementation. -// -// See Clock (base/time/clock.h) for the equivalent interface for Times. -class BASE_EXPORT TickClock { - public: - virtual ~TickClock(); - - // NowTicks() must be safe to call from any thread. The caller may - // assume that NowTicks() is monotonic (but not strictly monotonic). - // In other words, the returned TimeTicks will never decrease with - // time, although they might "stand still". - virtual TimeTicks NowTicks() const = 0; -}; - -} // namespace base - -#endif // BASE_TIME_TICK_CLOCK_H_
diff --git a/base/time/time.cc b/base/time/time.cc index 577895c..bd746b3 100644 --- a/base/time/time.cc +++ b/base/time/time.cc
@@ -14,7 +14,6 @@ #include "base/macros.h" #include "base/no_destructor.h" #include "base/strings/stringprintf.h" -#include "base/third_party/nspr/prtime.h" #include "base/time/time_override.h" #include "build_config.h" @@ -291,27 +290,6 @@ } // static -bool Time::FromStringInternal(const char* time_string, - bool is_local, - Time* parsed_time) { - DCHECK((time_string != nullptr) && (parsed_time != nullptr)); - - if (time_string[0] == '\0') - return false; - - PRTime result_time = 0; - PRStatus result = PR_ParseTimeString(time_string, - is_local ? PR_FALSE : PR_TRUE, - &result_time); - if (PR_SUCCESS != result) - return false; - - result_time += kTimeTToMicrosecondsOffset; - *parsed_time = Time(result_time); - return true; -} - -// static bool Time::ExplodedMostlyEquals(const Exploded& lhs, const Exploded& rhs) { return lhs.year == rhs.year && lhs.month == rhs.month && lhs.day_of_month == rhs.day_of_month && lhs.hour == rhs.hour &&
diff --git a/base/time/time.h b/base/time/time.h index 936c746..eef95f3 100644 --- a/base/time/time.h +++ b/base/time/time.h
@@ -619,23 +619,6 @@ return FromExploded(true, exploded, time); } - // Converts a string representation of time to a Time object. - // An example of a time string which is converted is as below:- - // "Tue, 15 Nov 1994 12:45:26 GMT". If the timezone is not specified - // in the input string, FromString assumes local time and FromUTCString - // assumes UTC. A timezone that cannot be parsed (e.g. "UTC" which is not - // specified in RFC822) is treated as if the timezone is not specified. - // TODO(iyengar) Move the FromString/FromTimeT/ToTimeT/FromFileTime to - // a new time converter class. - static bool FromString(const char* time_string, - Time* parsed_time) WARN_UNUSED_RESULT { - return FromStringInternal(time_string, true, parsed_time); - } - static bool FromUTCString(const char* time_string, - Time* parsed_time) WARN_UNUSED_RESULT { - return FromStringInternal(time_string, false, parsed_time); - } - // Fills the given exploded structure with either the local time or UTC from // this time structure (containing UTC). void UTCExplode(Exploded* exploded) const { @@ -675,17 +658,6 @@ const Exploded& exploded, Time* time) WARN_UNUSED_RESULT; - // Converts a string representation of time to a Time object. - // An example of a time string which is converted is as below:- - // "Tue, 15 Nov 1994 12:45:26 GMT". If the timezone is not specified - // in the input string, local time |is_local = true| or - // UTC |is_local = false| is assumed. A timezone that cannot be parsed - // (e.g. "UTC" which is not specified in RFC822) is treated as if the - // timezone is not specified. - static bool FromStringInternal(const char* time_string, - bool is_local, - Time* parsed_time) WARN_UNUSED_RESULT; - // Comparison does not consider |day_of_week| when doing the operation. static bool ExplodedMostlyEquals(const Exploded& lhs, const Exploded& rhs) WARN_UNUSED_RESULT; @@ -866,12 +838,6 @@ return TimeTicks(us); } -#if defined(OS_WIN) - protected: - typedef DWORD (*TickFunctionType)(void); - static TickFunctionType SetMockTickFunction(TickFunctionType ticker); -#endif - private: friend class time_internal::TimeBase<TimeTicks>; @@ -896,10 +862,8 @@ static bool IsSupported() WARN_UNUSED_RESULT { #if (defined(_POSIX_THREAD_CPUTIME) && (_POSIX_THREAD_CPUTIME >= 0)) || \ (defined(OS_MACOSX) && !defined(OS_IOS)) || defined(OS_ANDROID) || \ - defined(OS_FUCHSIA) + defined(OS_FUCHSIA) || defined(OS_WIN) return true; -#elif defined(OS_WIN) - return IsSupportedWin(); #else return false; #endif @@ -956,7 +920,6 @@ // allow testing. static double TSCTicksPerSecond(); - static bool IsSupportedWin() WARN_UNUSED_RESULT; static void WaitUntilInitializedWin(); #endif };
diff --git a/base/time/time_to_iso8601.cc b/base/time/time_to_iso8601.cc deleted file mode 100644 index 27e7bfc..0000000 --- a/base/time/time_to_iso8601.cc +++ /dev/null
@@ -1,20 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/time/time_to_iso8601.h" - -#include "base/strings/stringprintf.h" -#include "base/time/time.h" - -namespace base { - -std::string TimeToISO8601(const Time& t) { - Time::Exploded exploded; - t.UTCExplode(&exploded); - return StringPrintf("%04d-%02d-%02dT%02d:%02d:%02d.%03dZ", exploded.year, - exploded.month, exploded.day_of_month, exploded.hour, - exploded.minute, exploded.second, exploded.millisecond); -} - -} // namespace base
diff --git a/base/time/time_to_iso8601.h b/base/time/time_to_iso8601.h deleted file mode 100644 index 2643484..0000000 --- a/base/time/time_to_iso8601.h +++ /dev/null
@@ -1,20 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_TIME_TIME_TO_ISO8601_H_ -#define BASE_TIME_TIME_TO_ISO8601_H_ - -#include <string> - -#include "base/base_export.h" - -namespace base { - -class Time; - -BASE_EXPORT std::string TimeToISO8601(const base::Time& t); - -} // namespace base - -#endif // BASE_TIME_TIME_TO_ISO8601_H_
diff --git a/base/time/time_win.cc b/base/time/time_win.cc index 9c6eba0..6767fd6 100644 --- a/base/time/time_win.cc +++ b/base/time/time_win.cc
@@ -39,7 +39,6 @@ #include "base/atomicops.h" #include "base/bit_cast.h" -#include "base/cpu.h" #include "base/logging.h" #include "base/synchronization/lock.h" #include "base/threading/platform_thread.h" @@ -361,81 +360,6 @@ namespace { -// We define a wrapper to adapt between the __stdcall and __cdecl call of the -// mock function, and to avoid a static constructor. Assigning an import to a -// function pointer directly would require setup code to fetch from the IAT. -DWORD timeGetTimeWrapper() { - return timeGetTime(); -} - -DWORD (*g_tick_function)(void) = &timeGetTimeWrapper; - -// A structure holding the most significant bits of "last seen" and a -// "rollover" counter. -union LastTimeAndRolloversState { - // The state as a single 32-bit opaque value. - subtle::Atomic32 as_opaque_32; - - // The state as usable values. - struct { - // The top 8-bits of the "last" time. This is enough to check for rollovers - // and the small bit-size means fewer CompareAndSwap operations to store - // changes in state, which in turn makes for fewer retries. - uint8_t last_8; - // A count of the number of detected rollovers. Using this as bits 47-32 - // of the upper half of a 64-bit value results in a 48-bit tick counter. - // This extends the total rollover period from about 49 days to about 8800 - // years while still allowing it to be stored with last_8 in a single - // 32-bit value. - uint16_t rollovers; - } as_values; -}; -subtle::Atomic32 g_last_time_and_rollovers = 0; -static_assert( - sizeof(LastTimeAndRolloversState) <= sizeof(g_last_time_and_rollovers), - "LastTimeAndRolloversState does not fit in a single atomic word"); - -// We use timeGetTime() to implement TimeTicks::Now(). This can be problematic -// because it returns the number of milliseconds since Windows has started, -// which will roll over the 32-bit value every ~49 days. We try to track -// rollover ourselves, which works if TimeTicks::Now() is called at least every -// 48.8 days (not 49 days because only changes in the top 8 bits get noticed). -TimeTicks RolloverProtectedNow() { - LastTimeAndRolloversState state; - DWORD now; // DWORD is always unsigned 32 bits. - - while (true) { - // Fetch the "now" and "last" tick values, updating "last" with "now" and - // incrementing the "rollovers" counter if the tick-value has wrapped back - // around. Atomic operations ensure that both "last" and "rollovers" are - // always updated together. - int32_t original = subtle::Acquire_Load(&g_last_time_and_rollovers); - state.as_opaque_32 = original; - now = g_tick_function(); - uint8_t now_8 = static_cast<uint8_t>(now >> 24); - if (now_8 < state.as_values.last_8) - ++state.as_values.rollovers; - state.as_values.last_8 = now_8; - - // If the state hasn't changed, exit the loop. - if (state.as_opaque_32 == original) - break; - - // Save the changed state. If the existing value is unchanged from the - // original, exit the loop. - int32_t check = subtle::Release_CompareAndSwap( - &g_last_time_and_rollovers, original, state.as_opaque_32); - if (check == original) - break; - - // Another thread has done something in between so retry from the top. - } - - return TimeTicks() + - TimeDelta::FromMilliseconds( - now + (static_cast<uint64_t>(state.as_values.rollovers) << 32)); -} - // Discussion of tick counter options on Windows: // // (1) CPU cycle counter. (Retrieved via RDTSC) @@ -511,35 +435,12 @@ return TimeTicks() + QPCValueToTimeDelta(QPCNowRaw()); } -bool IsBuggyAthlon(const CPU& cpu) { - // On Athlon X2 CPUs (e.g. model 15) QueryPerformanceCounter is unreliable. - return cpu.vendor_name() == "AuthenticAMD" && cpu.family() == 15; -} - void InitializeNowFunctionPointer() { LARGE_INTEGER ticks_per_sec = {}; if (!QueryPerformanceFrequency(&ticks_per_sec)) ticks_per_sec.QuadPart = 0; - // If Windows cannot provide a QPC implementation, TimeTicks::Now() must use - // the low-resolution clock. - // - // If the QPC implementation is expensive and/or unreliable, TimeTicks::Now() - // will still use the low-resolution clock. A CPU lacking a non-stop time - // counter will cause Windows to provide an alternate QPC implementation that - // works, but is expensive to use. Certain Athlon CPUs are known to make the - // QPC implementation unreliable. - // - // Otherwise, Now uses the high-resolution QPC clock. As of 21 August 2015, - // ~72% of users fall within this category. - TimeTicksNowFunction now_function; - CPU cpu; - if (ticks_per_sec.QuadPart <= 0 || - !cpu.has_non_stop_time_stamp_counter() || IsBuggyAthlon(cpu)) { - now_function = &RolloverProtectedNow; - } else { - now_function = &QPCNow; - } + TimeTicksNowFunction now_function = &QPCNow; // Threading note 1: In an unlikely race condition, it's possible for two or // more threads to enter InitializeNowFunctionPointer() in parallel. This is @@ -569,15 +470,6 @@ } // namespace -// static -TimeTicks::TickFunctionType TimeTicks::SetMockTickFunction( - TickFunctionType ticker) { - TickFunctionType old = g_tick_function; - g_tick_function = ticker; - subtle::NoBarrier_Store(&g_last_time_and_rollovers, 0); - return old; -} - namespace subtle { TimeTicks TimeTicksNowIgnoringOverride() { return g_time_ticks_now_ignoring_override_function(); @@ -646,13 +538,6 @@ } // static -bool ThreadTicks::IsSupportedWin() { - static bool is_supported = - CPU().has_non_stop_time_stamp_counter() && !IsBuggyAthlon(CPU()); - return is_supported; -} - -// static void ThreadTicks::WaitUntilInitializedWin() { while (TSCTicksPerSecond() == 0) ::Sleep(10);
diff --git a/base/timer/mock_timer.cc b/base/timer/mock_timer.cc deleted file mode 100644 index ca0893b..0000000 --- a/base/timer/mock_timer.cc +++ /dev/null
@@ -1,59 +0,0 @@ -// Copyright 2014 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/timer/mock_timer.h" - -namespace base { - -MockTimer::MockTimer(bool retain_user_task, bool is_repeating) - : Timer(retain_user_task, is_repeating), - is_running_(false) { -} - -MockTimer::MockTimer(const Location& posted_from, - TimeDelta delay, - const base::Closure& user_task, - bool is_repeating) - : Timer(true, is_repeating), delay_(delay), is_running_(false) {} - -MockTimer::~MockTimer() = default; - -bool MockTimer::IsRunning() const { - return is_running_; -} - -base::TimeDelta MockTimer::GetCurrentDelay() const { - return delay_; -} - -void MockTimer::Start(const Location& posted_from, - TimeDelta delay, - const base::Closure& user_task) { - delay_ = delay; - user_task_ = user_task; - Reset(); -} - -void MockTimer::Stop() { - is_running_ = false; - if (!retain_user_task()) - user_task_.Reset(); -} - -void MockTimer::Reset() { - DCHECK(!user_task_.is_null()); - is_running_ = true; -} - -void MockTimer::Fire() { - DCHECK(is_running_); - base::Closure old_task = user_task_; - if (is_repeating()) - Reset(); - else - Stop(); - old_task.Run(); -} - -} // namespace base
diff --git a/base/timer/mock_timer.h b/base/timer/mock_timer.h deleted file mode 100644 index 49394b2..0000000 --- a/base/timer/mock_timer.h +++ /dev/null
@@ -1,41 +0,0 @@ -// Copyright 2014 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_TIMER_MOCK_TIMER_H_ -#define BASE_TIMER_MOCK_TIMER_H_ - -#include "base/timer/timer.h" - -namespace base { - -class BASE_EXPORT MockTimer : public Timer { - public: - MockTimer(bool retain_user_task, bool is_repeating); - MockTimer(const Location& posted_from, - TimeDelta delay, - const base::Closure& user_task, - bool is_repeating); - ~MockTimer() override; - - // base::Timer implementation. - bool IsRunning() const override; - base::TimeDelta GetCurrentDelay() const override; - void Start(const Location& posted_from, - base::TimeDelta delay, - const base::Closure& user_task) override; - void Stop() override; - void Reset() override; - - // Testing methods. - void Fire(); - - private: - base::Closure user_task_; - TimeDelta delay_; - bool is_running_; -}; - -} // namespace base - -#endif // BASE_TIMER_MOCK_TIMER_H_
diff --git a/base/win/OWNERS b/base/win/OWNERS deleted file mode 100644 index 4593b2c..0000000 --- a/base/win/OWNERS +++ /dev/null
@@ -1,7 +0,0 @@ -brucedawson@chromium.org -grt@chromium.org -jschuh@chromium.org -robliao@chromium.org -scottmg@chromium.org - -# COMPONENT: Internals>PlatformIntegration
diff --git a/build/gen.py b/build/gen.py index d72f39b..ed92d2f 100755 --- a/build/gen.py +++ b/build/gen.py
@@ -236,7 +236,6 @@ 'base/files/file_util.cc', 'base/files/scoped_file.cc', 'base/files/scoped_temp_dir.cc', - 'base/hash.cc', 'base/json/json_parser.cc', 'base/json/json_reader.cc', 'base/json/json_string_value_serializer.cc', @@ -250,9 +249,7 @@ 'base/process/memory.cc', 'base/process/process_handle.cc', 'base/process/process_iterator.cc', - 'base/rand_util.cc', 'base/sha1.cc', - 'base/strings/pattern.cc', 'base/strings/string_number_conversions.cc', 'base/strings/string_piece.cc', 'base/strings/string_split.cc', @@ -261,13 +258,8 @@ 'base/strings/stringprintf.cc', 'base/strings/utf_string_conversion_utils.cc', 'base/strings/utf_string_conversions.cc', - 'base/synchronization/atomic_flag.cc', 'base/third_party/icu/icu_utf.cc', - 'base/third_party/nspr/prtime.cc', - 'base/threading/thread_collision_warner.cc', 'base/time/clock.cc', - 'base/time/default_tick_clock.cc', - 'base/time/tick_clock.cc', 'base/time/time.cc', 'base/timer/elapsed_timer.cc', 'base/value_iterators.cc', @@ -360,7 +352,6 @@ 'tools/gn/output_file.cc', 'tools/gn/parse_node_value_adapter.cc', 'tools/gn/parser.cc', - 'tools/gn/parser_fuzzer.cc', 'tools/gn/parse_tree.cc', 'tools/gn/path_output.cc', 'tools/gn/pattern.cc', @@ -484,7 +475,6 @@ 'base/process/kill_posix.cc', 'base/process/process_handle_posix.cc', 'base/process/process_posix.cc', - 'base/rand_util_posix.cc', 'base/strings/string16.cc', 'base/synchronization/condition_variable_posix.cc', 'base/synchronization/lock_impl_posix.cc', @@ -499,7 +489,6 @@ 'base/process/process_handle_linux.cc', 'base/process/process_info_linux.cc', 'base/process/process_iterator_linux.cc', - 'base/process/process_linux.cc', 'base/strings/sys_string_conversions_posix.cc', 'base/synchronization/waitable_event_posix.cc', 'base/time/time_exploded_posix.cc', @@ -519,13 +508,10 @@ static_libraries['base']['sources'].extend([ 'base/files/file_util_mac.mm', 'base/mac/bundle_locations.mm', - 'base/mac/call_with_eh_frame.cc', - 'base/mac/call_with_eh_frame_asm.S', 'base/mac/dispatch_source_mach.cc', 'base/mac/foundation_util.mm', 'base/mac/mach_logging.cc', 'base/mac/scoped_mach_port.cc', - 'base/mac/scoped_mach_vm.cc', 'base/mac/scoped_nsautorelease_pool.mm', 'base/process/process_handle_mac.cc', 'base/process/process_info_mac.cc', @@ -546,7 +532,6 @@ if is_win: static_libraries['base']['sources'].extend([ - 'base/cpu.cc', 'base/files/file_enumerator_win.cc', 'base/files/file_util_win.cc', 'base/files/file_win.cc', @@ -556,7 +541,6 @@ 'base/process/process_info_win.cc', 'base/process/process_iterator_win.cc', 'base/process/process_win.cc', - 'base/rand_util_win.cc', 'base/strings/sys_string_conversions_win.cc', 'base/synchronization/condition_variable_win.cc', 'base/synchronization/lock_impl_win.cc',
diff --git a/tools/gn/OWNERS b/tools/gn/OWNERS deleted file mode 100644 index 82224cd..0000000 --- a/tools/gn/OWNERS +++ /dev/null
@@ -1,3 +0,0 @@ -brettw@chromium.org -dpranke@chromium.org -sdefresne@chromium.org
diff --git a/tools/gn/README.md b/tools/gn/README.md deleted file mode 100644 index fd0d9c5..0000000 --- a/tools/gn/README.md +++ /dev/null
@@ -1,18 +0,0 @@ -# What is GN? - -GN is a meta-build system that generates [Ninja](https://ninja-build.org) -build files so that you can build Chromium with Ninja. - -## I want more info on GN! - -Read these links: - - * [Quick start](docs/quick_start.md) - * [FAQ](docs/faq.md) - * [Language and operation details](docs/language.md) - * [Reference](docs/reference.md): The built-in `gn help` documentation. - * [Style guide](docs/style_guide.md) - * [Cross compiling and toolchains](docs/cross_compiles.md) - * [Hacking on GN itself](docs/hacking.md) - * [Standaline GN projects](docs/standalone.md) - * [Pushing new binaries](docs/update_binaries.md)
diff --git a/tools/gn/bin/compare_test_lists.py b/tools/gn/bin/compare_test_lists.py deleted file mode 100644 index 37fb1bf..0000000 --- a/tools/gn/bin/compare_test_lists.py +++ /dev/null
@@ -1,101 +0,0 @@ -# Copyright 2015 The Chromium Authors. All rights reserved. -# Use of this source code is governed by a BSD-style license that can be -# found in the LICENSE file. - -# This script compares the gtest test list for two different builds. -# -# Usage: -# compare_test_lists.py <build_dir_1> <build_dir_2> <binary_name> -# -# For example, from the "src" directory: -# python tools/gn/bin/compare_test_lists.py out/Debug out/gnbuild ipc_tests -# -# This will compile the given binary in both output directories, then extracts -# the test lists and prints missing or extra tests between the first and the -# second build. - -import os -import subprocess -import sys - -def BuildBinary(build_dir, binary_name): - """Builds the given binary in the given directory with Ninja. - - Returns True on success.""" - return subprocess.call(["ninja", "-C", build_dir, binary_name]) == 0 - - -def GetTestList(path_to_binary): - """Returns a set of full test names. - - Each test will be of the form "Case.Test". There will be a separate line - for each combination of Case/Test (there are often multiple tests in each - case). - - Throws an exception on failure.""" - raw_output = subprocess.check_output([path_to_binary, "--gtest_list_tests"]) - input_lines = raw_output.split('\n') - - # The format of the gtest_list_tests output is: - # "Case1." - # " Test1 # <Optional extra stuff>" - # " Test2" - # "Case2." - # " Test1" - case_name = '' # Includes trailing dot. - test_set = set() - for line in input_lines: - if len(line) > 1: - if line[0] == ' ': - # Indented means a test in previous case. - test_set.add(case_name + line[:line.find('#')].strip()) - else: - # New test case. - case_name = line.strip() - - return test_set - - -def PrintSetDiff(a_name, a, b_name, b, binary_name): - """Prints the test list difference between the given sets a and b. - - a_name and b_name will be used to refer to the directories of the two sets, - and the binary name will be shown as the source of the output.""" - - a_not_b = list(a - b) - if len(a_not_b): - print "\n", binary_name, "tests in", a_name, "but not", b_name - a_not_b.sort() - for cur in a_not_b: - print " ", cur - - b_not_a = list(b - a) - if len(b_not_a): - print "\n", binary_name, "tests in", b_name, "but not", a_name - b_not_a.sort() - for cur in b_not_a: - print " ", cur - - if len(a_not_b) == 0 and len(b_not_a) == 0: - print "\nTests match!" - - -def Run(a_dir, b_dir, binary_name): - if not BuildBinary(a_dir, binary_name): - print "Building", binary_name, "in", a_dir, "failed" - return 1 - if not BuildBinary(b_dir, binary_name): - print "Building", binary_name, "in", b_dir, "failed" - return 1 - - a_tests = GetTestList(os.path.join(a_dir, binary_name)) - b_tests = GetTestList(os.path.join(b_dir, binary_name)) - - PrintSetDiff(a_dir, a_tests, b_dir, b_tests, binary_name) - - -if len(sys.argv) != 4: - print "Usage: compare_test_lists.py <build_dir_1> <build_dir_2> " \ - "<test_binary_name>" - sys.exit(1) -sys.exit(Run(sys.argv[1], sys.argv[2], sys.argv[3]))
diff --git a/tools/gn/bin/roll_gn.py b/tools/gn/bin/roll_gn.py deleted file mode 100755 index cf4c878..0000000 --- a/tools/gn/bin/roll_gn.py +++ /dev/null
@@ -1,461 +0,0 @@ -#!/usr/bin/env python -# Copyright 2014 The Chromium Authors. All rights reserved. -# Use of this source code is governed by a BSD-style license that can be -# found in the LICENSE file. - -"""An auto-roller for GN binaries into Chromium. - -This script is used to update the GN binaries that a Chromium -checkout uses. In order to update the binaries, one must follow -four steps in order: - -1. Trigger try jobs to build a new GN binary at tip-of-tree and upload - the newly-built binaries into the right Google CloudStorage bucket. -2. Wait for the try jobs to complete. -3. Update the buildtools repo with the .sha1 hashes of the newly built - binaries. -4. Update Chromium's DEPS file to the new version of the buildtools repo. - -The script has four commands that correspond to the four steps above: -'build', 'wait', 'roll_buildtools', and 'roll_deps'. - -The script has a fifth command, 'roll', that runs the four in order. - -If given no arguments, the script will run the 'roll' command. - -It can only be run on linux in a clean Chromium checkout; it should -error out in most cases if something bad happens, but the error checking -isn't yet foolproof. - -""" - -from __future__ import print_function - -import argparse -import json -import os -import re -import subprocess -import sys -import tempfile -import time -import urllib2 - - -depot_tools_path = os.path.abspath(os.path.normpath(os.path.join( - os.path.dirname(__file__), '..', '..', '..', 'third_party', 'depot_tools'))) -if not depot_tools_path in sys.path: - sys.path.insert(0, depot_tools_path) - - -CHROMIUM_REPO = 'https://chromium.googlesource.com/chromium/src.git' - -COMMITISH_DIGITS = 10 - -UNKNOWN, PENDING, STARTED, SUCCESS = ( - 'unknown', 'pending', 'started', 'success') - -class BuildResult(object): - def __init__(self): - self.masterName = '-' - self.builderName = '-' - self.buildNumber = '-' - self.state = UNKNOWN - self.sha1 = '-' - self.url = '-' - - -class GNRoller(object): - def __init__(self): - self.chromium_src_dir = None - self.buildtools_dir = None - self.old_gn_commitish = None - self.new_gn_commitish = None - self.old_gn_version = None - self.new_gn_version = None - self.reviewer = 'dpranke@chromium.org' - if os.getenv('USER') == 'dpranke': - self.reviewer = 'brettw@chromium.org' - - def Roll(self): - parser = argparse.ArgumentParser() - parser.usage = __doc__ - parser.add_argument('command', nargs='?', default='roll', - help='build|roll|roll_buildtools|roll_deps|wait' - ' (%(default)s is the default)') - - args = parser.parse_args() - command = args.command - ret = self.SetUp() - if not ret and command in ('roll', 'build'): - ret = self.TriggerBuild() - if not ret and command in ('roll', 'wait'): - ret = self.WaitForBuildToFinish() - if not ret and command in ('roll', 'roll_buildtools'): - ret = self.RollBuildtools() - if not ret and command in ('roll', 'roll_deps'): - ret = self.RollDEPS() - - return ret - - def SetUp(self): - if sys.platform not in ('darwin', 'linux2'): - print('roll_gn is only tested and working on Linux and Mac for now.') - return 1 - - ret, out, _ = self.Call('git config --get remote.origin.url') - origin = out.strip() - if ret or origin != CHROMIUM_REPO: - print('Not in a Chromium repo? git config --get remote.origin.url ' - 'returned %d: %s' % (ret, origin)) - return 1 - - ret, _, _ = self.Call('git diff -q') - if ret: - print("Checkout is dirty, exiting") - return 1 - - _, out, _ = self.Call('git rev-parse --show-toplevel', cwd=os.getcwd()) - self.chromium_src_dir = out.strip() - self.buildtools_dir = os.path.join(self.chromium_src_dir, 'buildtools') - - self.new_gn_commitish, self.new_gn_version = self.GetNewVersions() - - _, out, _ = self.Call('gn --version') - self.old_gn_version = out.strip() - - _, out, _ = self.Call('git crrev-parse %s' % self.old_gn_version) - self.old_gn_commitish = out.strip() - return 0 - - def GetNewVersions(self): - _, out, _ = self.Call('git log -1 --grep Cr-Commit-Position') - commit_msg = out.splitlines() - first_line = commit_msg[0] - new_gn_commitish = first_line.split()[1] - - last_line = commit_msg[-1] - new_gn_version = re.sub('.*master@{#(\d+)}', '\\1', last_line) - - return new_gn_commitish, new_gn_version - - def TriggerBuild(self): - ret, _, _ = self.Call('git new-branch build_gn_%s' % self.new_gn_version) - if ret: - print('Failed to create a new branch for build_gn_%s' % - self.new_gn_version) - return 1 - - self.MakeDummyDepsChange() - - ret, out, err = self.Call('git commit -a -m "Build gn at %s"' % - self.new_gn_version) - if ret: - print('git commit failed: %s' % out + err) - return 1 - - print('Uploading CL to build GN at {#%s} - %s' % - (self.new_gn_version, self.new_gn_commitish)) - ret, out, err = self.Call('git cl upload -f') - if ret: - print('git-cl upload failed: %s' % out + err) - return 1 - - print('Starting try jobs') - self.Call('git-cl try -m tryserver.chromium.linux ' - '-b linux_chromium_gn_upload -r %s' % self.new_gn_commitish) - self.Call('git-cl try -m tryserver.chromium.mac ' - '-b mac_chromium_gn_upload -r %s' % self.new_gn_commitish) - self.Call('git-cl try -m tryserver.chromium.win ' - '-b win_chromium_gn_upload -r %s' % self.new_gn_commitish) - - return 0 - - def MakeDummyDepsChange(self): - with open('DEPS') as fp: - deps_content = fp.read() - new_deps = deps_content.replace("'buildtools_revision':", - "'buildtools_revision': ") - - with open('DEPS', 'w') as fp: - fp.write(new_deps) - - def WaitForBuildToFinish(self): - ret = self.CheckoutBuildBranch() - if ret: - return ret - - print('Checking build') - results = self.CheckBuild() - while (any(r.state in (PENDING, STARTED) for r in results.values())): - print() - print('Sleeping for 30 seconds') - time.sleep(30) - print('Checking build') - results = self.CheckBuild() - - ret = 0 if all(r.state == SUCCESS for r in results.values()) else 1 - if ret: - print('Build failed.') - else: - print('Builds ready.') - - # Close the build CL and move off of the build branch back to whatever - # we were on before. - self.Call('git-cl set-close') - self.MoveToLastHead() - - return ret - - def CheckoutBuildBranch(self): - ret, out, err = self.Call('git checkout build_gn_%s' % self.new_gn_version) - if ret: - print('Failed to check out build_gn_%s' % self.new_gn_version) - if out: - print(out) - if err: - print(err, file=sys.stderr) - return ret - - def CheckBuild(self): - _, out, _ = self.Call('git-cl try-results') - - builders = { - 'linux_chromium_gn_upload': 'linux64', - 'mac_chromium_gn_upload': 'mac', - 'win_chromium_gn_upload': 'win' - } - - results = {} - for platform in ('linux64', 'mac', 'win'): - results[platform] = BuildResult() - - state = PENDING - for line in out.splitlines(): - fields = line.strip().split() - if fields[0] == 'Started:': - state = STARTED - if fields[0] == 'Successes:': - state = SUCCESS - elif fields[0] == 'Total': - pass - elif fields[0] in builders: - builder = fields[0] - platform = builders[builder] - result = results[platform] - result.masterName = ('tryserver.chromium.%s' % - platform.replace('linux64', 'linux')) - result.builderName = builder - result.url = fields[1] - if result.url.startswith('id'): - result.state = PENDING - else: - result.state = state - result.buildNumber = int(result.url[result.url.rfind('/')+1:]) - - for result in results.values(): - if result.state == SUCCESS: - url = 'https://luci-milo.appspot.com/prpc/milo.BuildInfo/Get' - data = json.dumps({"buildbot": { - 'masterName': result.masterName, - 'builderName': result.builderName, - 'buildNumber': result.buildNumber, - }}) - headers = { - 'content-type': 'application/json', - 'accept': 'application/json', - } - - req = urllib2.Request(url, data, headers) - resp = urllib2.urlopen(req) - data = resp.read() - resp.close() - - # The first line of the response is garbage; skip it. - js = json.loads(data.splitlines()[1]) - - sha1_step_name = 'gn sha1' - for step in js['step']['substep']: - if step['step']['name'] == sha1_step_name: - sha1 = step['step']['text'][-1] - - result.sha1 = sha1 - - for platform, r in results.items(): - print(platform) - print(' sha1: %s' % r.sha1) - print(' state: %s' % r.state) - print(' build: %s' % r.buildNumber) - print(' url: %s' % r.url) - print() - - return results - - def RollBuildtools(self): - ret = self.CheckoutBuildBranch() - if ret: - return ret - - results = self.CheckBuild() - if (len(results) < 3 or - not all(r.state == SUCCESS for r in results.values()) or - not all(r.sha1 != '-' for r in results.values())): - print("Roll isn't done or didn't succeed, exiting:") - return 1 - - desc = self.GetBuildtoolsDesc() - - self.Call('git new-branch roll_buildtools_gn_%s' % self.new_gn_version, - cwd=self.buildtools_dir) - - for platform in results: - fname = 'gn.exe.sha1' if platform == 'win' else 'gn.sha1' - path = os.path.join(self.buildtools_dir, platform, fname) - with open(path, 'w') as fp: - fp.write('%s\n' % results[platform].sha1) - - desc_file = tempfile.NamedTemporaryFile(delete=False) - try: - desc_file.write(desc) - desc_file.close() - self.Call('git commit -a -F %s' % desc_file.name, - cwd=self.buildtools_dir) - self.Call('git-cl upload -f --send-mail', - cwd=self.buildtools_dir) - finally: - os.remove(desc_file.name) - - ret, out, err = self.Call('git cl land', cwd=self.buildtools_dir) - if ret: - print("buildtools git cl land failed: %d" % ret) - if out: - print(out) - if err: - print(err) - return ret - - # Fetch the revision we just committed so that RollDEPS will find it. - self.Call('git fetch', cwd=self.buildtools_dir) - - # Reset buildtools to the new commit so that we're not still on the - # merged branch. - self.Call('git checkout origin/master', cwd=self.buildtools_dir) - - _, out, _ = self.Call('git rev-parse origin/master', - cwd=self.buildtools_dir) - new_buildtools_commitish = out.strip() - print('Ready to roll buildtools to %s in DEPS' % new_buildtools_commitish) - - return 0 - - def RollDEPS(self): - ret, _, _ = self.Call('git new-branch roll_gn_%s' % self.new_gn_version) - if ret: - print('Failed to create a new branch for roll_gn_%s' % - self.new_gn_version) - return 1 - - _, out, _ = self.Call('git rev-parse origin/master', - cwd=self.buildtools_dir) - new_buildtools_commitish = out.strip() - - new_deps_lines = [] - old_buildtools_commitish = '' - with open(os.path.join(self.chromium_src_dir, 'DEPS')) as fp: - for l in fp.readlines(): - m = re.match(".*'buildtools_revision':.*'(.+)',", l) - if m: - old_buildtools_commitish = m.group(1) - new_deps_lines.append(" 'buildtools_revision': '%s',\n" % - new_buildtools_commitish) - else: - new_deps_lines.append(l) - - if not old_buildtools_commitish: - print('Could not update DEPS properly, exiting') - return 1 - - with open('DEPS', 'w') as fp: - fp.write(''.join(new_deps_lines)) - - desc = self.GetDEPSRollDesc(old_buildtools_commitish, - new_buildtools_commitish) - desc_file = tempfile.NamedTemporaryFile(delete=False) - try: - desc_file.write(desc) - desc_file.close() - self.Call('git commit -a -F %s' % desc_file.name) - self.Call('git-cl upload -f --send-mail --use-commit-queue') - finally: - os.remove(desc_file.name) - - # Move off of the roll branch onto whatever we were on before. - # Do not explicitly close the roll CL issue, however; the CQ - # will close it when the roll lands, assuming it does so. - self.MoveToLastHead() - - return 0 - - def MoveToLastHead(self): - # When this is called, there will be a commit + a checkout as - # the two most recent entries in the reflog, assuming nothing as - # modified the repo while this script has been running. - _, out, _ = self.Call('git reflog -2') - m = re.search('moving from ([^\s]+)', out) - last_head = m.group(1) - self.Call('git checkout %s' % last_head) - - def GetBuildtoolsDesc(self): - gn_changes = self.GetGNChanges() - return ( - 'Roll gn %s..%s (r%s:r%s)\n' - '\n' - '%s' - '\n' - 'TBR=%s\n' % ( - self.old_gn_commitish[:COMMITISH_DIGITS], - self.new_gn_commitish[:COMMITISH_DIGITS], - self.old_gn_version, - self.new_gn_version, - gn_changes, - self.reviewer, - )) - - def GetDEPSRollDesc(self, old_buildtools_commitish, new_buildtools_commitish): - gn_changes = self.GetGNChanges() - - return ( - 'Roll buildtools %s..%s\n' - '\n' - ' In order to roll GN %s..%s (r%s:r%s) and pick up\n' - ' the following changes:\n' - '\n' - '%s' - '\n' - 'TBR=%s\n' % ( - old_buildtools_commitish[:COMMITISH_DIGITS], - new_buildtools_commitish[:COMMITISH_DIGITS], - self.old_gn_commitish[:COMMITISH_DIGITS], - self.new_gn_commitish[:COMMITISH_DIGITS], - self.old_gn_version, - self.new_gn_version, - gn_changes, - self.reviewer, - )) - - def GetGNChanges(self): - _, out, _ = self.Call( - "git log --pretty=' %h %s' " + - "%s..%s tools/gn" % (self.old_gn_commitish, self.new_gn_commitish)) - return out - - def Call(self, cmd, cwd=None): - proc = subprocess.Popen(cmd, stdout=subprocess.PIPE, shell=True, - cwd=(cwd or self.chromium_src_dir)) - out, err = proc.communicate() - return proc.returncode, out or '', err or '' - - -if __name__ == '__main__': - roller = GNRoller() - sys.exit(roller.Roll())
diff --git a/tools/gn/bootstrap/OWNERS b/tools/gn/bootstrap/OWNERS deleted file mode 100644 index 21aeec2..0000000 --- a/tools/gn/bootstrap/OWNERS +++ /dev/null
@@ -1,4 +0,0 @@ -# It's OK to TBR changes to bootstrap.py that edits the file lists to bring -# them in line with the Chrome build. For more substantial changes, please -# send a normal review. -*
diff --git a/tools/gn/misc/OWNERS b/tools/gn/misc/OWNERS deleted file mode 100644 index 4d2bd88..0000000 --- a/tools/gn/misc/OWNERS +++ /dev/null
@@ -1,2 +0,0 @@ -scottmg@chromium.org -erg@chromium.org
diff --git a/tools/gn/bin/help_as_html.py b/tools/gn/misc/help_as_html.py similarity index 100% rename from tools/gn/bin/help_as_html.py rename to tools/gn/misc/help_as_html.py
diff --git a/tools/gn/bin/gn-format.py b/tools/gn/misc/vim/gn-format.py similarity index 100% rename from tools/gn/bin/gn-format.py rename to tools/gn/misc/vim/gn-format.py
diff --git a/tools/gn/parser_fuzzer.cc b/tools/gn/parser_fuzzer.cc deleted file mode 100644 index e40da78..0000000 --- a/tools/gn/parser_fuzzer.cc +++ /dev/null
@@ -1,71 +0,0 @@ -// Copyright 2016 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include <stdint.h> - -#include "tools/gn/input_file.h" -#include "tools/gn/parser.h" -#include "tools/gn/source_file.h" -#include "tools/gn/tokenizer.h" - -namespace { - -enum { kMaxContentDepth = 256, kMaxDodgy = 256 }; - -// Some auto generated input is too unreasonable for fuzzing GN. -// We see stack overflow when the parser hits really deeply "nested" input. -// (I.E.: certain input that causes nested parsing function calls). -// -// Abstract max limits are undesirable in the release GN code, so some sanity -// checks in the fuzzer to prevent stack overflow are done here. -// - 1) Too many opening bracket, paren, or brace in a row. -// - 2) Too many '!', '<' or '>' operators in a row. -bool SanityCheckContent(const std::vector<Token>& tokens) { - int depth = 0; - int dodgy_count = 0; - for (const auto& token : tokens) { - switch (token.type()) { - case Token::LEFT_PAREN: - case Token::LEFT_BRACKET: - case Token::LEFT_BRACE: - ++depth; - break; - case Token::RIGHT_PAREN: - case Token::RIGHT_BRACKET: - case Token::RIGHT_BRACE: - --depth; - break; - case Token::BANG: - case Token::LESS_THAN: - case Token::GREATER_THAN: - ++dodgy_count; - break; - default: - break; - } - // Bail out as soon as a boundary is hit, inside the loop. - if (depth >= kMaxContentDepth || dodgy_count >= kMaxDodgy) - return false; - } - - return true; -} - -} // namespace - -extern "C" int LLVMFuzzerTestOneInput(const unsigned char* data, size_t size) { - SourceFile source; - InputFile input(source); - input.SetContents(std::string(reinterpret_cast<const char*>(data), size)); - - Err err; - std::vector<Token> tokens = Tokenizer::Tokenize(&input, &err); - if (!SanityCheckContent(tokens)) - return 0; - - if (!err.has_error()) - Parser::Parse(tokens, &err); - - return 0; -}
diff --git a/tools/gn/tutorial/hello.cc b/tools/gn/tutorial/hello.cc deleted file mode 100644 index 8b25cd9..0000000 --- a/tools/gn/tutorial/hello.cc +++ /dev/null
@@ -1,17 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "tools/gn/tutorial/hello.h" - -#include <stdio.h> - -void Hello(const char* who) { - printf("Hello, %s.\n", who); -} - -#if defined(TWO_PEOPLE) -void Hello(const char* one, const char* two) { - printf("Hello, %s and %s.\n", one, two); -} -#endif
diff --git a/tools/gn/tutorial/hello.h b/tools/gn/tutorial/hello.h deleted file mode 100644 index 253fe24..0000000 --- a/tools/gn/tutorial/hello.h +++ /dev/null
@@ -1,14 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef TOOLS_GN_TUTORIAL_HELLO_H_ -#define TOOLS_GN_TUTORIAL_HELLO_H_ - -void Hello(const char* who); - -#if defined(TWO_PEOPLE) -void Hello(const char* one, const char* two); -#endif - -#endif // TOOLS_GN_TUTORIAL_HELLO_H_
diff --git a/tools/gn/tutorial/hello_world.cc b/tools/gn/tutorial/hello_world.cc deleted file mode 100644 index 84ffc3f..0000000 --- a/tools/gn/tutorial/hello_world.cc +++ /dev/null
@@ -1,10 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include <stdio.h> - -int main() { - printf("Hello, world.\n"); - return 0; -}
diff --git a/tools/gn/tutorial/say_hello.cc b/tools/gn/tutorial/say_hello.cc deleted file mode 100644 index d8092bd..0000000 --- a/tools/gn/tutorial/say_hello.cc +++ /dev/null
@@ -1,14 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "tools/gn/tutorial/hello.h" - -int main() { -#if defined(TWO_PEOPLE) - Hello("Bill", "Joy"); -#else - Hello("everyone"); -#endif - return 0; -}