1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/templates/progops.c Mon Oct 24 21:18:10 2016 +0200
1.3 @@ -0,0 +1,122 @@
1.4 +/* Operations depending on program specifics.
1.5 +*/
1.6 +
1.7 +#include <stdlib.h>
1.8 +#include "types.h"
1.9 +#include "ops.h"
1.10 +#include "progconsts.h"
1.11 +#include "progops.h"
1.12 +#include "progtypes.h"
1.13 +#include <stdio.h>
1.14 +
1.15 +/* Generic instantiation operations, defining common members. */
1.16 +
1.17 +__attr __new(const __table * table, __ref cls, int size)
1.18 +{
1.19 + __ref obj = calloc(1, size);
1.20 + __attr self = {obj, obj};
1.21 + __attr tmp = {0, cls};
1.22 + obj->table = table;
1.23 + __store_via_object(obj, __pos___class__, tmp);
1.24 + return self;
1.25 +}
1.26 +
1.27 +/* Generic invocation operations. */
1.28 +
1.29 +/* Invoke the given callable, supplying keyword argument details in the given
1.30 + codes and arguments arrays, indicating the number of arguments described.
1.31 + The number of positional arguments is specified, and such arguments then
1.32 + follow as conventional function arguments. Typically, at least one argument
1.33 + is specified, starting with any context argument.
1.34 +*/
1.35 +
1.36 +__attr __invoke(__attr callable,
1.37 + unsigned int nkwargs, __param kwcodes[], __attr kwargs[],
1.38 + unsigned int nargs, __attr args[])
1.39 +{
1.40 + /* Obtain the __args__ special member, referencing the parameter table. */
1.41 +
1.42 + __attr minparams = __load_via_object(callable.value, __pos___args__);
1.43 +
1.44 + /* Refer to the table and minimum/maximum. */
1.45 +
1.46 + const __ptable *ptable = minparams.ptable;
1.47 + const unsigned int min = minparams.min, max = ptable->size;
1.48 +
1.49 + /* Reserve enough space for the arguments. */
1.50 +
1.51 + __attr allargs[max];
1.52 +
1.53 + /* Traverse the arguments. */
1.54 +
1.55 + unsigned int pos, kwpos;
1.56 +
1.57 + /* Check the number of arguments. */
1.58 +
1.59 + if ((min > (nargs + nkwargs)) || ((nargs + nkwargs) > max))
1.60 + return null;
1.61 +
1.62 + /* Copy the arguments. */
1.63 +
1.64 + for (pos = 0; pos < nargs; pos++)
1.65 + allargs[pos] = args[pos];
1.66 +
1.67 + /* Erase the remaining arguments. */
1.68 +
1.69 + for (pos = nargs; pos < max; pos++)
1.70 + {
1.71 + allargs[pos].value = 0;
1.72 + }
1.73 +
1.74 + /* Fill keyword arguments. */
1.75 +
1.76 + for (kwpos = 0; kwpos < nkwargs; kwpos++)
1.77 + {
1.78 + pos = __HASPARAM(ptable, kwcodes[kwpos].pos, kwcodes[kwpos].code);
1.79 +
1.80 + /* Check the table entry against the supplied argument details.
1.81 + Set the argument but only if it does not overwrite positional
1.82 + arguments. */
1.83 +
1.84 + if ((pos == -1) || (pos < nargs))
1.85 + return null;
1.86 +
1.87 + /* Set the argument using the appropriate position. */
1.88 +
1.89 + allargs[pos] = kwargs[kwpos];
1.90 + }
1.91 +
1.92 + /* Fill the defaults. */
1.93 +
1.94 + for (pos = nargs; pos < max; pos++)
1.95 + {
1.96 + if (allargs[pos].value == 0)
1.97 + allargs[pos] = __GETDEFAULT(callable.value, pos - nargs);
1.98 + }
1.99 +
1.100 + /* Call with the prepared arguments. */
1.101 +
1.102 + return __load_via_object(callable.value, __pos___fn__).fn(allargs);
1.103 +}
1.104 +
1.105 +/* Error routines. */
1.106 +
1.107 +__attr __unbound_method(__attr args[])
1.108 +{
1.109 + /* NOTE: Should raise an exception. */
1.110 +
1.111 + fprintf(stderr, "Unbound method called!\n");
1.112 + exit(1);
1.113 +}
1.114 +
1.115 +/* Generic operations depending on specific program details. */
1.116 +
1.117 +void __SETDEFAULT(__ref obj, int pos, __attr value)
1.118 +{
1.119 + __store_via_object(obj, __FUNCTION_INSTANCE_SIZE + pos, value);
1.120 +}
1.121 +
1.122 +__attr __GETDEFAULT(__ref obj, int pos)
1.123 +{
1.124 + return __load_via_object(obj, __FUNCTION_INSTANCE_SIZE + pos);
1.125 +}