1/* { dg-do compile } */
2/* { dg-require-visibility "" } */
3
4typedef unsigned int size_t;
5namespace std __attribute__ ((__visibility__ ("default")))
6{
7  template < typename _Iterator > struct iterator_traits
8  {
9  };
10  template < typename _Tp > struct iterator_traits <_Tp * >
11  {
12    typedef _Tp & reference;
13  };
14}
15
16namespace __gnu_cxx __attribute__ ((__visibility__ ("default")))
17{
18  using std::iterator_traits;
19  template < typename _Iterator, typename _Container > class __normal_iterator
20  {
21  public:typedef _Iterator iterator_type;
22    typedef typename iterator_traits < _Iterator >::reference reference;
23    reference operator* () const
24    {
25    }
26    __normal_iterator operator++ (int)
27    {
28    }
29  };
30  template < typename _IteratorL, typename _IteratorR,
31    typename _Container > inline bool operator!= (const __normal_iterator <
32						  _IteratorL,
33						  _Container > &__lhs,
34						  const __normal_iterator <
35						  _IteratorR,
36						  _Container > &__rhs)
37  {
38  }
39}
40
41extern "C"
42{
43  extern "C"
44  {
45    __extension__ typedef __SIZE_TYPE__ __intptr_t;
46  }
47}
48namespace __gnu_cxx __attribute__ ((__visibility__ ("default")))
49{
50  template < typename _Tp > class new_allocator
51  {
52  public:typedef size_t size_type;
53    typedef _Tp *pointer;
54    template < typename _Tp1 > struct rebind
55    {
56      typedef new_allocator < _Tp1 > other;
57    };
58  };
59}
60
61namespace std __attribute__ ((__visibility__ ("default")))
62{
63template < typename _Tp > class allocator:public __gnu_cxx::new_allocator <
64    _Tp >
65  {
66  };
67}
68
69extern "C"
70{
71  typedef __intptr_t intptr_t;
72}
73namespace llvm
74{
75  template < typename NodeTy > class ilist_half_node
76  {
77  };
78template < typename NodeTy > class ilist_node:private ilist_half_node <
79    NodeTy >
80  {
81  };
82  class MachineBasicBlock;
83  class MachineOperand
84  {
85  public:enum MachineOperandType
86    {
87    }
88    Contents;
89    unsigned getReg () const
90    {
91    }
92  };
93  class TargetRegisterInfo;
94}
95
96namespace std __attribute__ ((__visibility__ ("default")))
97{
98  template < typename _Tp, typename _Alloc > struct _Vector_base
99  {
100    typedef typename _Alloc::template rebind < _Tp >::other _Tp_alloc_type;
101  };
102template < typename _Tp, typename _Alloc = std::allocator < _Tp > >class vector:protected _Vector_base < _Tp,
103    _Alloc
104    >
105  {
106    typedef _Vector_base < _Tp, _Alloc > _Base;
107    typedef typename _Base::_Tp_alloc_type _Tp_alloc_type;
108  public:typedef _Tp value_type;
109    typedef typename _Tp_alloc_type::pointer pointer;
110    typedef __gnu_cxx::__normal_iterator < pointer, vector > iterator;
111    iterator begin ()
112    {
113    }
114    iterator end ()
115    {
116    }
117  };
118}
119
120namespace llvm
121{
122  class MachineFunction;
123  class MachineInstr:public ilist_node < MachineInstr >
124  {
125  public:const MachineBasicBlock *getParent () const
126    {
127    }
128    const MachineOperand & getOperand (unsigned i) const
129    {
130    }
131    bool registerDefIsDead (unsigned Reg, const TargetRegisterInfo * TRI =
132			    __null) const
133    {
134    }
135  };
136  class AnalysisResolver;
137  class Pass
138  {
139    AnalysisResolver *Resolver;
140    intptr_t PassID;
141  public:  explicit Pass (intptr_t pid):Resolver (0), PassID (pid)
142    {
143    }
144    explicit Pass (const void *pid):Resolver (0), PassID ((intptr_t) pid)
145    {
146    }
147    template < typename AnalysisType > AnalysisType & getAnalysis () const;
148  };
149  class FunctionPass:public Pass
150  {
151  public:explicit FunctionPass (intptr_t pid):Pass (pid)
152    {
153    }
154    explicit FunctionPass (const void *pid):Pass (pid)
155    {
156    }
157  };
158  class PassInfo
159  {
160  public:typedef Pass *(*NormalCtor_t) ();
161  private:const char *const PassName;
162    const char *const PassArgument;
163    const intptr_t PassID;
164    const bool IsCFGOnlyPass;
165    const bool IsAnalysis;
166    const bool IsAnalysisGroup;
167    NormalCtor_t NormalCtor;
168  public:   PassInfo (const char *name, const char *arg, intptr_t pi, NormalCtor_t normal = 0, bool isCFGOnly = false, bool is_analysis = false):PassName (name), PassArgument (arg), PassID (pi),
169      IsCFGOnlyPass (isCFGOnly), IsAnalysis (is_analysis),
170      IsAnalysisGroup (false), NormalCtor (normal)
171    {
172    }
173  };
174  template < typename PassName > Pass * callDefaultCtor ()
175  {
176    return new PassName ();
177  }
178  template < typename passName > struct RegisterPass:public PassInfo
179  {
180  RegisterPass (const char *PassArg, const char *Name, bool CFGOnly = false, bool is_analysis = false):PassInfo (Name, PassArg, intptr_t (&passName::ID),
181	      PassInfo::NormalCtor_t (callDefaultCtor < passName >), CFGOnly,
182	      is_analysis)
183    {
184    }
185  };
186  template < typename T > class SmallVectorImpl
187  {
188  };
189  template < typename T,
190    unsigned N > class SmallVector:public SmallVectorImpl < T >
191  {
192  };
193  class MachineFunctionPass:public FunctionPass
194  {
195  protected:explicit MachineFunctionPass (intptr_t ID):FunctionPass (ID)
196    {
197    }
198    explicit MachineFunctionPass (void *ID):FunctionPass (ID)
199    {
200    }
201    virtual bool runOnMachineFunction (MachineFunction & MF) = 0;
202  };
203  class LiveIndex
204  {
205  private:unsigned index;
206  };
207  class VNInfo
208  {
209  };
210  struct LiveRange
211  {
212    LiveIndex start;
213    LiveIndex end;
214    VNInfo *valno;
215  };
216  class LiveInterval
217  {
218  public:typedef SmallVector < LiveRange, 4 > Ranges;
219    bool containsOneValue () const
220    {
221    }
222    LiveRange *getLiveRangeContaining (LiveIndex Idx)
223    {
224    }
225    void removeRange (LiveIndex Start, LiveIndex End, bool RemoveDeadValNo =
226		      false);
227    void removeRange (LiveRange LR, bool RemoveDeadValNo = false)
228    {
229      removeRange (LR.start, LR.end, RemoveDeadValNo);
230    }
231  };
232  class LiveIntervals:public MachineFunctionPass
233  {
234  public:static char ID;
235    LiveIndex getDefIndex (LiveIndex index)
236    {
237    }
238    LiveInterval & getInterval (unsigned reg)
239    {
240    }
241    LiveIndex getInstructionIndex (const MachineInstr * instr) const
242    {
243    }
244  };
245}
246
247using namespace llvm;
248namespace
249{
250struct __attribute__ ((visibility ("hidden"))) StrongPHIElimination:public
251    MachineFunctionPass
252  {
253    static char ID;
254  StrongPHIElimination ():MachineFunctionPass (&ID)
255    {
256    }
257    bool runOnMachineFunction (MachineFunction & Fn);
258  };
259}
260
261static RegisterPass < StrongPHIElimination > X ("strong-phi-node-elimination",
262						"Eliminate PHI nodes for register allocation, intelligently");
263bool
264StrongPHIElimination::runOnMachineFunction (MachineFunction & Fn)
265{
266  LiveIntervals & LI = getAnalysis < LiveIntervals > ();
267  std::vector < MachineInstr * >phis;
268  for (std::vector < MachineInstr * >::iterator I = phis.begin (), E =
269       phis.end (); I != E;)
270    {
271      MachineInstr *PInstr = *(I++);
272      unsigned DestReg = PInstr->getOperand (0).getReg ();
273      LiveInterval & PI = LI.getInterval (DestReg);
274      if (PInstr->registerDefIsDead (DestReg))
275	{
276	  if (PI.containsOneValue ())
277	    {
278	      LiveIndex idx =
279		LI.getDefIndex (LI.getInstructionIndex (PInstr));
280	      PI.removeRange (*PI.getLiveRangeContaining (idx), true);
281	    }
282	}
283    }
284}
285