format_signature.hpp 4.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188
  1. // Copyright Daniel Wallin 2008. Use, modification and distribution is
  2. // subject to the Boost Software License, Version 1.0. (See accompanying
  3. // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  4. #ifndef LUABIND_FORMAT_SIGNATURE_081014_HPP
  5. # define LUABIND_FORMAT_SIGNATURE_081014_HPP
  6. # include <luabind/config.hpp>
  7. # include <luabind/lua_include.hpp>
  8. # include <luabind/typeid.hpp>
  9. # include <boost/mpl/begin_end.hpp>
  10. # include <boost/mpl/next.hpp>
  11. # include <boost/mpl/size.hpp>
  12. namespace luabind { namespace adl
  13. {
  14. class object;
  15. class argument;
  16. template <class Base>
  17. struct table;
  18. } // namespace adl
  19. using adl::object;
  20. using adl::argument;
  21. using adl::table;
  22. } // namespace luabind
  23. namespace luabind { namespace detail {
  24. LUABIND_API std::string get_class_name(lua_State* L, type_id const& i);
  25. template <class T>
  26. struct type_to_string
  27. {
  28. static void get(lua_State* L)
  29. {
  30. lua_pushstring(L, get_class_name(L, typeid(T)).c_str());
  31. }
  32. };
  33. template <class T>
  34. struct type_to_string<T*>
  35. {
  36. static void get(lua_State* L)
  37. {
  38. type_to_string<T>::get(L);
  39. lua_pushstring(L, "*");
  40. lua_concat(L, 2);
  41. }
  42. };
  43. template <class T>
  44. struct type_to_string<T&>
  45. {
  46. static void get(lua_State* L)
  47. {
  48. type_to_string<T>::get(L);
  49. lua_pushstring(L, "&");
  50. lua_concat(L, 2);
  51. }
  52. };
  53. template <class T>
  54. struct type_to_string<T const>
  55. {
  56. static void get(lua_State* L)
  57. {
  58. type_to_string<T>::get(L);
  59. lua_pushstring(L, " const");
  60. lua_concat(L, 2);
  61. }
  62. };
  63. # define LUABIND_TYPE_TO_STRING(x) \
  64. template <> \
  65. struct type_to_string<x> \
  66. { \
  67. static void get(lua_State* L) \
  68. { \
  69. lua_pushstring(L, #x); \
  70. } \
  71. };
  72. # define LUABIND_INTEGRAL_TYPE_TO_STRING(x) \
  73. LUABIND_TYPE_TO_STRING(x) \
  74. LUABIND_TYPE_TO_STRING(unsigned x)
  75. LUABIND_INTEGRAL_TYPE_TO_STRING(char)
  76. LUABIND_INTEGRAL_TYPE_TO_STRING(short)
  77. LUABIND_INTEGRAL_TYPE_TO_STRING(int)
  78. LUABIND_INTEGRAL_TYPE_TO_STRING(long)
  79. LUABIND_TYPE_TO_STRING(void)
  80. LUABIND_TYPE_TO_STRING(bool)
  81. LUABIND_TYPE_TO_STRING(std::string)
  82. LUABIND_TYPE_TO_STRING(lua_State)
  83. LUABIND_TYPE_TO_STRING(luabind::object)
  84. LUABIND_TYPE_TO_STRING(luabind::argument)
  85. # undef LUABIND_INTEGRAL_TYPE_TO_STRING
  86. # undef LUABIND_TYPE_TO_STRING
  87. template <class Base>
  88. struct type_to_string<table<Base> >
  89. {
  90. static void get(lua_State* L)
  91. {
  92. lua_pushstring(L, "table");
  93. }
  94. };
  95. # ifndef LUABIND_CPP0x
  96. template <class End>
  97. void format_signature_aux(lua_State*, bool, End, End)
  98. {}
  99. template <class Iter, class End>
  100. void format_signature_aux(lua_State* L, bool first, Iter, End end)
  101. {
  102. if (!first)
  103. lua_pushstring(L, ",");
  104. type_to_string<typename Iter::type>::get(L);
  105. format_signature_aux(L, false, typename mpl::next<Iter>::type(), end);
  106. }
  107. template <class Signature>
  108. void format_signature(lua_State* L, char const* function, Signature)
  109. {
  110. typedef typename mpl::begin<Signature>::type first;
  111. type_to_string<typename first::type>::get(L);
  112. lua_pushstring(L, " ");
  113. lua_pushstring(L, function);
  114. lua_pushstring(L, "(");
  115. format_signature_aux(
  116. L
  117. , true
  118. , typename mpl::next<first>::type()
  119. , typename mpl::end<Signature>::type()
  120. );
  121. lua_pushstring(L, ")");
  122. lua_concat(L, static_cast<int>(mpl::size<Signature>()) * 2 + 2);
  123. }
  124. # else // LUABIND_CPP0x
  125. inline void format_signature_aux(lua_State*, vector<>, bool)
  126. {}
  127. template <class T, class... Args>
  128. void format_signature_aux(lua_State* L, vector<T, Args...>, bool first = true)
  129. {
  130. if (!first)
  131. lua_pushstring(L, ",");
  132. type_to_string<T>::get(L);
  133. format_signature_aux(L, vector<Args...>(), false);
  134. }
  135. template <class R, class... Args>
  136. void format_signature(lua_State* L, char const* function, vector<R, Args...>)
  137. {
  138. type_to_string<R>::get(L);
  139. lua_pushstring(L, " ");
  140. lua_pushstring(L, function);
  141. lua_pushstring(L, "(");
  142. format_signature_aux(L, vector<R, Args...>());
  143. lua_pushstring(L, ")");
  144. lua_concat(L, (sizeof...(Args) + 1) * 2 + 2);
  145. }
  146. # endif // LUABIND_CPP0x
  147. }} // namespace luabind::detail
  148. #endif // LUABIND_FORMAT_SIGNATURE_081014_HPP