flx_rtl.hpp

00001 #line 473 "./lpsrc/flx_rtl.pak"
00002 #ifndef __FLX_RTL_H__
00003 #define __FLX_RTL_H__
00004 #include "flx_rtl_config.hpp"
00005 #include "flx_meta.hpp"
00006 #include "flx_gc.hpp"
00007 #include <string>
00008 #include <functional>
00009 
00010 #if FLX_PTF_STATIC_STRUCT
00011 #define PTF ptf.
00012 #elif FLX_PTF_STATIC_POINTER
00013 #define PTF ptf->
00014 #else
00015 #define PTF ptf->
00016 #endif
00017 
00018 // for declarations in header file
00019 #if FLX_PTF_STATIC_STRUCT
00020 #define FLX_FMEM_DECL
00021 #define FLX_FPAR_DECL_ONLY
00022 #define FLX_FPAR_DECL
00023 #define FLX_APAR_DECL_ONLY
00024 #define FLX_APAR_DECL
00025 #define FLX_DCL_THREAD_FRAME extern thread_frame_t ptf;
00026 #elif FLX_PTF_STATIC_POINTER
00027 #define FLX_FMEM_DECL
00028 #define FLX_FPAR_DECL_ONLY
00029 #define FLX_FPAR_DECL
00030 #define FLX_APAR_DECL_ONLY
00031 #define FLX_APAR_DECL
00032 #define FLX_DCL_THREAD_FRAME extern thread_frame_t *ptf;
00033 #else
00034 #define FLX_FMEM_DECL thread_frame_t *ptf;
00035 #define FLX_FPAR_DECL_ONLY thread_frame_t *_ptf
00036 #define FLX_FPAR_DECL thread_frame_t *_ptf,
00037 #define FLX_APAR_DECL_ONLY thread_frame_t *ptf
00038 #define FLX_APAR_DECL thread_frame_t *ptf,
00039 #define FLX_DCL_THREAD_FRAME
00040 #endif
00041 
00042 #if FLX_CGOTO
00043   #define FLX_PC_DECL void *pc;
00044 #else
00045   #define FLX_PC_DECL int pc;
00046 #endif
00047 
00048 
00049 namespace flx { namespace rtl {
00050 
00051 // ********************************************************
00052 // Felix system classes
00053 // ********************************************************
00054 
00055 struct RTL_EXTERN con_t;     // continuation
00056 struct RTL_EXTERN thread_t; // f-thread
00057 struct RTL_EXTERN _ref_;     // pointer/reference
00058 struct RTL_EXTERN _uctor_;   // union constructor
00059 struct RTL_EXTERN schannel_t;   // synchronous channel type
00060 struct RTL_EXTERN slist_t;   // singly linked list of void*
00061 struct RTL_EXTERN _root_ptr_t;   // singly linked list of void*
00062 
00063 struct RTL_EXTERN unit {};   // unit
00064   // INLINE DEFINITION, PROBLEMATIC!!
00065 
00066 // ********************************************************
00067 // Shape (RTTI) objects for system classes
00068 // con_t is only an abstract base, so has no fixed shape
00069 // shapes for instance types generated by Felix compiler
00070 // we provide a shape for C 'int' type as well
00071 // ********************************************************
00072 
00073 RTL_EXTERN extern flx::gc::generic::gc_shape_t _fthread_ptr_map;
00074 RTL_EXTERN extern flx::gc::generic::gc_shape_t schannel_ptr_map;
00075 RTL_EXTERN extern flx::gc::generic::gc_shape_t _ref_ptr_map;
00076 RTL_EXTERN extern flx::gc::generic::gc_shape_t _uctor_ptr_map;
00077 RTL_EXTERN extern flx::gc::generic::gc_shape_t _int_ptr_map;
00078 RTL_EXTERN extern flx::gc::generic::gc_shape_t unit_ptr_map;
00079 RTL_EXTERN extern flx::gc::generic::gc_shape_t slist_ptr_map;
00080 RTL_EXTERN extern flx::gc::generic::gc_shape_t _root_ptr_ptr_map;
00081 
00082 // ********************************************************
00083 // Standard C++ Exceptions
00084 // ********************************************************
00085 
00086 struct RTL_EXTERN flx_exception_t;
00087 struct RTL_EXTERN flx_exec_failure_t;
00088 struct RTL_EXTERN flx_range_srcref_t;
00089 struct RTL_EXTERN flx_match_failure_t;
00090 struct RTL_EXTERN flx_assert_failure_t;
00091 struct RTL_EXTERN flx_assert2_failure_t;
00092 struct RTL_EXTERN flx_switch_failure_t;
00093 // ********************************************************
00094 /// CONTINUATION.
00095 // ********************************************************
00096 
00097 struct RTL_EXTERN con_t ///< abstract base for mutable continuations
00098 {
00099   FLX_PC_DECL               ///< interior program counter
00100   _uctor_ *p_svc;           ///< pointer to service request
00101 
00102   con_t();                  ///< initialise pc, p_svc to 0
00103   virtual con_t *resume()=0;///< method to perform a computational step
00104   virtual ~con_t();
00105   con_t * _caller;          ///< callers continuation (return address)
00106 };
00107 
00108 // ********************************************************
00109 /// SLIST. singly linked lists: SHARABLE and COPYABLE
00110 /// SLIST manages pointers to memory managed by the collector
00111 // ********************************************************
00112 
00113 struct RTL_EXTERN slist_t {
00114   gc::generic::collector_t *gc;
00115   struct slist_node_t *head;
00116 
00117   slist_t (gc::generic::collector_t *); ///< create empty list
00118   slist_t (slist_t const &);            ///< shallow copy
00119 
00120   void push(void *data);                ///< push a gc pointer
00121   void *pop();                          ///< pop a gc pointer
00122   bool isempty()const;
00123 };
00124 
00125 // ********************************************************
00126 /// FTHREAD. Felix threads
00127 // ********************************************************
00128 
00129 struct RTL_EXTERN fthread_t // fthread abstraction
00130 {
00131   con_t *cc;                    ///< current continuation
00132 
00133   fthread_t();                  ///< dead thread, suitable for assignment
00134   fthread_t(con_t*);            ///< make thread from a continuation
00135   _uctor_ *run();               ///< run until dead or driver service request
00136   void kill();                  ///< kill by detaching the continuation
00137   _uctor_ *get_svc()const;      ///< get current service request of waiting thread
00138 private: // uncopyable
00139   fthread_t(fthread_t const&);
00140   void operator=(fthread_t const&);
00141 };
00142 
00143 // ********************************************************
00144 /// SCHANNEL. Synchronous channels
00145 // ********************************************************
00146 
00147 struct RTL_EXTERN schannel_t
00148 {
00149   slist_t *waiting_to_read;             ///< fthreads waiting for a writer
00150   slist_t *waiting_to_write;            ///< fthreads waiting for a reader
00151   schannel_t(gc::generic::collector_t*);
00152   void push_reader(fthread_t *);        ///< add a reader
00153   fthread_t *pop_reader();              ///< pop a reader, NULL if none
00154   void push_writer(fthread_t *);        ///< add a writer
00155   fthread_t *pop_writer();              ///< pop a writer, NULL if none
00156 private: // uncopyable
00157   schannel_t(schannel_t const&);
00158   void operator= (schannel_t const&);
00159 };
00160 
00161 // ********************************************************
00162 /// REFERENCE. Felix pointer type
00163 /// note: non-polymorphic, so ctor can be inline
00164 /// This type is used to represent pointers to variables.
00165 /// It has two components: a frame pointer and offset.
00166 /// A whole frame is refered to by setting the offset to 0.
00167 /// A non-collectable pointer is refered to by setting the frame to 0
00168 /// References are first class values: they can copied, assigned,
00169 /// and default constructed. Holding a reference in a location
00170 /// known to the gc ensures the target variable is not collected:
00171 /// Such references cannot dangle.
00172 /// The frame/offset representation was chosen since it fits
00173 /// well with a copying collector: the price is that finding
00174 /// the interior pointer requires adding the offset to the frame
00175 /// pointer. Note that 'frame' points to the CLIENTDATA address
00176 /// of a frame where user data starts: this is not the lowest
00177 /// machine address of the frame's allocated memory or FRAME
00178 /// address, despite the name.
00179 // ********************************************************
00180 
00181 struct RTL_EXTERN _ref_
00182 {
00183   void *frame;      ///< Heap frame pointer
00184   std::ptrdiff_t offset;   ///< Client Data offset
00185 
00186   _ref_() : frame(0),offset(0) {} ///< NULL reference
00187   _ref_(void *f, void *d):
00188     frame(f), offset((unsigned char*)d-(unsigned char*)f) {}
00189       ///< init from interior pointer d of a collectable frame f
00190 
00191   _ref_(void *f, std::ptrdiff_t d):
00192     frame(f), offset(d) {} ///< init from collectable frame f and offset d
00193 
00194   _ref_(_ref_ const& r) : frame(r.frame), offset(r.offset) {}
00195     ///< copy constructor
00196 
00197   void operator = (_ref_ const& r); ///< assignment operator
00198 
00199   void *get_data()const { return (unsigned char*)frame + offset; }
00200     ///< get interior pointer
00201 
00202   void set_data(void *p)
00203     { offset = (unsigned char*)p - (unsigned char*)frame; }
00204     ///< set interior pointer into same frame
00205 
00206   void set(void *f, void *p)
00207   { frame = f; offset = (unsigned char*)p - (unsigned char*)f; } ///< set from frame f and interior pointer
00208 
00209   bool operator==(_ref_ x) const  ///< compare equal
00210   { return frame==x.frame && offset==x.offset; }
00211 
00212   bool operator!=(_ref_ x) const  ///< compare inequal
00213   { return frame!=x.frame || offset!=x.offset; }
00214 };
00215 
00216 
00217 // ********************************************************
00218 /// VARIANTS. Felix union type
00219 /// note: non-polymorphic, so ctor can be inline
00220 // ********************************************************
00221 
00222 struct RTL_EXTERN _uctor_
00223 {
00224   int variant;  ///< Variant code
00225   void *data;   ///< Heap variant constructor data
00226   _uctor_() : variant(-1), data(0) {}
00227   _uctor_(int i, void *d) : variant(i), data(d) {}
00228   _uctor_(int *a, _uctor_ x) : variant(a[x.variant]), data(x.data) {}
00229 };
00230 
00231 // ********************************************************
00232 /// ROOT POINTER.
00233 /// Use to chain pseudo roots together. Generally scannable
00234 /// but not collectable.
00235 // ********************************************************
00236 
00237 struct RTL_EXTERN _root_ptr_t
00238 {
00239   _root_ptr_t();
00240   _root_ptr_t(void *x);
00241   _root_ptr_t(_root_ptr_t const&);
00242   void operator=(_root_ptr_t const&);
00243   ~_root_ptr_t();
00244 
00245   _root_ptr_t *next;
00246   _root_ptr_t *prev;
00247   void *data;
00248 
00249 private:
00250   void insert_after (_root_ptr_t*);
00251   void erase();
00252 };
00253 
00254 // INLINE! All casts
00255 template<class T>
00256 struct root_ptr_t : _root_ptr_t {
00257   root_ptr_t(){}
00258   root_ptr_t(root_ptr_t<T> const&){}
00259   root_ptr_t<T>& operator=(root_ptr_t<T> const &a){
00260     return reinterpret_cast<root_ptr_t<T>&>(_root_ptr_t::operator=(a));
00261   }
00262  ~root_ptr_t(){}
00263 
00264   root_ptr_t(T const *a) : _root_ptr_t (const_cast<T*>(a)) {}
00265 
00266   T *operator->() { return (T*)data; }
00267   T const *operator->() const { return (T const*)data; }
00268   T &operator*() { return *(T*)data; }
00269   T const &operator*() const { return *(T const*)data; }
00270 };
00271 
00272 template<class T>
00273 bool operator == (root_ptr_t<T> a, root_ptr_t<T> b)
00274 {
00275   return a-> data == b->data;
00276 }
00277 
00278 template<class T>
00279 bool operator != (root_ptr_t<T> a, root_ptr_t<T> b)
00280 {
00281   return a-> data != b->data;
00282 }
00283 
00284 template<class T>
00285 bool operator < (root_ptr_t<T> const &a, root_ptr_t<T> const &b)
00286 {
00287   // we use this because it enforces a total order
00288   return std::less<void const*>()(a-> data, b->data);
00289 }
00290 
00291 template<class T>
00292 bool operator <= (root_ptr_t<T> const &a, root_ptr_t<T> const &b)
00293 {
00294   // we use this because it enforces a total order
00295   return std::less_equal<void const*>()(a-> data, b->data);
00296 }
00297 
00298 template<class T>
00299 bool operator > (root_ptr_t<T> const &a, root_ptr_t<T> const &b)
00300 {
00301   // we use this because it enforces a total order
00302   return std::greater<void const*>()(a-> data, b->data);
00303 }
00304 
00305 template<class T>
00306 bool operator >= (root_ptr_t<T> const &a, root_ptr_t<T> const &b)
00307 {
00308   // we use this because it enforces a total order
00309   return std::greater_equal<void const*>()(a-> data, b->data);
00310 }
00311 
00312 
00313 // ********************************************************
00314 /// EXCEPTION: Felix exception base abstraction.
00315 /// Mainly used to convert catches into subroutine
00316 /// calls which then dispatch on RTTI manually.
00317 // ********************************************************
00318 
00319 struct RTL_EXTERN flx_exception_t {
00320   virtual ~flx_exception_t()=0;
00321 };
00322 
00323 // ********************************************************
00324 /// EXCEPTION: EXEC protocol failure.
00325 /// Thrown when trying to run a dead procedure
00326 // ********************************************************
00327 
00328 struct RTL_EXTERN flx_exec_failure_t : flx_exception_t {
00329   std::string filename;  ///< dll filename
00330   std::string operation; ///< faulty operation
00331   std::string what;      ///< error description
00332   flx_exec_failure_t(std::string f, std::string o, std::string w);
00333   virtual ~flx_exec_failure_t();
00334 };
00335 
00336 // ********************************************************
00337 /// SOURCE REFERENCE: to track places in user source code.
00338 // ********************************************************
00339 
00340 struct RTL_EXTERN flx_range_srcref_t {
00341   char *filename;  ///< source file name
00342   int startline;   ///< first line (1 origin)
00343   int startcol;    ///< first column (1 origin)
00344   int endline;     ///< last line
00345   int endcol;      ///< last column
00346   flx_range_srcref_t(char *f,int sl, int sc, int el, int ec);
00347   flx_range_srcref_t();
00348 };
00349 
00350 // ********************************************************
00351 /// EXCEPTION: HALT.
00352 /// Thrown by halt command
00353 // ********************************************************
00354 
00355 struct RTL_EXTERN flx_halt_t : flx_exception_t {
00356   std::string reason;         ///< halt argument
00357   flx_range_srcref_t flx_loc; ///< location in Felix file
00358   char *cxx_srcfile;          ///< C++ file name
00359   int cxx_srcline;            ///< C++ line number
00360   flx_halt_t(flx_range_srcref_t ff, char *cf, int cl, std::string reason);
00361   virtual ~flx_halt_t();
00362 };
00363 
00364 // ********************************************************
00365 /// EXCEPTION: MATCH failure.
00366 /// Thrown when no match cases match the argument of a match,
00367 /// regmatch, or reglex
00368 // ********************************************************
00369 
00370 struct RTL_EXTERN flx_match_failure_t : flx_exception_t {
00371   flx_range_srcref_t flx_loc; ///< location in Felix file
00372   char *cxx_srcfile;          ///< C++ file name
00373   int cxx_srcline;            ///< C++ line number
00374   flx_match_failure_t(flx_range_srcref_t ff, char *cf, int cl);
00375   virtual ~flx_match_failure_t();
00376 };
00377 
00378 // ********************************************************
00379 /// EXCEPTION: ASSERT failure.
00380 /// Thrown when user assertion fails
00381 // ********************************************************
00382 
00383 struct RTL_EXTERN flx_assert_failure_t : flx_exception_t {
00384   flx_range_srcref_t flx_loc; ///< location in Felix file
00385   char *cxx_srcfile;          ///< C++ file
00386   int cxx_srcline;            ///< __LINE__ macro
00387   flx_assert_failure_t(flx_range_srcref_t ff, char *cf, int cl);
00388   virtual ~flx_assert_failure_t();
00389 };
00390 
00391 struct RTL_EXTERN flx_assert2_failure_t : flx_exception_t {
00392   flx_range_srcref_t flx_loc; ///< location in Felix file
00393   flx_range_srcref_t flx_loc2; ///< second location in Felix file
00394   char *cxx_srcfile;          ///< C++ file
00395   int cxx_srcline;            ///< __LINE__ macro
00396   flx_assert2_failure_t(flx_range_srcref_t ff, flx_range_srcref_t ff2, char *cf, int cl);
00397   virtual ~flx_assert2_failure_t();
00398 };
00399 
00400 // ********************************************************
00401 /// EXCEPTION: RANGE failure.
00402 /// Thrown when a range check fails
00403 // ********************************************************
00404 
00405 struct RTL_EXTERN flx_range_failure_t : flx_exception_t {
00406   flx_range_srcref_t flx_loc; ///< location in Felix file
00407   char *cxx_srcfile;          ///< C++ file
00408   int cxx_srcline;            ///< __LINE__ macro
00409   flx_range_failure_t(flx_range_srcref_t ff, char *cf, int cl);
00410   virtual ~flx_range_failure_t();
00411 };
00412 
00413 RTL_EXTERN long range_check (long l, long x, long h, flx_range_srcref_t sref, char *cf, int cl);
00414 
00415 
00416 // ********************************************************
00417 /// EXCEPTION: SWITCH failure. this is a system failure!
00418 // ********************************************************
00419 
00420 struct RTL_EXTERN flx_switch_failure_t : flx_exception_t {
00421   virtual ~flx_switch_failure_t();
00422 };
00423 
00424 
00425 // ********************************************************
00426 // SERVICE REQUEST CODE
00427 // THESE VALUES MUST SYNCH WITH THE STANDARD LIBRARY
00428 // ********************************************************
00429 
00430 enum svc_t               // what the dispatch should do
00431 {                        // when the resume callback returns
00432   svc_yield = 0,
00433   svc_get_fthread=1,
00434   svc_read=2,
00435   svc_general=3,         // temporary hack by RF
00436   svc_reserved=4,
00437   svc_spawn_pthread=5,
00438   svc_spawn_detached=6,
00439   svc_sread=7,           // synchronous read
00440   svc_swrite=8,          // synchronous write
00441   svc_kill=9,           // kill fthread
00442   svc_compact=10,        // run compactor
00443   svc_collect=11,        // run collector
00444   svc_collect_and_compact=12,        // run collector and compactor
00445   svc_end
00446 };
00447 
00448 struct readreq_t {
00449   schannel_t *chan;
00450   _ref_ variable;
00451 };
00452 
00453 }} // namespaces
00454 
00455 #define FLX_EXEC_FAILURE(f,op,what) \
00456   throw flx::rtl::flx_exec_failure_t (f,op,what)
00457 
00458 #define FLX_HALT(f,sl,sc,el,ec,s) \
00459   throw flx::rtl::flx_halt_t (flx_range_srcref_t(f,sl,sc,el,ec),__FILE__,__LINE__,s)
00460 
00461 #define FLX_MATCH_FAILURE(f,sl,sc,el,ec) \
00462   throw flx::rtl::flx_match_failure_t (flx_range_srcref_t(f,sl,sc,el,ec),__FILE__,__LINE__)
00463 
00464 #define FLX_ASSERT_FAILURE(f,sl,sc,el,ec) \
00465   throw flx::rtl::flx_assert_failure_t (flx_range_srcref_t(f,sl,sc,el,ec),__FILE__,__LINE__)
00466 
00467 #define FLX_ASSERT2_FAILURE(f,sl,sc,el,ec,f2,sl2,sc2,el2,ec2) \
00468   throw flx::rtl::flx_assert2_failure_t (\
00469     flx_range_srcref_t(f,sl,sc,el,ec),\
00470     flx_range_srcref_t(f2,sl2,sc2,el2,sc2),\
00471     __FILE__,__LINE__)
00472 
00473 #define FLX_RANGE_FAILURE(f,sl,sc,el,ec) \
00474   throw flx::rtl::flx_range_failure_t (flx_range_srcref_t(f,sl,sc,el,ec),__FILE__,__LINE__)
00475 
00476 // for generated code in body file
00477 #define INIT_PC pc=0;
00478     ///< interior program counter
00479 
00480 #if FLX_CGOTO
00481   #define FLX_START_SWITCH if(pc)goto *pc;
00482   #define FLX_SET_PC(x) pc=&&case_##x;
00483   #define FLX_CASE_LABEL(x) case_##x:;
00484   #define FLX_DECLARE_LABEL(n,i,x) \
00485     extern void f##i##_##n##_##x(void) __asm__("l"#i"_"#n"_"#x);
00486   #define FLX_LABEL(n,i,x) x:\
00487     __asm__(".global l"#i"_"#n"_"#x);\
00488     __asm__("l"#i"_"#n"_"#x":");\
00489     __asm__(""::"g"(&&x));
00490   #define FLX_FARTARGET(n,i,x) (void*)&f##i##_##n##_##x
00491   #define FLX_END_SWITCH
00492 #else
00493   #define FLX_START_SWITCH switch(pc){case 0:;
00494   #define FLX_SET_PC(x) pc=x;
00495   #define FLX_CASE_LABEL(x) case x:;
00496   #define FLX_DECLARE_LABEL(n,i,x)
00497   #define FLX_LABEL(n,i,x) case n: x:;
00498   #define FLX_FARTARGET(n,i,x) n
00499   #define FLX_END_SWITCH default: throw flx_switch_failure_t(); }
00500 #endif
00501 
00502 #define FLX_RETURN \
00503 { \
00504   con_t *tmp = _caller; \
00505   _caller = 0; \
00506   return tmp; \
00507 }
00508 
00509 #define FLX_NEWP(x) new(*PTF gc,x##_ptr_map)x
00510 
00511 #define FLX_FINALISER(x) \
00512 static void x##_finaliser(collector_t *, void *p){\
00513   ((x*)p)->~x();\
00514 }
00515 
00516 #if FLX_USE_REGPARM3 && FLX_HAVE_GNU_X86
00517 #define FLX_REGPARM __attribute__((regparm(3)))
00518 #else
00519 #define FLX_REGPARM
00520 #endif
00521 
00522 #if FLX_PTF_STATIC_STRUCT
00523 #define FLX_FMEM_INIT_ONLY
00524 #define FLX_FMEM_INIT :
00525 #define FLX_FPAR_PASS_ONLY
00526 #define FLX_FPAR_PASS
00527 #define FLX_APAR_PASS_ONLY
00528 #define FLX_APAR_PASS
00529 #define _PTF _ptf.
00530 #define _PTFV
00531 #define FLX_PASS_PTF 0
00532 #define FLX_EAT_PTF(x)
00533 #define FLX_DEF_THREAD_FRAME thread_frame_t ptf;
00534 #elif FLX_PTF_STATIC_POINTER
00535 #define FLX_FMEM_INIT_ONLY
00536 #define FLX_FMEM_INIT :
00537 #define FLX_FPAR_PASS_ONLY
00538 #define FLX_FPAR_PASS
00539 #define FLX_APAR_PASS_ONLY
00540 #define FLX_APAR_PASS
00541 #define _PTF _ptf->
00542 #define _PTFV
00543 #define FLX_PASS_PTF 0
00544 #define FLX_EAT
00545 #define FLX_DEF_THREAD_FRAME thread_frame_t *ptf=0;
00546 #else
00547 #define FLX_FMEM_INIT_ONLY : ptf(_ptf)
00548 #define FLX_FMEM_INIT : ptf(_ptf),
00549 #define FLX_FPAR_PASS_ONLY ptf
00550 #define FLX_FPAR_PASS ptf,
00551 #define FLX_APAR_PASS_ONLY _ptf
00552 #define FLX_APAR_PASS _ptf,
00553 #define _PTF _ptf->
00554 #define _PTFV _ptf
00555 #define FLX_PASS_PTF 1
00556 #define FLX_EAT_PTF(x) x
00557 #define FLX_DEF_THREAD_FRAME
00558 #endif
00559 
00560 #if FLX_PTF_STATIC_STRUCT
00561 #define FLX_FRAME_WRAPPERS(mname) \
00562 extern "C" thread_frame_t *create_thread_frame(\
00563   collector_t *gc\
00564 ) {\
00565   ptf.gc = gc;\
00566   return &ptf;\
00567 }
00568 #elif FLX_PTF_STATIC_POINTER
00569 #define FLX_FRAME_WRAPPERS(mname) \
00570 extern "C" thread_frame_t *create_thread_frame(\
00571   collector_t *gc\
00572 ) {\
00573   mname::thread_frame_t *p = new(*gc,mname::thread_frame_t_ptr_map) mname::thread_frame_t(gc);\
00574   ptf = p;\
00575   return p;\
00576 }
00577 #else
00578 #define FLX_FRAME_WRAPPERS(mname) \
00579 extern "C" FLX_EXPORT mname::thread_frame_t *create_thread_frame(\
00580   collector_t *gc\
00581 ) {\
00582   mname::thread_frame_t *p = new(*gc,mname::thread_frame_t_ptr_map) mname::thread_frame_t(gc);\
00583   return p;\
00584 }
00585 #endif
00586 
00587 #if FLX_PTF_STATIC_STRUCT
00588 #define FLX_START_WRAPPER(mname,x)\
00589 extern "C" con_t *flx_start(\
00590   mname::thread_frame_t *ptf,\
00591   int argc,\
00592   char **argv,\
00593   FILE *stdin_,\
00594   FILE *stdout_,\
00595   FILE *stderr_\
00596 ) {\
00597   ptf->argc = argc;\
00598   ptf->argv = argv;\
00599   ptf->flx_stdin = stdin_;\
00600   ptf->flx_stdout = stdout_;\
00601   ptf->flx_stderr = stderr_;\
00602   return (new(*ptf->gc,mname::x##_ptr_map) \
00603     mname::x()) ->call(0);\
00604 }
00605 #elif FLX_PTF_STATIC_POINTER
00606 #define FLX_START_WRAPPER(mname,x)\
00607 extern "C" con_t *flx_start(\
00608   mname::thread_frame_t *ptf,\
00609   int argc,\
00610   char **argv,\
00611   FILE *stdin_,\
00612   FILE *stdout_,\
00613   FILE *stderr_\
00614 ) {\
00615   ptf->argc = argc;\
00616   ptf->argv = argv;\
00617   ptf->flx_stdin = stdin_;\
00618   ptf->flx_stdout = stdout_;\
00619   ptf->flx_stderr = stderr_;\
00620   return (new(*ptf->gc,mname::x##_ptr_map) \
00621     mname::x()) ->call(0);\
00622 }
00623 #else
00624 #define FLX_START_WRAPPER(mname,x)\
00625 extern "C" FLX_EXPORT con_t *flx_start(\
00626   mname::thread_frame_t *ptf,\
00627   int argc,\
00628   char **argv,\
00629   FILE *stdin_,\
00630   FILE *stdout_,\
00631   FILE *stderr_\
00632 ) {\
00633   ptf->argc = argc;\
00634   ptf->argv = argv;\
00635   ptf->flx_stdin = stdin_;\
00636   ptf->flx_stdout = stdout_;\
00637   ptf->flx_stderr = stderr_;\
00638   return (new(*ptf->gc,mname::x##_ptr_map) \
00639     mname::x(ptf)) ->call(0);\
00640 }
00641 #endif
00642 
00643 #if FLX_PTF_STATIC_STRUCT
00644 #define FLX_STACK_START_WRAPPER(mname,x)\
00645 extern "C" con_t *flx_start(\
00646   mname::thread_frame_t *ptf,\
00647   int argc,\
00648   char **argv,\
00649   FILE *stdin_,\
00650   FILE *stdout_,\
00651   FILE *stderr_\
00652 ) {\
00653   ptf->argc = argc;\
00654   ptf->argv = argv;\
00655   ptf->flx_stdin = stdin_;\
00656   ptf->flx_stdout = stdout_;\
00657   ptf->flx_stderr = stderr_;\
00658   mname::x().stack_call();\
00659   return 0;\
00660 }
00661 #elif FLX_PTF_STATIC_POINTER
00662 #define FLX_STACK_START_WRAPPER(mname,x)\
00663 extern "C" con_t *flx_start(\
00664   mname::thread_frame_t *ptf,\
00665   int argc,\
00666   char **argv,\
00667   FILE *stdin_,\
00668   FILE *stdout_,\
00669   FILE *stderr_\
00670 ) {\
00671   ptf->argc = argc;\
00672   ptf->argv = argv;\
00673   ptf->flx_stdin = stdin_;\
00674   ptf->flx_stdout = stdout_;\
00675   ptf->flx_stderr = stderr_;\
00676   mname::x().stack_call();\
00677   return 0;\
00678 }
00679 #else
00680 #define FLX_STACK_START_WRAPPER(mname,x)\
00681 extern "C" FLX_EXPORT con_t *flx_start(\
00682   mname::thread_frame_t *ptf,\
00683   int argc,\
00684   char **argv,\
00685   FILE *stdin_,\
00686   FILE *stdout_,\
00687   FILE *stderr_\
00688 ) {\
00689   ptf->argc = argc;\
00690   ptf->argv = argv;\
00691   ptf->flx_stdin = stdin_;\
00692   ptf->flx_stdout = stdout_;\
00693   ptf->flx_stderr = stderr_;\
00694   mname::x(ptf).stack_call();\
00695   return 0;\
00696 }
00697 #endif
00698 
00699 #if FLX_PTF_STATIC_STRUCT
00700 #define FLX_C_START_WRAPPER(mname,x)\
00701 extern "C" con_t *flx_start(\
00702   mname::thread_frame_t *ptf,\
00703   int argc,\
00704   char **argv,\
00705   FILE *stdin_,\
00706   FILE *stdout_,\
00707   FILE *stderr_\
00708 ) {\
00709   ptf->argc = argc;\
00710   ptf->argv = argv;\
00711   ptf->flx_stdin = stdin_;\
00712   ptf->flx_stdout = stdout_;\
00713   ptf->flx_stderr = stderr_;\
00714   mname::x();\
00715   return 0;\
00716 }
00717 #elif FLX_PTF_STATIC_POINTER
00718 #define FLX_C_START_WRAPPER(mname,x)\
00719 extern "C" con_t *flx_start(\
00720   mname::thread_frame_t *ptf,\
00721   int argc,\
00722   char **argv,\
00723   FILE *stdin_,\
00724   FILE *stdout_,\
00725   FILE *stderr_\
00726 ) {\
00727   ptf->argc = argc;\
00728   ptf->argv = argv;\
00729   ptf->flx_stdin = stdin_;\
00730   ptf->flx_stdout = stdout_;\
00731   ptf->flx_stderr = stderr_;\
00732   mname::x();\
00733   return 0;\
00734 }
00735 #else
00736 #define FLX_C_START_WRAPPER(mname,x)\
00737 extern "C" FLX_EXPORT con_t *flx_start(\
00738   mname::thread_frame_t *ptf,\
00739   int argc,\
00740   char **argv,\
00741   FILE *stdin_,\
00742   FILE *stdout_,\
00743   FILE *stderr_\
00744 ) {\
00745   ptf->argc = argc;\
00746   ptf->argv = argv;\
00747   ptf->flx_stdin = stdin_;\
00748   ptf->flx_stdout = stdout_;\
00749   ptf->flx_stderr = stderr_;\
00750   mname::x(ptf);\
00751   return 0;\
00752 }
00753 #endif
00754 
00755 #endif

Generated on Mon Dec 24 04:04:21 2007 for Felix by  doxygen 1.5.4