1ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao// RUN: %clang_cc1 -fsyntax-only -verify %s
2ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao
3ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liaotemplate<typename MetaFun, typename T>
4ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liaostruct bind_metafun {
5ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao  typedef typename MetaFun::template apply<T> type;
6ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao};
7ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao
8ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liaostruct add_pointer {
9ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao  template<typename T>
10ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao  struct apply {
11ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao    typedef T* type;
12ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao  };
13ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao};
14ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao
15ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liaoint i;
16ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao// FIXME: if we make the declarator below a pointer (e.g., with *ip),
17ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao// the error message isn't so good because we don't get the handy
18ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao// 'aka' telling us that we're dealing with an int**. Should we fix
19ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao// getDesugaredType to dig through pointers and such?
20ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liaobind_metafun<add_pointer, int>::type::type ip = &i;
21ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liaobind_metafun<add_pointer, float>::type::type fp = &i; // expected-error{{cannot initialize a variable of type 'bind_metafun<add_pointer, float>::type::type' (aka 'float *') with an rvalue of type 'int *'}}
22ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao
23ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao
24ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liaotemplate<typename T>
25ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liaostruct extract_type_type {
26ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao  typedef typename T::type::type t;
27ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao};
28ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liao
29ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liaodouble d;
30ea285162342df160e7860e26528bc7110bc6c0cdShih-wei Liaoextract_type_type<bind_metafun<add_pointer, double> >::t dp = &d;
31