1//===-- DeclLookups.h - Low-level interface to all names in a DC-*- C++ -*-===//
2//
3//                     The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10//  This file defines DeclContext::all_lookups_iterator.
11//
12//===----------------------------------------------------------------------===//
13
14#ifndef LLVM_CLANG_AST_DECLLOOKUPS_H
15#define LLVM_CLANG_AST_DECLLOOKUPS_H
16
17#include "clang/AST/ASTContext.h"
18#include "clang/AST/DeclBase.h"
19#include "clang/AST/DeclContextInternals.h"
20#include "clang/AST/DeclarationName.h"
21
22namespace clang {
23
24/// all_lookups_iterator - An iterator that provides a view over the results
25/// of looking up every possible name.
26class DeclContext::all_lookups_iterator {
27  StoredDeclsMap::iterator It, End;
28public:
29  typedef lookup_result             value_type;
30  typedef lookup_result             reference;
31  typedef lookup_result             pointer;
32  typedef std::forward_iterator_tag iterator_category;
33  typedef std::ptrdiff_t            difference_type;
34
35  all_lookups_iterator() {}
36  all_lookups_iterator(StoredDeclsMap::iterator It,
37                       StoredDeclsMap::iterator End)
38      : It(It), End(End) {}
39
40  DeclarationName getLookupName() const { return It->first; }
41
42  reference operator*() const { return It->second.getLookupResult(); }
43  pointer operator->() const { return It->second.getLookupResult(); }
44
45  all_lookups_iterator& operator++() {
46    // Filter out using directives. They don't belong as results from name
47    // lookup anyways, except as an implementation detail. Users of the API
48    // should not expect to get them (or worse, rely on it).
49    do {
50      ++It;
51    } while (It != End &&
52             It->first == DeclarationName::getUsingDirectiveName());
53
54    return *this;
55  }
56
57  all_lookups_iterator operator++(int) {
58    all_lookups_iterator tmp(*this);
59    ++(*this);
60    return tmp;
61  }
62
63  friend bool operator==(all_lookups_iterator x, all_lookups_iterator y) {
64    return x.It == y.It;
65  }
66  friend bool operator!=(all_lookups_iterator x, all_lookups_iterator y) {
67    return x.It != y.It;
68  }
69};
70
71inline DeclContext::lookups_range DeclContext::lookups() const {
72  DeclContext *Primary = const_cast<DeclContext*>(this)->getPrimaryContext();
73  if (Primary->hasExternalVisibleStorage())
74    getParentASTContext().getExternalSource()->completeVisibleDeclsMap(Primary);
75  if (StoredDeclsMap *Map = Primary->buildLookup())
76    return lookups_range(all_lookups_iterator(Map->begin(), Map->end()),
77                         all_lookups_iterator(Map->end(), Map->end()));
78  return lookups_range();
79}
80
81inline DeclContext::all_lookups_iterator DeclContext::lookups_begin() const {
82  return lookups().begin();
83}
84
85inline DeclContext::all_lookups_iterator DeclContext::lookups_end() const {
86  return lookups().end();
87}
88
89inline DeclContext::lookups_range DeclContext::noload_lookups() const {
90  DeclContext *Primary = const_cast<DeclContext*>(this)->getPrimaryContext();
91  if (StoredDeclsMap *Map = Primary->getLookupPtr())
92    return lookups_range(all_lookups_iterator(Map->begin(), Map->end()),
93                         all_lookups_iterator(Map->end(), Map->end()));
94  return lookups_range();
95}
96
97inline
98DeclContext::all_lookups_iterator DeclContext::noload_lookups_begin() const {
99  return noload_lookups().begin();
100}
101
102inline
103DeclContext::all_lookups_iterator DeclContext::noload_lookups_end() const {
104  return noload_lookups().end();
105}
106
107} // end namespace clang
108
109#endif
110