54 Commits

Author SHA1 Message Date
Sam McCall
fe8a168161 [unittest] teach gTest to print entries of DenseMap as pairs
When an assertion like the following fails:
   EXPECT_THAT(map, ElementsAre(Pair("p", "nullable"))));
Error message before:
   Actual: { 40-byte object <E8-A5 9C-7F 25-37 00-00 58-7E 51-51 D0-7F 00-00 00-00 00-00 00-00 00-00 01-00 00-00 00-00 00-00 00-DA C7-7F 25-37 00-00> }
After:
   Actual: { ("p", "nonnull") }

It is not ideal that we need to refer directly to DenseMapPair inside the
internal namespace, but I believe the practical maintenance risk is low.
This change is covered by DenseMap's unittests, as we've covered SmallString etc
in the past.

Differential Revision: https://reviews.llvm.org/D153930
2023-06-28 11:29:52 +02:00
Elliot Goodrich
cea0eea28e [llvm] Split out DenseMapInfo<variant> specialization
Remove the `DenseMapInfo<std::variant<Ts...>>` variant out from
`llvm/ADT/DenseMapInfo.h` into a separate header
`llvm/ADT/DenseMapInfoVariant.h`

This allows us to remove the `<variant>` include, which is being
transitively and unncessary included in all translation units that
include `llvm/ADT/DenseMap.h`.

There have been similar changes to move out specializations for

    * `APInt.h` fd7e309e02fd226b0390888388ed732608e52c73 and
    * `StringRef.h`/`ArrayRef.h`
      983565a6fe4a9f40c7caf82b65c650c20dbcc104

to reduce the compilation time. As we are unable to move the
specialization into `<variant>`, we create a separate
`DenseMapInfoVariant.h` header that can be used by anyone who needs this
specialization.

This reduces the total number of preprocessing tokens across the LLVM
source files in lib from (roughly) 1,964,876,961 to 1,936,551,496 - a
reduction of ~1.44%. This should result in a small improvement in
compilation time.

Differential Revision: https://reviews.llvm.org/D150997
2023-06-22 06:50:54 +01:00
Sam McCall
9e932e08a8 [ADT] Fix DenseMapInfo<variant>::isEqual to delegate to DenseMapInfo, not ==
Differential Revision: https://reviews.llvm.org/D151557
2023-06-06 18:36:37 +02:00
Kazu Hirata
21700677cb [ADT] Implement {DenseMap,MapVector,StringMap}::contains
This patch implements the C++20-style contains() for DenseMap,
MapVector, and StringMap.

With this patch, every set and map container type that has count()
also has contains().

Differential Revision: https://reviews.llvm.org/D145895
2023-03-13 09:13:28 -07:00
Ryan Guo
be83a4b257 [ADT] Fix tests for StringMap::at and DenseMap::at
These methods won't assert for release build.
2023-02-17 10:07:01 -08:00
Ryan Guo
132003603a [ADT] Add at method (assertive lookup) to DenseMap and StringMap
This patch makes it easier for users when they want to use validated
lookup on DenseMap/StringMap as a composable C++ expression. For
instance:

```
// instead of
if (auto val = map.lookup(key))
   return val;
assert("...");

// we can write
return map.at(key);
```

Differential Revision: https://reviews.llvm.org/D143976
2023-02-17 08:32:29 -08:00
Gregory Alfonso
7f86bb0a71 [llvm] Call reserve before push_back in a loop
It is generally good practice, if you know how big the vector is going to be in the end, to reserve before continually calling "push_back" or "emplace_back"

Reviewed By: MaskRay

Differential Revision: https://reviews.llvm.org/D139483
2022-12-08 08:42:50 +00:00
Nathan James
6aa050a690 Reland "[llvm][NFC] Use c++17 style variable type traits"
This reverts commit 632a389f96355cbe7ed8fa7b8d2ed6267c92457c.

This relands commit
1834a310d060d55748ca38d4ae0482864c2047d8.

Differential Revision: https://reviews.llvm.org/D137493
2022-11-08 14:15:15 +00:00
Nathan James
632a389f96 Revert "[llvm][NFC] Use c++17 style variable type traits"
This reverts commit 1834a310d060d55748ca38d4ae0482864c2047d8.
2022-11-08 13:11:41 +00:00
Nathan James
1834a310d0
[llvm][NFC] Use c++17 style variable type traits
This was done as a test for D137302 and it makes sense to push these changes

Reviewed By: dblaikie

Differential Revision: https://reviews.llvm.org/D137493
2022-11-08 12:22:52 +00:00
Kadir Cetinkaya
4940f205d4
[llvm][Support] Add DenseMapInfo for std::variant
Differential Revision: https://reviews.llvm.org/D133200
2022-09-02 15:36:10 +02:00
Vladislav Dzhidzhoev
2c84b92346 Fix assertion in SmallDenseMap constructor with reserve from non-power-of-2 buckets count
`SmallDenseMap` constructor with reserve gets an arbitrary `NumInitBuckets` value and passes it below to `init` method.

If `NumInitBuckets` is greater then `InlineBuckets`, then `SmallDenseMap` initializes to large representation passing `NumInitBuckets` below to `DenseMap` initialization. `DenseMap::initEmpty` method asserts that initial buckets count must be a power of 2.

Proposed solution is to update `NumInitBuckets` value in `SmallDenseMap` constructor till the next power of 2. It should satisfy both `DenseMap` preconditions and required minimum buckets count for reservation.

Reviewed By: atrick

Differential Revision: https://reviews.llvm.org/D129825
2022-07-25 17:09:44 +00:00
River Riddle
4c484f11d3 [llvm] Add a SFINAE template parameter to DenseMapInfo
This allows for using SFINAE partial specialization for DenseMapInfo.
In MLIR, this is particularly useful as it will allow for defining partial
specializations that support all Attribute, Op, and Type classes without
needing to specialize DenseMapInfo for each individual class.

Differential Revision: https://reviews.llvm.org/D113641
2021-11-16 18:54:14 +00:00
Jakub Kuderski
3c3165cfa0 [ADT] Add initializer_list constructor to SmallDenseMap
Make it easier to initialize small maps inline. Note that DenseMap already has an initializer_list constructor.

Reviewed By: dblaikie

Differential Revision: https://reviews.llvm.org/D106363
2021-07-21 09:32:16 -04:00
Benjamin Kramer
05de4b4139 Put back the trailing commas on TYPED_TEST_SUITE
This avoids a -pedantic warning:
warning: ISO C++11 requires at least one argument for the "..." in a variadic macro

See also https://github.com/google/googletest/issues/2271
2021-05-17 14:14:13 +02:00
Benjamin Kramer
d4d80a2903 Bump googletest to 1.10.0 2021-05-14 19:16:31 +02:00
Reid Kleckner
53f51da09e [ADT] Allow K to be incomplete during DenseMap<K*, V> instantiation
DenseMap requires two sentinel values for keys: empty and tombstone
values. To avoid undefined behavior, LLVM aligns the two sentinel
pointers to alignof(T). This requires T to be complete, which is
needlessly restrictive.

Instead, assume that DenseMap pointer keys have a maximum alignment of
4096, and use the same sentinel values for all pointer keys. The new
sentinels are:
  empty:     static_cast<uintptr_t>(-1) << 12
  tombstone: static_cast<uintptr_t>(-2) << 12

These correspond to the addresses of -4096 and -8192. Hopefully, such a
key is never inserted into a DenseMap.

I encountered this while looking at making clang's SourceManager not
require FileManager.h, but it has several maps keyed on classes defined
in FileManager.h. FileManager depends on various LLVM FS headers, which
cumulatively take ~200ms to parse, and are generally not needed.

Reviewed By: hans

Differential Revision: https://reviews.llvm.org/D75301
2020-02-28 14:24:04 -08:00
Nikita Popov
fe593fe15f [ADT] Fix SmallDenseMap assertion with large InlineBuckets
Fixes issue encountered in D56362, where I tried to use a
SmallSetVector<Instruction*, 128> with an excessively large number
of inline elements. This triggers an "Must allocate more buckets
than are inline" assertion inside allocateBuckets() under certain
usage patterns.

The issue is as follows: The grow() method is used either to grow
the map, or to rehash it and remove tombstones. The latter is done
if the fraction of empty (non-used, non-tombstone) elements is
below 1/8. In this case grow() is invoked with the current number
of buckets.

This is currently incorrectly handled for dense maps using the small
rep. The current implementation will switch them over to the large
rep, which violates the invariant that the large rep is only used
if there are more than InlineBuckets buckets.

This patch fixes the issue by staying in the small rep and only
moving the buckets. An alternative, if we do want to switch to the
large rep in this case, would be to relax the assertion in
allocateBuckets().

Differential Revision: https://reviews.llvm.org/D56455
2019-12-11 21:41:14 +01:00
Simon Pilgrim
d050e45631 [ADT] Remove MSVC-only "no two-phase name lookup" typename path.
Now that we've dropped VS2015 support (D64326) we can use the regular codepath as VS2017+ correctly handles it

llvm-svn: 365502
2019-07-09 15:24:19 +00:00
Chandler Carruth
2946cd7010 Update the file headers across all of the LLVM projects in the monorepo
to reflect the new license.

We understand that people may be surprised that we're moving the header
entirely to discuss the new license. We checked this carefully with the
Foundation's lawyer and we believe this is the correct approach.

Essentially, all code in the project is now made available by the LLVM
project under our new license, so you will see that the license headers
include that license only. Some of our contributors have contributed
code under our old license, and accordingly, we have retained a copy of
our old license notice in the top-level files in each project and
repository.

llvm-svn: 351636
2019-01-19 08:50:56 +00:00
Lang Hames
cb1f0cf54b [ADT] Adds equality operators for DenseMap and DenseSet, and an initializer_list
constructor for DenseMap (DenseSet already had an initializer_list constructor).

These changes make it easier to migrate existing code that uses std::map and
std::set (which support initializer_list construction and equality comparison)
to DenseMap and DenseSet.

llvm-svn: 344522
2018-10-15 15:26:47 +00:00
Adrian Prantl
5f8f34e459 Remove \brief commands from doxygen comments.
We've been running doxygen with the autobrief option for a couple of
years now. This makes the \brief markers into our comments
redundant. Since they are a visual distraction and we don't want to
encourage more \brief markers in new code either, this patch removes
them all.

Patch produced by

  for i in $(git grep -l '\\brief'); do perl -pi -e 's/\\brief //g' $i & done

Differential Revision: https://reviews.llvm.org/D46290

llvm-svn: 331272
2018-05-01 15:54:18 +00:00
Roman Lebedev
429b00325f [unittests] ADT: silence -Wself-assign diagnostics
Summary:
D44883 extends -Wself-assign to also work on C++ classes.
In it's current state (as suggested by @rjmccall), it is not under it's own sub-group.
Since that diag is enabled by `-Wall`, stage2 testing showed that:
* It does not fire on any llvm code
* It does fire for these 3 unittests
* It does fire for libc++ tests

This diff simply silences those new warnings in llvm's unittests.
A similar diff will be needed for libcxx. (`libcxx/test/std/language.support/support.types/byteops/`, maybe something else)

Since i don't think we want to repeat rL322901, let's talk about it.
I've subscribed everyone who i think might be interested...

There are several ways forward:
* Not extend -Wself-assign, close D44883. Not very productive outcome i'd say.
* Keep D44883 in it's current state.
  Unless your custom overloaded operators do something unusual for when self-assigning,
  the warning is no less of a false-positive than the current -Wself-assign.
  Except for tests of course, there you'd want to silence it. The current suggestion is:
  ```
  S a;
  a = (S &)a;
  ```
* Split the diagnostic in two - `-Wself-assign-builtin` (i.e. what is `-Wself-assign` in trunk),
  and `-Wself-assign-overloaded` - the new part in D44883.
  Since, as i said, i'm not really sure why it would be less of a error than the current `-Wself-assign`,
  both would still be in `-Wall`. That way one could simply pass `-Wno-self-assign-overloaded` for all the tests.
  Pretty simple to do, and will surely work.
* Split the diagnostic in two - `-Wself-assign-trivial`, and `-Wself-assign-nontrivial`.
  The choice of which diag to emit would depend on trivial-ness of that particular operator.
  The current `-Wself-assign` would be `-Wself-assign-trivial`.
  https://godbolt.org/g/gwDASe - `A`, `B` and `C` case would be treated as trivial, and `D`, `E` and `F` as non-trivial.
  Will be the most complicated to implement.

Thoughts?

Reviewers: aaron.ballman, rsmith, rtrieu, rjmccall, dblaikie, atrick, gottesmm

Reviewed By: dblaikie

Subscribers: lebedev.ri, phosek, vsk, rnk, thakis, sammccall, mclow.lists, llvm-commits, rjmccall

Differential Revision: https://reviews.llvm.org/D45082

llvm-svn: 329491
2018-04-07 10:37:18 +00:00
Malcolm Parsons
21e545d08d Fix typos of occurred and occurrence
llvm-svn: 323318
2018-01-24 10:33:39 +00:00
Chandler Carruth
9a67b07398 Re-sort #include lines for unittests. This uses a slightly modified
clang-format (https://reviews.llvm.org/D33932) to keep primary headers
at the top and handle new utility headers like 'gmock' consistently with
other utility headers.

No other change was made. I did no manual edits, all of this is
clang-format.

This should allow other changes to have more clear and focused diffs,
and is especially motivated by moving some headers into more focused
libraries.

llvm-svn: 304786
2017-06-06 11:06:56 +00:00
Daniel Berlin
04d9e746f1 Add support for DenseMap/DenseSet count and find using const pointers
Summary:
Similar to SmallPtrSet, this makes find and count work with both const
referneces and const pointers.

Reviewers: dblaikie

Subscribers: llvm-commits, mzolotukhin

Differential Revision: https://reviews.llvm.org/D30713

llvm-svn: 297424
2017-03-10 00:25:26 +00:00
Justin Lebar
688c8347c9 [ADT] Remove CachedHash<T>.
Nobody is using it.

Differential Revision: https://reviews.llvm.org/D25630

llvm-svn: 284503
2016-10-18 17:50:39 +00:00
Benjamin Kramer
857754a1cb [DenseMap] Add a C++17-style try_emplace method.
This provides an elegant pattern to solve the "construct if not in map
already" problem we have many times in LLVM. Without try_emplace we
either have to rely on a sentinel value (nullptr) or do two lookups.

llvm-svn: 276277
2016-07-21 13:37:53 +00:00
Rafael Espindola
e9f0784acc Add a CachedHash structure.
A DenseMap doesn't store the hashes, so it needs to recompute them when
the table is resized.

In some applications the hashing cost is noticeable. That is the case
for example in lld for symbol names (StringRef).

This patch adds a templated structure that can wraps any value that can
go in a DenseMap and caches the hash.

llvm-svn: 266981
2016-04-21 12:16:21 +00:00
Mehdi Amini
412989750d StringMap/DenseMap unittests: use piecewise_construct and ensure no copy occurs.
This makes us no longer relying on move-construction elision by the compiler.
Suggested by D. Blaikie.

From: Mehdi Amini <mehdi.amini@apple.com>
llvm-svn: 264475
2016-03-25 23:25:06 +00:00
Mehdi Amini
9706dcf93b Disable counting the number of move in the unittest, it seems to rely on move-construction elision
From: Mehdi Amini <mehdi.amini@apple.com>
llvm-svn: 264412
2016-03-25 15:46:14 +00:00
Mehdi Amini
05eca80cb8 Fix DenseMap::reserve(): the formula was wrong
Summary:
Just running the loop in the unittests for a few more iterations
(till 48) exhibit that the condition on the limit was not handled
properly in r263522.
Rewrite the test to use a class to count move/copies that happens
when inserting into the map.
Also take the opportunity to refactor the logic to compute the
number of buckets required for a given number of entries in the map.
Use this when constructing a DenseMap with a desired size given to
the constructor (and add a tests for this).

Reviewers: dblaikie

Subscribers: llvm-commits

Differential Revision: http://reviews.llvm.org/D18345

From: Mehdi Amini <mehdi.amini@apple.com>
llvm-svn: 264384
2016-03-25 05:57:52 +00:00
Mehdi Amini
844baa240a Fix unittests: resize() -> reserve()
From: Mehdi Amini <mehdi.amini@apple.com>
llvm-svn: 264029
2016-03-22 07:35:51 +00:00
Fiona Glaser
a4b1ace461 DenseMap: make .resize() do the intuitive thing
In some places, like InstCombine, we resize a DenseMap to fit the elements
we intend to put in it, then insert those elements (to avoid continual
reallocations as it grows). But .resize(foo) doesn't actually do what
people think; it resizes to foo buckets (which is really an
implementation detail the user of DenseMap probably shouldn't care about),
not the space required to fit foo elements. DenseMap grows if 3/4 of its
buckets are full, so this actually causes one forced reallocation every
time instead of avoiding a reallocation.

This patch makes .resize(foo) do the intuitive thing: it grows to the size
necessary to fit foo elements without new allocations.

Also include a test to verify that .resize() actually does what we think it
does.

llvm-svn: 263522
2016-03-15 01:50:46 +00:00
Michael Gottesman
ef711c1831 Add a unittest for SmallDenseMap that tests assigning a SmallDenseMap when it is not small.
This complements CopyConstructorNotSmallTest. If we are testing the copy
constructor in such a way, we should also probably test assignment in the same
way.

llvm-svn: 251736
2015-10-31 05:23:53 +00:00
Chandler Carruth
5953482285 [ADT] Teach DenseMap to support StringRef keys.
While often you want to use something specialized like StringMap, when
the strings already have persistent storage a normal densemap over them
can be more efficient.

This can't go into StringRef.h because of really obnoxious header chains
from the hashing code to the endian detection code to CPU feature
detection code to StringMap.

llvm-svn: 240528
2015-06-24 10:06:29 +00:00
David Blaikie
54a7ca3fcb Explicitly default DenseMapTest::CtorTest::operator=
Using the implicit default copy assignment operator in the presence of a
user-declared copy ctor is deprecated in C++11.

llvm-svn: 231225
2015-03-04 07:57:45 +00:00
David Blaikie
7f1e0565b3 Revert "Remove the explicit SDNodeIterator::operator= in favor of the implicit default"
Accidentally committed a few more of these cleanup changes than
intended. Still breaking these out & tidying them up.

This reverts commit r231135.

llvm-svn: 231136
2015-03-03 21:18:16 +00:00
David Blaikie
bb8da4c08f Remove the explicit SDNodeIterator::operator= in favor of the implicit default
There doesn't seem to be any need to assert that iterator assignment is
between iterators over the same node - if you want to reuse an iterator
variable to iterate another node, that's perfectly acceptable. Just
don't mix comparisons between iterators into disjoint sequences, as
usual.

llvm-svn: 231135
2015-03-03 21:17:08 +00:00
Andrew Trick
fd4f32be90 Fix SmallDenseMap assignment operator.
Self assignment would lead to buckets of garbage, causing quadratic probing to hang.

llvm-svn: 214790
2014-08-04 22:18:25 +00:00
David Blaikie
7c8d13911a Fix some -Wsign-compare fallout from changing container count member functions to return unsigned instead of bool.
llvm-svn: 211393
2014-06-20 19:54:13 +00:00
Craig Topper
66f09ad041 [C++11] Use 'nullptr'.
llvm-svn: 210442
2014-06-08 22:29:17 +00:00
Duncan P. N. Exon Smith
0d64f8b0ca fix crash in SmallDenseMap copy constructor
Prevent a crash in the SmallDenseMap copy constructor whenever the other
map is not in small mode.

<rdar://problem/14292693>

llvm-svn: 202206
2014-02-25 23:35:13 +00:00
Reid Kleckner
0f679177e1 Tweak an _MSC_VER ifdef to use typename with clang in a unittest
In theory, Clang should figure out how to parse this correctly without
typename, but since this is the last TU that Clang falls back on in the
self-host, I'm going to compromise and check for __clang__.

And now Clang can self-host on -win32 without fallback!  The 'check' and
'check-clang' targets both pass.

llvm-svn: 201358
2014-02-13 19:51:13 +00:00
Pete Cooper
8ba353da39 Fixed bug in SmallDenseMap where it wouldn't leave enough space for an empty bucket if the number of values was exactly equal to the small capacity. This led to an infinite loop when finding a non-existent element
llvm-svn: 166492
2012-10-23 18:47:35 +00:00
Chandler Carruth
4de807a552 Add a unit test for 'swap', and fix a pile of bugs in
SmallDenseMap::swap.

First, make it parse cleanly. Yay for uninstantiated methods.

Second, make the inline-buckets case work correctly. This is way
trickier than it should be due to the uninitialized values in empty and
tombstone buckets.

Finally fix a few typos that caused construction/destruction mismatches
in the counting unittest.

llvm-svn: 158641
2012-06-17 11:28:13 +00:00
Chandler Carruth
a1be842f98 Add tests for *DenesMap for both key and value types' construction and
destruction and fix a bug in SmallDenseMap they caught.

This is kind of a poor-man's version of the testing that just adds the
addresses to a set on construction and removes them on destruction. We
check that double construction and double destruction don't occur.
Amusingly enough, this is enough to catch a lot of SmallDenseMap issues
because we spend a lot of time with fixed stable addresses in the inline
buffer.

The SmallDenseMap bug fix included makes grow() not double-destroy in
some cases. It also fixes a FIXME there, the code was pretty crappy. We
now don't have any wasted initialization, but we do move the entries in
inline bucket array an extra time. It's probably a better tradeoff, and
is much easier to get correct.

llvm-svn: 158639
2012-06-17 10:33:51 +00:00
Chandler Carruth
20dd838ae5 Introduce a SmallDenseMap container that re-uses the existing DenseMap
implementation.

This type includes an inline bucket array which is used initially. Once
it is exceeded, an array of 64 buckets is allocated on the heap. The
bucket count grows from there as needed. Some highlights of this
implementation:

- The inline buffer is very carefully aligned, and so supports types
  with alignment constraints.
- It works hard to avoid aliasing issues.
- Supports types with non-trivial constructors, destructors, copy
  constructions, etc. It works reasonably hard to minimize copies and
  unnecessary initialization. The most common initialization is to set
  keys to the empty key, and so that should be fast if at all possible.

This class has a performance / space trade-off. It tries to optimize for
relatively small maps, and so packs the inline bucket array densely into
the object. It will be marginally slower than a normal DenseMap in a few
use patterns, so it isn't appropriate everywhere.

The unit tests for DenseMap have been generalized a bit to support
running over different map implementations in addition to different
key/value types. They've then been automatically extended to cover the
new container through the magic of GoogleTest's typed tests.

All of this is still a bit rough though. I'm going to be cleaning up
some aspects of the implementation, documenting things better, and
adding tests which include non-trivial types. As soon as I'm comfortable
with the correctness, I plan to switch existing users of SmallMap over
to this class as it is already more correct w.r.t. construction and
destruction of objects iin the map.

Thanks to Benjamin Kramer for all the reviews of this and the lead-up
patches. That said, more review on this would really be appreciated. As
I've noted a few times, I'm quite surprised how hard it is to get the
semantics for a hashtable-based map container with a small buffer
optimization correct. =]

llvm-svn: 158638
2012-06-17 09:05:09 +00:00
Chandler Carruth
a68dcb448a Work around a bug with MSVC 10 where it fails to recognize a valid use
of typename. GCC and Clang were fine with this, but MSVC won't accept
it. Fortunately, it also doesn't need it. Yuck.

Thanks to Nakamura for pointing this out in IRC.

llvm-svn: 158593
2012-06-16 03:54:11 +00:00
Chandler Carruth
2b50c40ebd Type parameterize the DenseMap unit tests.
These were already trying to be type parameterized over different
key/value pairs. I've realized this goal using GoogleTest's typed test
functionality. This allows us to easily replicate the tests across
different key/value combinations and soon different mapping templates.

I've fixed a few bugs in the tests and extended them a bit in the
process as many tests were only applying to the int->int mapping.

llvm-svn: 158589
2012-06-16 01:31:33 +00:00