TinyPtrVector.h revision 840635741f132a9a10f052cbf3b21e14bc74835a
19d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner//===- llvm/ADT/TinyPtrVector.h - 'Normally tiny' vectors -------*- C++ -*-===// 29d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner// 39d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner// The LLVM Compiler Infrastructure 49d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner// 59d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner// This file is distributed under the University of Illinois Open Source 69d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner// License. See LICENSE.TXT for details. 79d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner// 89d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner//===----------------------------------------------------------------------===// 99d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner// 109d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner// This file defines the Type class. 119d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner// 129d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner//===----------------------------------------------------------------------===// 139d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 149d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner#ifndef LLVM_ADT_TINYPTRVECTOR_H 159d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner#define LLVM_ADT_TINYPTRVECTOR_H 169d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 179d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner#include "llvm/ADT/SmallVector.h" 189d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner#include "llvm/ADT/PointerUnion.h" 199d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 209d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattnernamespace llvm { 219d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 229d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner/// TinyPtrVector - This class is specialized for cases where there are 239d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner/// normally 0 or 1 element in a vector, but is general enough to go beyond that 249d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner/// when required. 259d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner/// 269d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner/// NOTE: This container doesn't allow you to store a null pointer into it. 279d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner/// 289d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattnertemplate <typename EltTy> 299d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattnerclass TinyPtrVector { 309d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattnerpublic: 319d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner typedef llvm::SmallVector<EltTy, 4> VecTy; 329d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner llvm::PointerUnion<EltTy, VecTy*> Val; 339d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 349d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner TinyPtrVector() {} 359d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner TinyPtrVector(const TinyPtrVector &RHS) : Val(RHS.Val) { 369d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner if (VecTy *V = Val.template dyn_cast<VecTy*>()) 379d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner Val = new VecTy(*V); 389d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } 399d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner ~TinyPtrVector() { 409d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner if (VecTy *V = Val.template dyn_cast<VecTy*>()) 419d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner delete V; 429d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } 439d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 449d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner /// empty() - This vector can be empty if it contains no element, or if it 459d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner /// contains a pointer to an empty vector. 469d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner bool empty() const { 479d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner if (Val.isNull()) return true; 489d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner if (VecTy *Vec = Val.template dyn_cast<VecTy*>()) 499d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner return Vec->empty(); 509d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner return false; 519d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } 529d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 539d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner unsigned size() const { 549d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner if (empty()) 559d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner return 0; 569d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner if (Val. template is<EltTy>()) 579d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner return 1; 589d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner return Val. template get<VecTy*>()->size(); 599d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } 609d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 619d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner EltTy operator[](unsigned i) const { 629d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner assert(!Val.isNull() && "can't index into an empty vector"); 639d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner if (EltTy V = Val.template dyn_cast<EltTy>()) { 649d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner assert(i == 0 && "tinyvector index out of range"); 659d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner return V; 669d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } 679d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 689d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner assert(i < Val. template get<VecTy*>()->size() && 699d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner "tinyvector index out of range"); 709d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner return (*Val. template get<VecTy*>())[i]; 719d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } 729d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 739d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner EltTy front() const { 749d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner assert(!empty() && "vector empty"); 759d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner if (EltTy V = Val.template dyn_cast<EltTy>()) 769d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner return V; 779d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner return Val.template get<VecTy*>()->front(); 789d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } 799d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 809d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner void push_back(EltTy NewVal) { 819d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner assert(NewVal != 0 && "Can't add a null value"); 829d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 839d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner // If we have nothing, add something. 849d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner if (Val.isNull()) { 859d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner Val = NewVal; 869d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner return; 879d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } 889d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 899d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner // If we have a single value, convert to a vector. 909d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner if (EltTy V = Val.template dyn_cast<EltTy>()) { 919d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner Val = new VecTy(); 929d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner Val.template get<VecTy*>()->push_back(V); 939d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } 949d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 959d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner // Add the new value, we know we have a vector. 969d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner Val.template get<VecTy*>()->push_back(NewVal); 979d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } 989d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 999d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner void clear() { 1009d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner // If we have a single value, convert to empty. 101840635741f132a9a10f052cbf3b21e14bc74835aChris Lattner if (Val.template is<EltTy>()) { 1029d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner Val = (EltTy)0; 1039d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } else if (VecTy *Vec = Val.template dyn_cast<VecTy*>()) { 1049d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner // If we have a vector form, just clear it. 1059d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner Vec->clear(); 1069d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } 1079d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner // Otherwise, we're already empty. 1089d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner } 1099d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 1109d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattnerprivate: 1119d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner void operator=(const TinyPtrVector&); // NOT IMPLEMENTED YET. 1129d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner}; 1139d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner} // end namespace llvm 1149d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner 1159d69d4aadd4a58aba5634d5c3d2c2a6d8d284134Chris Lattner#endif 116