示例#1
0
c_bool
v_leaseAddObserverNoLock(
    v_lease _this,
    v_leaseManager observer)
{
    c_bool added;
    v_leaseManager found;

    assert(_this != NULL);
    assert(C_TYPECHECK(_this, v_lease));
    assert(observer != NULL);
    assert(C_TYPECHECK(observer, v_leaseManager));

    if(_this->observers)
    {
        found = c_setInsert(_this->observers, observer);
        if (found == observer)
        {
            added = TRUE;
        } else
        {
            added = FALSE;
        }
    } else
    {
        added = FALSE;
    }
    return added;
}
示例#2
0
void
v_subscriberAddReader(
    v_subscriber s,
    v_reader r)
{
    v_reader found;
    v_partition d;
    c_iter iter;

    assert(s != NULL);
    assert(r != NULL);

    iter = c_iterNew(NULL);
    c_lockWrite(&s->lock);
    v_partitionAdminWalk(s->partitions,collectPartitions,iter);
    while ((d = c_iterTakeFirst(iter)) != NULL) {
        v_readerSubscribe(r,d);
        c_free(d);
    }
    found = c_setInsert(s->readers,r);
    c_lockUnlock(&s->lock);
    if (found != r) {
        OS_REPORT_1(OS_ERROR,
                    "v_subscriberAddReader", 0,
                    "shared <%s> name already defined",
                    r->qos->share.name);
    }
    c_iterFree(iter);
}
示例#3
0
v_entry
v_readerAddEntry(
    v_reader r,
    v_entry e)
{
    v_entry found;

    assert(C_TYPECHECK(r,v_reader));
    assert(C_TYPECHECK(e,v_entry));

    v_readerEntrySetLock(r);
    found = c_setInsert(r->entrySet.entries, e);
    v_readerEntrySetUnlock(r);

    return c_keep(found);
}
示例#4
0
void
v_participantAdd(
    v_participant p,
    v_entity e)
{
    v_entity found;

    assert(p != NULL);
    assert(C_TYPECHECK(p,v_participant));
    assert(e != NULL);
    assert(C_TYPECHECK(e,v_entity));

    c_lockWrite(&p->lock);
    found = c_setInsert(p->entities,e);
    c_lockUnlock(&p->lock);
    assert(found == e);
}
示例#5
0
void
v_serviceFillNewGroups(
    v_service service)
{
    c_set newGroups;
    C_STRUCT(v_event) ge;
    v_group g, oldGroup;
    c_iter oldGroups;
    v_kernel kernel;

    assert(service != NULL);
    assert(C_TYPECHECK(service, v_service));

    kernel = v_objectKernel(service);
    newGroups = (c_voidp)c_setNew(v_kernelType(kernel, K_GROUP));

    if (newGroups != NULL) {
        addAllGroups(newGroups, kernel->groupSet);
        v_observerLock(v_observer(service));
        g = v_group(c_read(newGroups)); /* need a group for the event */

        if(v_observer(service)->eventData != NULL){
            oldGroups = ospl_c_select((c_set)v_observer(service)->eventData, 0);
            oldGroup = v_group(c_iterTakeFirst(oldGroups));

            while(oldGroup){
                newGroups = c_setInsert(newGroups, oldGroup);
                c_free(oldGroup);
                oldGroup = v_group(c_iterTakeFirst(oldGroups));
            }
            c_iterFree(oldGroups);
        }
        /* just for safety, when assertion are compiled out, free the prev set */
        c_free((c_object)v_observer(service)->eventData);
        v_observer(service)->eventData = (c_voidp)newGroups;

        ge.kind = V_EVENT_NEW_GROUP;
        ge.source = v_publicHandle(v_public(kernel));
        ge.userData = g;
        v_observerNotify(v_observer(service), &ge, NULL);
        v_observerUnlock(v_observer(service));
        c_free(g);
    }
}
示例#6
0
/**************************************************************
 * register/deregister of leases
 **************************************************************/
v_result
v_leaseManagerRegister(
    v_leaseManager  _this,
    v_lease         lease,
    v_leaseActionId actionId,
    v_public        actionObject,
    c_bool          repeatLease)
{
    c_bool obsAdded;
    v_leaseAction leaseAction;
    v_leaseAction found;
    v_result result;
    v_kernel k;

    assert(_this != NULL);
    assert(C_TYPECHECK(_this, v_leaseManager));
    assert(lease != NULL);
    assert(C_TYPECHECK(lease, v_lease));
    assert(actionObject != NULL);
    assert(C_TYPECHECK(actionObject, v_public));

    /* Step 1: Create a lease action object. This object will contain the relevant
     * information needed when reacting to an expired lease. This action information
     * can be different depending on which lease manager a lease is being registered
     * to, hence why the leaseAction object resides at leaseManager level and not
     * at lease level as it did in the past
     */
    k = v_objectKernel(_this);
    leaseAction = v_leaseAction(v_objectNew(k, K_LEASEACTION));
    if(!leaseAction)
    {
        OS_REPORT(OS_ERROR, "v_leaseManager", 0,
            "Failed to create a v_leaseManager object. "
            "Most likely not enough shared memory available to "
            "complete the operation.");
        result = V_RESULT_OUT_OF_MEMORY;
    } else
    {
        leaseAction->lease = v_lease(c_keep(lease));
        assert(leaseAction->lease);
        leaseAction->actionId = actionId;
        leaseAction->actionObject = v_publicHandle(actionObject);
        leaseAction->repeat = repeatLease;
        /* Step 2: insert the leaseAction object into the set of leases. */
        c_mutexLock(&_this->mutex);
        found = c_setInsert(_this->leases, leaseAction);
        if(!found)
        {
            /* Because the leaseAction object was just allocated we only have
             * to check if found is a NULL pointer. As it can never find the
             * action already being present in the set.
             */
            OS_REPORT(OS_ERROR, "v_leaseManager", 0,
                "Unable to register the lease to the list of "
                "leases of the leaseManager object! Most likely not enough shared "
                "memory available to complete the operation.");
            result = V_RESULT_OUT_OF_MEMORY;
            c_free(leaseAction);
            leaseAction = NULL;
        } else
        {
            assert(found == leaseAction);
            /* Step 3: Determine if the newly inserted leaseAction will become the
             * 'next lease to expire'. E.G., if the lease contained within the
             * leaseAction object has an expiry time that is the closest to the
             * present time compared to the other leases managed within this lease
             * manager. To prevent the lease time from changing while we evaluate the
             * lease we will lock the lease object.
             */
            v_leaseLock(lease);
            if(!_this->firstLeaseToExpire)
            {
                _this->firstLeaseToExpire = c_keep(leaseAction);
                /* head changed, so signal */
                c_condBroadcast(&_this->cond);
            } else if ((_this->firstLeaseToExpire->lease != lease) &&
                       (c_timeCompare(v_leaseExpiryTime(_this->firstLeaseToExpire->lease),
                                     v_leaseExpiryTimeNoLock(lease)) == C_GT))
            {
                c_free(_this->firstLeaseToExpire);
                _this->firstLeaseToExpire = c_keep(leaseAction);
                /* head changed, so signal */
                c_condBroadcast(&_this->cond);
            }/* else do nothing as the newly added lease expires after the firstLeaseToExpire */
            /* Step 4: Now that the lease was successfully inserted into the lease manager,
             * we need to register the leaseManager as an observer of the lease to ensure that the
             * lease manager is notified if the lease expiry time and/or duration changes.
             */
            obsAdded = v_leaseAddObserverNoLock(lease, _this);
            if(!obsAdded)
            {
                OS_REPORT(OS_ERROR, "v_leaseManager", 0,
                    "Unable to register the lease manager to the list of "
                    "observers of the lease object! Possibly not enough "
                    "shared memory available to complete the operation.");
                result = V_RESULT_INTERNAL_ERROR;
                v_leaseUnlock(lease);
                /* Remove the lease from the leaseManager */
                found = c_setRemove(_this->leases, leaseAction, NULL, NULL);
                if(found != leaseAction)
                {
                    OS_REPORT(OS_ERROR, "v_leaseManager", 0,
                        "Unable to unregister the lease to the list of "
                        "leases of the leaseManager object after previous internal error!");
                }
                c_free(leaseAction);
                leaseAction = NULL;
            } else
            {
                /* Now that the lease manager is in the observer list of the lease, we can unlock the lease
                 * as from now on we will be notified of any changes to the lease expiry time and/or duration
                 */
                v_leaseUnlock(lease);
                result = V_RESULT_OK;
            }

        }
        c_mutexUnlock(&_this->mutex);
    }
    if(leaseAction)
    {
        /* Done with the leaseAction object in this operation. If the object is not a NULL
         * pointer then everything went ok. The leases set of the leaseManager should be
         * the only one maintaining a ref count now (and possibly the 'firstLeaseToExpire'
         * attribute. But we do not need the leaseAction object in this operation anymore
         * and we are not returning it, so we need to lower the ref count for the new operation
         */
        c_free(leaseAction);
    }/* else do nothing */

    return result;
}