#line 1 "ah_get/main.cc"
#ifndef __ac_FIRST__home_Tom_aspectcX43X43__
#define __ac_FIRST__home_Tom_aspectcX43X43__
#define __ac_FIRST_FILE__home_Tom_aspectcX43X43_ah_get_main_cc__
#ifndef __ac_have_predefined_includes__
#define __ac_have_predefined_includes__
#endif // __ac_have_predefined_includes__

#ifndef __ac_h_
#define __ac_h_
#ifdef __cplusplus
namespace AC {
  typedef const char* Type;
  enum JPType { GET = 65536, SET = 131072, REF = 1048576, BUILTIN = 524288, CALL = 262144, EXECUTION = 16777216, CONSTRUCTION = 33554432, DESTRUCTION = 67108864 };
  enum Protection { PROT_NONE, PROT_PRIVATE, PROT_PROTECTED, PROT_PUBLIC };
  enum Specifiers { SPEC_NONE = 0x0 , SPEC_STATIC = 0x1, SPEC_MUTABLE = 0x2, SPEC_VIRTUAL = 0x4 };
  struct Action {
    void **_args; void *_result; void *_entity; void *_array; void **_indices; void *_target; void *_that; void *_fptr;
    void (*_wrapper)(Action &);
    inline void trigger () { _wrapper (*this); }
  };
  template <typename T> struct ResultBuffer {
    char _data[sizeof (T)];
    void operator = (const T& t) { *this = (const ResultBuffer &)t; }
  };
  template <typename T, typename N> struct TL {
    typedef T type; typedef N next; enum { ARGS = next::ARGS + 1 };
  };
  struct TLE { enum { ARGS = 0 }; };
  template <typename T> struct Referred { typedef T type; };
  template <typename T> struct Referred<T &> { typedef T type; };
  template <typename TL, int I> struct Arg {
    typedef typename Arg<typename TL::next, I - 1>::Type Type;
    typedef typename Referred<Type>::type ReferredType;
  };
  template <typename TL> struct Arg<TL, 0> {
    typedef typename TL::type Type;
    typedef typename Referred<Type>::type ReferredType;
  };
  template <typename T, bool Qual> struct ConstQualify {};
  template <typename T> struct ConstQualify<T, false> { typedef T type; };
  template <typename T> struct ConstQualify<T, true> { typedef const T type; };
  template <typename T> struct ConstQualify<const T, true> { typedef const T type; };
  template <typename TL, unsigned int FC, int I> struct ArgCQ {
    typedef typename ConstQualify<typename Arg<TL, I>::Type, ( FC >> I ) & 1>::type Type;
    typedef typename Referred<Type>::type ReferredType;
  };
  template <typename T> int ttest(...);
  template <typename T> char ttest(typename T::__TI const volatile *);
  template<typename T> struct HasTypeInfo {
    enum { RET=((sizeof(ttest<T>(0))==1)?1:0) };
  };
  template<typename T, int HAVE = HasTypeInfo<T>::RET> struct TypeInfo {
    enum { AVAILABLE = 0, BASECLASSES = 0, MEMBERS = 0, FUNCTIONS = 0,
           CONSTRUCTORS = 0, DESTRUCTORS = 0 };
    typedef T That;
  };
  template<typename T> struct TypeInfo<T, 1> : T::__TI {
    enum { AVAILABLE = 1 };
  };
  template<typename T> struct RT {};
  template<typename T> RT<T> rt_deduce (const T&) { return RT<T>(); }
  template<typename T> RT<T> rt_deduce (const volatile T&) { return RT<T>(); }
  struct Cnv { template<typename T> operator RT<T>() const { return RT<T>(); }};
  #define __AC_TYPEOF(expr) (1?AC::Cnv():AC::rt_deduce(expr))
  template <class Aspect, int Index>
  struct CFlow {
    static int &instance () {
      static int counter = 0;
      return counter;
    }
    CFlow () { instance ()++; }
    ~CFlow () { instance ()--; }
    static bool active () { return instance () > 0; }
  };
  template <typename T, typename E, typename O> inline E T::* mptr_castT( E O::*mptr ) { return static_cast< E T::* >( mptr ); }
  template <typename A> struct SpliceT {};
  template <typename B, unsigned int D> struct SpliceT< B[D] > {
    typedef B Base;
    enum { Dim = D };
  };
  template <unsigned int TSize, typename TIdx, typename N> struct DIL : N {
    typedef N Next;
    enum { Count = Next::Count + 1 };
    enum { Size = TSize };
    typedef TIdx Idx;
    Idx idx;
    template <typename B> struct Entity { typedef typename SpliceT< typename Next::template Entity<B>::Type >::Base Type; };
    template <typename E> struct Array { typedef typename Next::template Array<E>::Type Type[Size]; };
    template <typename E> inline E& apply( typename Array<E>::Type &base ) { return Next::template apply<E>( base[idx] ); }
    template <typename A> struct Append { typedef DIL<Size, Idx, typename Next::template Append<A>::NewList > NewList; };
    template <typename ONext> inline void copyTo( DIL<Size,Idx,ONext> *target ) {
      target->idx = idx;
      Next::copyTo( static_cast<ONext *>( target ) );
    };
  };
  struct DILE {
    enum { Count = 0 };
    template <typename B> struct Entity { typedef B Type; };
    template <typename E> struct Array { typedef E Type; };
    template <typename E> inline E& apply( typename Array<E>::Type &base ) { return base; }
    template <typename A> struct Append { typedef A NewList; };
    template <typename O> inline void copyTo( O * ) {};
  };
  template <typename L, unsigned int D> struct DIL_Op {
    enum { Size = DIL_Op<typename L::Next, D - 1>::Size };
    typedef typename DIL_Op<typename L::Next, D - 1>::Idx Idx;
    inline static Idx &idx( L *di ) { return DIL_Op<typename L::Next, D - 1>::idx( di ); }
  };
  template <typename L> struct DIL_Op<L,0> {
    enum  { Size = L::Size };
    typedef typename L::Idx Idx;
    inline static Idx &idx( L *di ) { return di->idx; }
  };
  template <typename TEntity> struct BI_Entity {
    typedef TEntity Entity;
    Entity &_ent;
    inline BI_Entity( Entity &ent ) : _ent( ent ) {}
    inline Entity &entity() { return _ent; }
  };
  template <typename TTarget, typename TEntity> struct BI_Member {
    typedef TEntity Entity;
    typedef TTarget Target;
    typedef Entity Target::*Member;
    Target &_target;
    Member _member;
    inline BI_Member( Target &target, Member mem ) : _target( target ), _member( mem ) {}
    inline Entity &entity() { return _target.*_member; }
  };
  template <typename TTarget, typename TEntity> struct BI_Static {
    typedef TEntity Entity;
    typedef TTarget Target;
    Entity &_ent;
    Target &_target;
    inline BI_Static( Target &target, Entity &ent ) : _ent( ent ), _target( target ) {}
    inline Entity &entity() { return _ent; }
  };
  template <typename TBI, typename TDI> struct PackedEntity {
    typedef PackedEntity<TBI, TDI> SELF;
    typedef TBI BI;
    typedef TDI DI;
    BI _base;
    DI _indices;
    inline PackedEntity( BI base ) : _base( base ) {}
    typedef typename BI::Entity Base;
    typedef typename DI::template Entity<Base>::Type Entity;
    inline Base &base() { return _base.entity(); };
    inline Entity &entity() { return _indices.template apply<Entity>( base() ); }
    enum { DIMS = DI::Count };
    template <unsigned int D> struct Dim : DIL_Op<DI,D> {};
    template <unsigned int D> inline typename Dim<D>::Idx &idx() { return Dim<D>::idx( &_indices ); }
    template<typename NextIdx> struct Extend {
      typedef typename SpliceT<Entity>::Base NewEnt;
      enum { NextDim = SpliceT<Entity>::Dim };
      typedef typename DI::template Append< DIL< NextDim, NextIdx, DILE > >::NewList NewDI;
      typedef PackedEntity< BI, NewDI > NewPacked;
    };
    template<typename TIdxN> inline typename Extend<TIdxN>::NewPacked operator []( TIdxN idxN ) {
      typedef typename Extend<TIdxN>::NewPacked __PE;
      __PE res( _base );
      _indices.copyTo( &res._indices );
      __PE::template Dim<__PE::DIMS - 1>::idx( &res._indices ) = idxN;
      return res;
    }
    inline SELF operator =( Entity arg ) { entity() = arg; return *this; }
    template<typename ARG> inline SELF operator +=( ARG arg ) { entity() += arg; return *this; }
    template<typename ARG> inline SELF operator -=( ARG arg ) { entity() -= arg; return *this; }
    template<typename ARG> inline SELF operator *=( ARG arg ) { entity() *= arg; return *this; }
    template<typename ARG> inline SELF operator /=( ARG arg ) { entity() /= arg; return *this; }
    template<typename ARG> inline SELF operator %=( ARG arg ) { entity() %= arg; return *this; }
    template<typename ARG> inline SELF operator |=( ARG arg ) { entity() |= arg; return *this; }
    template<typename ARG> inline SELF operator ^=( ARG arg ) { entity() ^= arg; return *this; }
    template<typename ARG> inline SELF operator &=( ARG arg ) { entity() &= arg; return *this; }
    template<typename ARG> inline SELF operator <<=( ARG arg ) { entity() <<= arg; return *this; }
    template<typename ARG> inline SELF operator >>=( ARG arg ) { entity() >>= arg; return *this; }
    inline SELF operator ++() { ++entity(); return *this; }
    inline SELF operator --() { --entity(); return *this; }
  };
  template <typename TEntity>
    inline PackedEntity< BI_Entity<TEntity>, DILE > PEInit( TEntity &ent ) {
      return PackedEntity< BI_Entity<TEntity>, DILE >( BI_Entity<TEntity>( ent ) );
    }
  template <typename TTarget, typename TEntity>
    inline PackedEntity<BI_Member<TTarget, TEntity>, DILE> PEInit( const TTarget &target, TEntity TTarget::*member ) {
      return PackedEntity< BI_Member<TTarget, TEntity>, DILE >( BI_Member<TTarget, TEntity>( const_cast<TTarget &>( target ), member ) );
    }
  template <typename TTarget, typename TEntity>
    inline PackedEntity<BI_Static<TTarget, TEntity>, DILE> PEInit( const TTarget &target, TEntity &ent ) {
      return PackedEntity< BI_Static<TTarget, TEntity>, DILE >( BI_Static<TTarget, TEntity>( const_cast<TTarget &>( target ), ent ) );
    }

#ifdef __acdef_float
template <typename BASE, int ID=0> struct _FloatN {
  BASE val;
  _FloatN() {}
  _FloatN(const BASE& v) : val(v) {}
  operator BASE() const { return val; }
};
#endif
}

#ifdef __acdef_float
typedef AC::_FloatN<float> _Float32;
typedef AC::_FloatN<double> _Float32x;
typedef AC::_FloatN<long double, 0> _Float64;
typedef AC::_FloatN<long double, 1> _Float128;
typedef AC::_FloatN<long double, 2> _Float64x;
#endif

#if defined(__acweaving) && defined(__ARM_NEON)
typedef __attribute__ ((__neon_vector_type__ (4))) float __Float32x4_t;
typedef __attribute__ ((__neon_vector_type__ (2))) double __Float64x2_t;
#endif
#endif // __cplusplus
#endif // __ac_h_
class Hello;
#endif // __ac_FIRST__home_Tom_aspectcX43X43__
#line 219 "main.acc"

#ifndef __ac_fwd_Hello__
#define __ac_fwd_Hello__
class Hello;
namespace AC {
  __attribute((always_inline)) inline void invoke_Hello_Hello__a0_before ();
}
#endif

#ifndef __ac_need__home_Tom_aspectcX43X43_ah_get_hello_world_ah__
#define __ac_need__home_Tom_aspectcX43X43_ah_get_hello_world_ah__
#endif

#line 1 "ah_get/main.cc"

#line 1 "ah_get/main.cc"
#include <iostream>

char exclamation = '!';

#line 240 "main.acc"

template <typename TResult, typename TEntity>
__attribute__((always_inline)) inline TResult __Get__Z4mainv_0_0 (TEntity &ent, AC::RT<TResult>){
  TResult __result_buffer;
  AC::invoke_Hello_Hello__a0_before ();
  __result_buffer = ::exclamation;
  return (TResult &)__result_buffer;
}

#line 5 "ah_get/main.cc"

#line 5 "ah_get/main.cc"
int main(){
  std::cout << __Get__Z4mainv_0_0<  > (exclamation, __AC_TYPEOF((exclamation)) ) << std::endl; //print World String 
  return 0;
}
#line 257 "main.acc"

#ifndef __ac_have_predefined_includes__
/*** begin of aspect includes ***/
// commented out by ac++: #include "hello_world.ah"
/*** end of aspect includes ***/
#endif
#line 9 "ah_get/main.cc"

#line 9 "ah_get/main.cc"

#ifdef __ac_FIRST_FILE__home_Tom_aspectcX43X43_ah_get_main_cc__
#ifdef __ac_need__home_Tom_aspectcX43X43_ah_get_hello_world_ah__
#ifndef __ac_have__home_Tom_aspectcX43X43_ah_get_hello_world_ah__
#define __ac_have__home_Tom_aspectcX43X43_ah_get_hello_world_ah__
// commented out by ac++: #include "hello_world.ah"
#line 1 "ah_get/hello_world.ah"
#ifndef __WORLD_AH__
#define __WORLD_AH__

// commented out by ac++: #include <iostream>
// commented out by ac++: #include <string>

class Hello {
#line 281 "main.acc"
public:
  template <typename, int = 0> struct __BYPASSHello {};
  template <typename, int> friend struct __BYPASSHello;
private:
#line 7 "ah_get/hello_world.ah"

#line 7 "ah_get/hello_world.ah"


  public: __attribute__((always_inline)) inline void __a0_before() {
    //print "Hello" before gettig the "World" String of the World Object
    std::cout << "Hello World";
  }

#line 296 "main.acc"

public:
  static Hello *aspectof () {
    static Hello __instance;
    return &__instance;
  }
  static Hello *aspectOf () {
    return aspectof ();
  }
private:

#line 14 "ah_get/hello_world.ah"

#line 14 "ah_get/hello_world.ah"
}
#line 312 "main.acc"
;
namespace AC {
  __attribute((always_inline)) inline void invoke_Hello_Hello__a0_before () {
    ::Hello::aspectof()->__a0_before ();
  }
} 

#line 14 "ah_get/hello_world.ah"

#line 14 "ah_get/hello_world.ah"
;

#endif
#line 15 "ah_get/main.cc"
#endif
#endif
#undef __ac_FIRST__home_Tom_aspectcX43X43__
#undef __ac_FIRST_FILE__home_Tom_aspectcX43X43_ah_get_main_cc__
#endif // __ac_FIRST_FILE__home_Tom_aspectcX43X43_ah_get_main_cc__
