/**
 * Run a routine for a thread context API call.
 */
void CallProgramDispatcher::run()
{
    RexxString *targetName = new_string(program);
    /* go resolve the name               */
    RexxString *name = activity->resolveProgramName(targetName, OREF_NULL, OREF_NULL);
    if (name == OREF_NULL)                /* not found?                        */
    {
        /* got an error here                 */
        reportException(Error_Program_unreadable_notfound, targetName);
    }
    ProtectedObject p(name);
    // create a routine from this file
    RoutineClass *routine = RoutineClass::fromFile(name);
    p = routine;

    if (arguments != OREF_NULL)
    {
        size_t argumentsCount = arguments->size();
        RexxArray *argumentsCopy = (RexxArray *)arguments->copy();
        ProtectedObject p(argumentsCopy);
        argumentsCopy->put(IntegerZero, argumentsCount + 1); // Counter of named arguments (Zero). To support correctly omitted positional arguments, don't use append!
        // use the provided name for the call name
        routine->runProgram(activity, argumentsCopy->data(), argumentsCount, result);
    }
    else
    {
        // we use a null string for the name when things are called directly
        routine->runProgram(activity, NULL, 0, result);
    }
}
/**
 * Return the information that needs to be saved in the saved
 * image.
 *
 * @return An array of the items added to the saved image.
 */
RexxArray *PackageManager::getImageData()
{

    RexxArray *imageArray = new_array(IMAGE_ARRAY_SIZE);
    imageArray->put(packages, IMAGE_PACKAGES);
    imageArray->put(packageRoutines, IMAGE_PACKAGE_ROUTINES);
    imageArray->put(registeredRoutines, IMAGE_REGISTERED_ROUTINES);
    imageArray->put(loadedRequires, IMAGE_REQUIRES);

    return imageArray;
}
Exemple #3
0
/**
 * Extract from the method dictionary all methods defined with
 * a given scope.
 *
 * @param scope  The target scope.  If null, then all methods
 *               are returned.
 *
 * @return A supplier holding the names and methods with the target
 *         scope.  This supplier can be empty.
 */
RexxSupplier *RexxBehaviour::getMethods(RexxObject *scope)
{
    // if asking for everything, just return the supplier.
    if (scope == OREF_NULL)
    {
        return this->methodDictionary->supplier();
    }

    size_t count = 0;
    HashLink i;

    // travese the method dictionary, searching for methods with the target scope
    for (i = this->methodDictionary->first(); this->methodDictionary->index(i) != OREF_NULL; i = this->methodDictionary->next(i))
    {
        if (((RexxMethod *)this->methodDictionary->value(i))->getScope() == scope)
        {
            count++;
        }
    }

    RexxArray *names = new_array(count);
    RexxArray *methods = new_array(count);
    count = 1;

    // pass two, copy the entries into the array
    for (i = this->methodDictionary->first(); this->methodDictionary->index(i) != OREF_NULL; i = this->methodDictionary->next(i))
    {
        if (((RexxMethod *)this->methodDictionary->value(i))->getScope() == scope)
        {
            names->put(this->methodDictionary->index(i), count);
            methods->put(this->methodDictionary->value(i), count);
            count++;
        }
    }

    return (RexxSupplier *)new_supplier(methods, names);
}
Exemple #4
0
RexxMethod *RexxBehaviour::superMethod(
    RexxString * messageName,          /* target method name                */
    RexxObject * startScope)           /* starting scope                    */
/******************************************************************************/
/* Function:   Find a method using the given starting scope information       */
/******************************************************************************/
{
    /* if we have scopes defined and we  */
    /* have a good start scope           */
    if (this->scopes != OREF_NULL && startScope != TheNilObject)
    {
        /* get the scope list for the given  */
        /* starting scope                    */
        RexxArray *scopeList = (RexxArray *)this->scopes->get(startScope);
        if (scopeList != OREF_NULL)        /* have a matching list?             */
        {
            /* get a list of methods             */
            RexxArray *methods = this->methodDictionary->stringGetAll(messageName);
            size_t scopes_size = scopeList->size(); /* get the two array sizes           */
            size_t methods_size = methods->size();
            /* search through the methods list   */
            /* for the first one with a          */
            /* conforming scope                  */
            for (size_t i = 1; i <= methods_size; i++)
            {
                /* get the next method               */
                RexxMethod *method = (RexxMethod *)methods->get(i);
                /* now loop through the scopes list  */
                for (size_t j = 1; j <= scopes_size; j++)
                {
                    /* got a matching scope here?        */
                    if (scopeList->get(j) == method->getScope())
                    {
                        return method;             /* return the method                 */
                    }
                }
            }
        }
    }
    return OREF_NULL;                    /* nothing found                     */
}
Exemple #5
0
void RexxInstructionForward::execute(
    RexxActivation      *context,      /* current activation context        */
    RexxExpressionStack *stack)        /* evaluation stack                  */
/******************************************************************************/
/* Function:  Execute a forward instruction                                   */
/******************************************************************************/
{
    RexxObject *_target;                  /* evaluated target                  */
    RexxString *_message;                 /* evaluated message                 */
    RexxObject *_superClass;              /* evaluated super class             */
    RexxObject *result;                  /* message result                    */
    RexxObject *temp;                    /* temporary object                  */
    size_t      count = 0;               /* count of array expressions        */
    size_t      i;                       /* loop counter                      */
    RexxObject **_arguments;

    ProtectedObject p_message;
    
    context->traceInstruction(this);     /* trace if necessary                */
    if (!context->inMethod())            /* is this a method clause?          */
    {
                                         /* raise an error                    */
        reportException(Error_Execution_forward);
    }
    _target = OREF_NULL;                  /* no object yet                     */
    _message = OREF_NULL;                 /* no message over ride              */
    _superClass = OREF_NULL;              /* no super class over ride          */
    _arguments = OREF_NULL;               /* no argument over ride             */

    if (this->target != OREF_NULL)       /* sent to a different object?       */
    {
                                         /* get the expression value          */
        _target = this->target->evaluate(context, stack);
    }
    if (this->message != OREF_NULL)    /* sending a different message?      */
    {
        /* get the expression value          */
        temp = this->message->evaluate(context, stack);
        _message = REQUEST_STRING(temp);    /* get the string version            */
        p_message = _message;
        _message = _message->upper();       /* and force to uppercase            */
        p_message = _message;
    }
    if (this->superClass != OREF_NULL)   /* overriding the super class?       */
    {
                                         /* get the expression value          */
        _superClass = this->superClass->evaluate(context, stack);
    }
    if (this->arguments != OREF_NULL)  /* overriding the arguments?         */
    {
        /* get the expression value          */
        temp = this->arguments->evaluate(context, stack);
        /* get an array version              */
        RexxArray *argArray = REQUEST_ARRAY(temp);
        stack->push(argArray);           /* protect this on the stack         */
        /* not an array item or a multiple   */
        /* dimension one?                    */
        if (argArray == TheNilObject || argArray->getDimension() != 1)
        {
            /* this is an error                  */
            reportException(Error_Execution_forward_arguments);
        }
        count = argArray->size();          /* get the size                      */
                                           /* omitted trailing arguments?       */
        if (count != 0 && argArray->get(count) == OREF_NULL)
        {
            count--;                         /* decrement the count               */
            while (count > 0)              /* loop down to first full one       */
            {
                /* find a real argument              */
                if (argArray->get(count) != OREF_NULL)
                {
                    break;                       /* break out of here                 */
                }
                count--;                       /* step back the count               */
            }
        }
        _arguments = argArray->data();    /* point directly to the argument data */
    }
    if (this->array != OREF_NULL)      /* have an array of extra info?      */
    {
        count = this->array->size();       /* get the expression count          */
        for (i = 1; i <= count; i++)     /* loop through the expression list  */
        {
            RexxObject *argElement = this->array->get(i);
            /* real argument?                    */
            if (argElement != OREF_NULL)
            {
                /* evaluate the expression           */
                argElement->evaluate(context, stack);
            }
            else
            {
                /* just push a null reference for the missing ones */
                stack->push(OREF_NULL);
            }
        }
        /* now point at the stacked values */
        _arguments = stack->arguments(count);
    }
    /* go forward this                   */
    result = context->forward(_target, _message, _superClass, _arguments, count, instructionFlags&forward_continue);
    if (instructionFlags&forward_continue)  /* not exiting?                      */
    {
        if (result != OREF_NULL)         /* result returned?                  */
        {
            context->traceResult(result);    /* trace if necessary                */
                                             /* set the RESULT variable to the    */
                                             /* message return value              */
            context->setLocalVariable(OREF_RESULT, VARIABLE_RESULT, result);
        }
        else                               /* drop the variable RESULT          */
        {
            context->dropLocalVariable(OREF_RESULT, VARIABLE_RESULT);
        }
        context->pauseInstruction();       /* do debug pause if necessary       */
    }
}