/[svn]/linuxsampler/trunk/src/scriptvm/common.h
ViewVC logotype

Diff of /linuxsampler/trunk/src/scriptvm/common.h

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 2581 by schoenebeck, Fri May 30 12:48:05 2014 UTC revision 2612 by schoenebeck, Tue Jun 10 13:32:16 2014 UTC
# Line 15  Line 15 
15  #define LS_INSTR_SCRIPT_PARSER_COMMON_H  #define LS_INSTR_SCRIPT_PARSER_COMMON_H
16    
17  #include "../common/global.h"  #include "../common/global.h"
18    #include <vector>
19    #include <map>
20    #include <stddef.h> // offsetof()
21    
22  namespace LinuxSampler {  namespace LinuxSampler {
23            
# Line 45  namespace LinuxSampler { Line 48  namespace LinuxSampler {
48          VM_EXEC_ERROR = (1<<2),          VM_EXEC_ERROR = (1<<2),
49      };      };
50    
51        class VMIntExpr;
52        class VMStringExpr;
53    
54      class VMExpr {      class VMExpr {
55      public:      public:
56          virtual ExprType_t exprType() const = 0;          virtual ExprType_t exprType() const = 0;
57            VMIntExpr* asInt() const;
58            VMStringExpr* asString() const;
59      };      };
60    
61      class VMIntExpr : virtual public VMExpr {      class VMIntExpr : virtual public VMExpr {
# Line 74  namespace LinuxSampler { Line 82  namespace LinuxSampler {
82          virtual StmtFlags_t resultFlags() { return STMT_SUCCESS; }          virtual StmtFlags_t resultFlags() { return STMT_SUCCESS; }
83      };      };
84    
85        /** @brief VM built-in function.
86         *
87         * Abstract base class for built-in script functions, defining the interface
88         * for all built-in script function implementations.
89         */
90      class VMFunction {      class VMFunction {
91      public:      public:
92            /**
93             * Script data type of the function's return value. If the function does
94             * not return any value, then it returns EMPTY_EXPR here.
95             */
96          virtual ExprType_t returnType() = 0;          virtual ExprType_t returnType() = 0;
97    
98            /**
99             * Minimum amount of function arguments this function accepts. If a
100             * script is calling this function with less arguments, the script
101             * parser will throw a parser error.
102             */
103          virtual int minRequiredArgs() const = 0;          virtual int minRequiredArgs() const = 0;
104    
105            /**
106             * Maximum amount of function arguments this functions accepts. If a
107             * script is calling this function with more arguments, the script
108             * parser will throw a parser error.
109             */
110          virtual int maxAllowedArgs() const = 0;          virtual int maxAllowedArgs() const = 0;
111    
112            /**
113             * Script data type of the function's @c iArg 'th function argument.
114             * The information provided here is less strong than acceptsArgType().
115             * The parser will compare argument data types provided in scripts by
116             * calling cceptsArgType(). The return value of argType() is used by the
117             * parser instead to show an appropriate parser error which data type
118             * this function usually expects as "default" data type. Reason: a
119             * function may accept multiple data types for a certain function
120             * argument and would automatically cast the passed argument value in
121             * that case to the type it actually needs.
122             *
123             * @param iArg - index of the function argument in question
124             */
125          virtual ExprType_t argType(int iArg) const = 0;          virtual ExprType_t argType(int iArg) const = 0;
126    
127            /**
128             * This function is called by the parser to check whether arguments
129             * passed in scripts to this function are accepted by this function. If
130             * a script calls this function with an argument's data type not
131             * accepted by this function, the parser will throw a parser error.
132             *
133             * @param iArg - index of the function argument in question
134             * @param type - script data type used for this function argument by
135             *               currently parsed script
136             */
137          virtual bool acceptsArgType(int iArg, ExprType_t type) const = 0;          virtual bool acceptsArgType(int iArg, ExprType_t type) const = 0;
138    
139            /**
140             * Implements the actual function execution. This function is called by
141             * the VM when this function shall be executed at script runtime.
142             *
143             * @param args - function arguments for executing this built-in function
144             */
145          virtual VMFnResult* exec(VMFnArgs* args) = 0;          virtual VMFnResult* exec(VMFnArgs* args) = 0;
146    
147            /**
148             * Concenience method for function implementations to show warning
149             * messages.
150             *
151             * @param txt - warning text
152             */
153            void wrnMsg(const String& txt);
154    
155            /**
156             * Concenience method for function implementations to show error
157             * messages.
158             *
159             * @param txt - error text
160             */
161            void errMsg(const String& txt);
162        };
163    
164        /**
165         * POD base of VMIntRelPtr and VMInt8RelPtr structures. Not intended to be
166         * used directly. Use VMIntRelPtr or VMInt8RelPtr instead.
167         */
168        struct VMRelPtr {
169            void** base; ///< Base pointer.
170            int offset;  ///< Offset (in bytes) to base pointer.
171        };
172    
173        /** @brief Pointer to built-in VM integer variable (of C/C++ type int).
174         *
175         * Used for defining built-in integer script variables.
176         *
177         * @b CAUTION: You may only use this class for pointing to C/C++ variables
178         * of type "int" (which on most systems is 32 bit in size). If the C/C++ int
179         * variable you want to reference is only 8 bit in size, then you @b must
180         * use VMInt8RelPtr instead!
181         *
182         * For efficiency reasons the actual native C/C++ int variable is referenced
183         * by two components here. The actual native int C/C++ variable in memory
184         * is dereferenced at VM run-time by taking the @c base pointer dereference
185         * and adding @c offset bytes. This has the advantage that for a large
186         * number of built-in int variables, only one (or few) base pointer need
187         * to be re-assigned before running a script, instead of updating each
188         * built-in variable each time before a script is executed.
189         *
190         * Refer to DECLARE_VMINT() for example code.
191         *
192         * @see VMInt8RelPtr, DECLARE_VMINT()
193         */
194        struct VMIntRelPtr : VMRelPtr {
195            VMIntRelPtr() {
196                base   = NULL;
197                offset = 0;
198            }
199            VMIntRelPtr(const VMRelPtr& data) {
200                base   = data.base;
201                offset = data.offset;
202            }
203            virtual int evalInt() { return *(int*)&(*(uint8_t**)base)[offset]; }
204            virtual void assign(int i) { *(int*)&(*(uint8_t**)base)[offset] = i; }
205        };
206    
207        /** @brief Pointer to built-in VM integer variable (of C/C++ type int8_t).
208         *
209         * Used for defining built-in integer script variables.
210         *
211         * @b CAUTION: You may only use this class for pointing to C/C++ variables
212         * of type "int8_t" (8 bit integer). If the C/C++ int variable you want to
213         * reference is an "int" type (which is 32 bit on most systems), then you
214         * @b must use VMIntRelPtr instead!
215         *
216         * For efficiency reasons the actual native C/C++ int variable is referenced
217         * by two components here. The actual native int C/C++ variable in memory
218         * is dereferenced at VM run-time by taking the @c base pointer dereference
219         * and adding @c offset bytes. This has the advantage that for a large
220         * number of built-in int variables, only one (or few) base pointer need
221         * to be re-assigned before running a script, instead of updating each
222         * built-in variable each time before a script is executed.
223         *
224         * Refer to DECLARE_VMINT() for example code.
225         *
226         * @see VMIntRelPtr, DECLARE_VMINT()
227         */
228        struct VMInt8RelPtr : VMIntRelPtr {
229            VMInt8RelPtr() : VMIntRelPtr() {}
230            VMInt8RelPtr(const VMRelPtr& data) : VMIntRelPtr(data) {}
231            virtual int evalInt() OVERRIDE {
232                return *(uint8_t*)&(*(uint8_t**)base)[offset];
233            }
234            virtual void assign(int i) OVERRIDE {
235                *(uint8_t*)&(*(uint8_t**)base)[offset] = i;
236            }
237      };      };
238    
239        /**
240         * Convenience macro for initializing VMIntRelPtr and VMInt8RelPtr
241         * structures. Example:
242         * @code
243         * struct Foo {
244         *   uint8_t a;
245         *   int b;
246         * };
247         *
248         * Foo foo1 = (Foo) { 1, 3000 };
249         * Foo foo2 = (Foo) { 2, 4000 };
250         *
251         * Foo* pFoo;
252         *
253         * VMInt8RelPtr var1 = DECLARE_VMINT(pFoo, class Foo, a);
254         * VMIntRelPtr  var2 = DECLARE_VMINT(pFoo, class Foo, b);
255         *
256         * pFoo = &foo1;
257         * printf("%d\n", var1->evalInt()); // will print 1
258         * printf("%d\n", var2->evalInt()); // will print 3000
259         *
260         * pFoo = &foo2;
261         * printf("%d\n", var1->evalInt()); // will print 2
262         * printf("%d\n", var2->evalInt()); // will print 4000
263         * @endcode
264         */
265        #define DECLARE_VMINT(basePtr, T_struct, T_member) ( \
266            (VMRelPtr) {                                     \
267                (void**) &basePtr,                           \
268                offsetof(T_struct, T_member)                 \
269            }                                                \
270        )                                                    \
271    
272        /** @brief Built-in VM 8 bit integer array variable.
273         *
274         * Used for defining built-in integer array script variables.
275         */
276        struct VMInt8Array {
277            int8_t* data;
278            int size;
279    
280            VMInt8Array() : data(NULL), size(0) {}
281        };
282    
283        /** @brief Provider for built-in script functions and variables.
284         *
285         * Abstract base class defining the interface for all classes which add and
286         * implement built-in script functions and built-in script variables.
287         */
288      class VMFunctionProvider {      class VMFunctionProvider {
289      public:      public:
290            /**
291             * Returns pointer to the built-in function with the given function
292             * name, or NULL if there is no built-in function with that name.
293             *
294             * @param name - function name
295             */
296          virtual VMFunction* functionByName(const String& name) = 0;          virtual VMFunction* functionByName(const String& name) = 0;
     };  
       
     class VMParserContext {  
     public:  
         virtual ~VMParserContext() {}  
     };  
297    
298            /**
299             * Returns a variable name indexed map of all built-in script variables
300             * which point to native "int" (usually 32 bit) variables.
301             */
302            virtual std::map<String,VMIntRelPtr*> builtInIntVariables() = 0;
303    
304            /**
305             * Returns a variable name indexed map of all built-in script variables
306             * which point to native "int8_t" (8 bit) variables.
307             */
308            virtual std::map<String,VMInt8Array*> builtInIntArrayVariables() = 0;
309    
310            /**
311             * Returns a variable name indexed map of all built-in constant script
312             * variables, which never change their value at runtime.
313             */
314            virtual std::map<String,int> builtInConstIntVariables() = 0;
315        };
316    
317        /** @brief Execution state of a virtual machine.
318         *
319         * An instance of this abstract base class represents exactly one execution
320         * state of a virtual machine. This encompasses most notably the VM
321         * execution stack, and VM polyphonic variables. It does not contain global
322         * variable. Global variables are contained in the VMParserContext object.
323         * You might see a VMExecContext object as one virtual thread of the virtual
324         * machine.
325         *
326         * In contrast to a VMParserContext, a VMExecContext is not tied to a
327         * ScriptVM instance. Thus you can use a VMExecContext with different
328         * ScriptVM instances, however not concurrently at the same time.
329         *
330         * @see VMParserContext
331         */
332      class VMExecContext {      class VMExecContext {
333      public:      public:
334          virtual ~VMExecContext() {}          virtual ~VMExecContext() {}
# Line 136  namespace LinuxSampler { Line 371  namespace LinuxSampler {
371          return "invalid";          return "invalid";
372      }      }
373    
374        /** @brief Virtual machine representation of a script.
375         *
376         * An instance of this abstract base class represents a parsed script,
377         * translated into a virtual machine. You should first check if there were
378         * any parser errors. If there were any parser errors, you should refrain
379         * from executing the virtual machine. Otherwise if there were no parser
380         * errors (i.e. only warnings), then you might access one of the script's
381         * event handlers by i.e. calling eventHandlerByName() and pass the
382         * respective event handler to the ScriptVM class (or to one of its
383         * descendants) for execution.
384         *
385         * @see VMExecContext
386         */
387        class VMParserContext {
388        public:
389            virtual ~VMParserContext() {}
390            virtual std::vector<ParserIssue> issues() const = 0;
391            virtual std::vector<ParserIssue> errors() const = 0;
392            virtual std::vector<ParserIssue> warnings() const = 0;
393            virtual VMEventHandler* eventHandler(uint index) = 0;
394            virtual VMEventHandler* eventHandlerByName(const String& name) = 0;
395        };
396    
397  } // namespace LinuxSampler  } // namespace LinuxSampler
398    
399  #endif // LS_INSTR_SCRIPT_PARSER_COMMON_H  #endif // LS_INSTR_SCRIPT_PARSER_COMMON_H

Legend:
Removed from v.2581  
changed lines
  Added in v.2612

  ViewVC Help
Powered by ViewVC