ShSyntax.hpp

Go to the documentation of this file.
00001 // Sh: A GPU metaprogramming language.
00002 //
00003 // Copyright 2003-2005 Serious Hack Inc.
00004 // 
00005 // This library is free software; you can redistribute it and/or
00006 // modify it under the terms of the GNU Lesser General Public
00007 // License as published by the Free Software Foundation; either
00008 // version 2.1 of the License, or (at your option) any later version.
00009 //
00010 // This library is distributed in the hope that it will be useful,
00011 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00012 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00013 // Lesser General Public License for more details.
00014 //
00015 // You should have received a copy of the GNU Lesser General Public
00016 // License along with this library; if not, write to the Free Software
00017 // Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, 
00018 // MA  02110-1301, USA
00020 #ifndef SHSYNTAX_HPP
00021 #define SHSYNTAX_HPP
00022 
00023 #include "ShDllExport.hpp"
00024 #include "ShProgram.hpp"
00025 #include "ShUtility.hpp"
00026 
00031 
00032 
00033 #define SH_PUSH_ARG_QUEUE ::SH::shPushArgQueue()
00034 #define SH_PUSH_ARG ::SH::shPushArg()
00035 #define SH_PROCESS_ARG(arg, internal_cond) ::SH::shProcessArg(arg, internal_cond)
00036 
00037 
00039 
00040 
00046 #define SH_BEGIN_PROGRAM(target) ::SH::shBeginShader(target);
00047 
00055 #define SH_END_PROGRAM         ::SH::shEndShader();
00056 
00057 
00058 #define SH_END                 SH_END_PROGRAM
00059 
00060 #define SH_BEGIN_VERTEX_PROGRAM ::SH::shBeginShader("gpu:vertex");
00061 #define SH_BEGIN_FRAGMENT_PROGRAM ::SH::shBeginShader("gpu:fragment");
00062 
00064 
00065 
00070 #define SH_IF(cond) { \
00071   bool sh__internal_cond; \
00072   ::SH::shIf(SH_PUSH_ARG_QUEUE && SH_PUSH_ARG && SH_PROCESS_ARG(cond, &sh__internal_cond)); \
00073   if (::SH::ShContext::current()->parsing() || sh__internal_cond) {{
00074 
00079 #define SH_ELSE  \
00080   }} \
00081   ::SH::shElse(); \
00082   if (::SH::ShContext::current()->parsing() || !sh__internal_cond) {{
00083 
00088 #define SH_ENDIF \
00089   }} \
00090   ::SH::shEndIf(); \
00091 }
00092 
00093 
00095 
00096 
00100 #define SH_WHILE(cond) { \
00101   bool sh__internal_cond; \
00102   ::SH::shWhile(SH_PUSH_ARG_QUEUE && SH_PUSH_ARG && SH_PROCESS_ARG(cond, &sh__internal_cond)); \
00103   bool sh__internal_firsttime = true; \
00104   while ((sh__internal_firsttime && (::SH::ShContext::current()->parsing() || sh__internal_cond)) \
00105          || (!::SH::ShContext::current()->parsing() && ::SH::shEvaluateCondition(cond))) {{{
00106 
00110 #define SH_ENDWHILE \
00111     sh__internal_firsttime = false; \
00112   }}} \
00113   ::SH::shEndWhile(); \
00114 }
00115 
00116 
00118 
00119 
00123 #define SH_DO       { \
00124   ::SH::shDo(); \
00125   do {{{{
00126 
00130 #define SH_UNTIL(cond) \
00131   }}}} while (!::SH::ShContext::current()->parsing() && !::SH::shEvaluateCondition(cond)); \
00132   if (::SH::ShContext::current()->parsing()) ::SH::shUntil(SH_PUSH_ARG_QUEUE && SH_PUSH_ARG && SH_PROCESS_ARG(cond, 0)); }
00133 
00134 
00136 
00137 
00143 // TODO: It is possible to make declaring variables in init work. do so.
00144 #define SH_FOR(init,cond,update) { \
00145   if (::SH::ShContext::current()->parsing()) \
00146     ::SH::shFor(SH_PUSH_ARG_QUEUE \
00147              && SH_PUSH_ARG && SH_PROCESS_ARG(init, 0) \
00148              && SH_PUSH_ARG && SH_PROCESS_ARG(cond, 0) \
00149              && SH_PUSH_ARG && SH_PROCESS_ARG(update, 0)); \
00150   if (!::SH::ShContext::current()->parsing()) init; \
00151   bool sh__internal_first_time = true; \
00152   while (1) {{{{{ \
00153     if (!::SH::ShContext::current()->parsing()) { \
00154       if (!sh__internal_first_time) { update; } \
00155       else { sh__internal_first_time = false; } \
00156       if (!shEvaluateCondition(cond)) break; \
00157     }                                                                                  
00158 
00162 #define SH_ENDFOR \
00163     if (::SH::ShContext::current()->parsing()) break; \
00164   }}}}} \
00165   ::SH::shEndFor(); \
00166 }
00167 
00168 
00170 
00171 
00178 #define SH_BREAK(cond) \
00179   if (!::SH::ShContext::current()->parsing()) { \
00180     if (::SH::shEvaluateCondition(cond)) break;\
00181   } else {\
00182     ::SH::shBreak(SH_PUSH_ARG_QUEUE && SH_PUSH_ARG && SH_PROCESS_ARG(cond, 0));\
00183   }
00184 
00191 #define SH_CONTINUE(cond) \
00192   if (!::SH::ShContext::current()->parsing()) { \
00193     if (::SH::shEvaluateCondition(cond)) continue;\
00194   } else {\
00195     ::SH::shContinue(SH_PUSH_ARG_QUEUE && SH_PUSH_ARG && SH_PROCESS_ARG(cond, 0));\
00196   }
00197 
00200 #define SH_RETURN(a) ::SH::shRET(a)
00201 
00202 
00211 #define SH_BEGIN_SECTION(name) \
00212   {{{{{{ \
00213     if(::SH::ShContext::current()->parsing()) { \
00214       ::SH::shBeginSection(); \
00215       ::SH::shComment(name); \
00216     }
00217 
00218 #define SH_END_SECTION \
00219     if(::SH::ShContext::current()->parsing()) { ::SH::shEndSection(); } \
00220   }}}}}} 
00221 
00222 
00224 
00225 
00231 #define SH_NAME(var) do { var.name( # var); } while (0)
00232 
00242 #define SH_DECL(var) var; var.name( # var ); ::SH::ShIgnore() & var
00243 
00252 #define SH_NAMEDECL(var, varName) var; var.name( varName ); ::SH::ShIgnore() & var
00253 
00254 
00255 namespace SH {
00256 
00258 SH_DLLEXPORT
00259 bool shProcessArg(const ShVariable& arg, bool* internal_cond);
00260 
00262 SH_DLLEXPORT
00263 bool shPushArg();
00264 
00266 SH_DLLEXPORT
00267 bool shPushArgQueue();
00268 
00270 SH_DLLEXPORT
00271 bool shEvaluateCondition(const ShVariable& arg);
00272 
00274 SH_DLLEXPORT
00275 ShProgram shBeginShader(const std::string& kind = "");
00277 SH_DLLEXPORT
00278 void shEndShader();
00279 
00281 SH_DLLEXPORT
00282 void shCompile(ShProgram& prg);
00284 SH_DLLEXPORT
00285 void shCompile(ShProgram& prg, const std::string& target);
00286 
00288 SH_DLLEXPORT
00289 void shCompileShader(ShProgram& prg);
00291 SH_DLLEXPORT
00292 void shCompileShader(ShProgram& prg, const std::string& target);
00293 
00295 SH_DLLEXPORT
00296 void shBind(ShProgram& prg);
00298 SH_DLLEXPORT
00299 void shBind(const std::string& target, ShProgram& shader);
00300 
00302 SH_DLLEXPORT
00303 void shBindShader(ShProgram& shader);
00305 SH_DLLEXPORT
00306 void shBindShader(const std::string& target, ShProgram& shader);
00307 
00309 SH_DLLEXPORT
00310 void shBind(const ShProgramSet& s);
00311 
00313 SH_DLLEXPORT
00314 void shUnbind();
00315 
00317 SH_DLLEXPORT
00318 void shUnbind(ShProgram& prg);
00320 SH_DLLEXPORT
00321 void shUnbind(const std::string& target, ShProgram& shader);
00322 
00324 SH_DLLEXPORT
00325 void shUnbind(const ShProgramSet& s);
00326 
00328 SH_DLLEXPORT
00329 void shLink(const ShProgramSet& s);
00330 
00334 SH_DLLEXPORT
00335 void shUpdate();
00336 
00338 SH_DLLEXPORT
00339 bool shSetBackend(const std::string& name);
00340 
00342 SH_DLLEXPORT
00343 bool shUseBackend(const std::string& name);
00344 
00346 SH_DLLEXPORT
00347 bool shHaveBackend(const std::string& name);
00348 
00350 SH_DLLEXPORT
00351 void shClearBackends();
00352 
00354 SH_DLLEXPORT
00355 std::string shFindBackend(const std::string& target);
00356 
00362 SH_DLLEXPORT
00363 void shInit();
00364 
00366 SH_DLLEXPORT
00367 void shIf(bool);
00369 SH_DLLEXPORT
00370 void shElse();
00372 SH_DLLEXPORT
00373 void shEndIf();
00374 
00376 SH_DLLEXPORT
00377 void shWhile(bool);
00379 SH_DLLEXPORT
00380 void shEndWhile();
00381 
00383 SH_DLLEXPORT
00384 void shDo();
00386 SH_DLLEXPORT
00387 void shUntil(bool);
00388 
00390 SH_DLLEXPORT
00391 void shFor(bool);
00393 SH_DLLEXPORT
00394 void shEndFor();
00395 
00397 SH_DLLEXPORT
00398 void shBreak(bool);
00400 SH_DLLEXPORT
00401 void shContinue(bool);
00402 
00404 SH_DLLEXPORT
00405 void shBeginSection();
00407 SH_DLLEXPORT
00408 void shEndSection();
00409 
00412 SH_DLLEXPORT
00413 void shComment(const std::string& comment);
00414 
00415 }
00416 
00417 #endif

Generated on Wed Nov 9 15:29:40 2005 for Sh by  doxygen 1.4.5