Exemplo n.º 1
0
mrp_attr_t *mrp_attribute_get_value(uint32_t          idx,
                                    mrp_attr_t       *value,
                                    uint32_t          nattr,
                                    mrp_attr_def_t   *defs,
                                    mrp_attr_value_t *attrs)
{
    mrp_attr_t *vdst;
    mrp_attr_def_t *adef;

    MRP_ASSERT(!nattr || (nattr > 0 && defs && attrs), "invalid argument");
    MRP_ASSERT(idx < nattr, "invalid argument");

    if ((vdst = value) || (vdst = mrp_alloc(sizeof(mrp_attr_t)))) {
        adef = defs + idx;

        if (!(adef->access & MRP_RESOURCE_READ))
            memset(vdst, 0, sizeof(mrp_attr_t));
        else {
            vdst->name  = adef->name;
            vdst->type  = adef->type;
            vdst->value = attrs[idx];
        }
    }

    return vdst;
}
Exemplo n.º 2
0
int16_t *filter_buffer_dup(context_t *ctx,
                           int32_t start,
                           int32_t end,
                           size_t *ret_length)
{
    filter_buf_t *filtbuf;
    int16_t *dup;
    size_t len;


    if (!ctx || !(filtbuf = ctx->filtbuf))
        return NULL;

    if (start < 0 || end < 0 || start >= end || start >= filtbuf->len)
        return NULL;

    len = (end - start) * sizeof(int16_t);

    if (!(dup = mrp_alloc(len)))
        len = 0;
    else
        memcpy(dup, filtbuf->buf + start, len);

    if (ret_length)
        *ret_length = len / sizeof(int16_t);

    return dup;
}
Exemplo n.º 3
0
void filter_buffer_initialize(context_t *ctx,
                              int32_t bufsiz,
                              int32_t highwater_mark,
                              int32_t silen)
{
    options_t *opts;
    filter_buf_t *filtbuf;
    uint32_t rate;
    int32_t frlen;
    int32_t hwm;
    size_t silence;

    if (!ctx || !(opts = ctx->opts) || !(filtbuf = ctx->filtbuf))
        return;

    rate = opts->rate;
    frlen = filtbuf->frlen;
    bufsiz = (bufsiz + (frlen - 1)) / frlen * frlen;
    hwm = (highwater_mark + (frlen - 1)) / frlen * frlen;
    silence = INJECTED_SILENCE * frlen;

    filtbuf->buf = mrp_alloc((bufsiz + silence) * sizeof(int16_t));
    filtbuf->max = bufsiz;
    filtbuf->hwm = hwm;
    filtbuf->silen = silen;

    if (ctx->verbose) {
        mrp_debug("frame length %d samples", filtbuf->frlen);
        mrp_debug("filter buffer size %u samples (%.3lf sec); "
                  "high-water mark %u samples (%.3lf sec)",
                  filtbuf->max, (double)filtbuf->max / (double)rate,
                  filtbuf->hwm, (double)filtbuf->hwm / (double)rate);
        mrp_debug("silence detection window %d samples (%.3lf sec)",
                  filtbuf->silen, (double)filtbuf->silen / (double)rate);
    }
}
Exemplo n.º 4
0
void mrp_resource_owner_update_zone(uint32_t zoneid,
                                    mrp_resource_set_t *reqset,
                                    uint32_t reqid)
{
    typedef struct {
        uint32_t replyid;
        mrp_resource_set_t *rset;
        bool move;
    } event_t;

    mrp_resource_owner_t oldowners[MRP_RESOURCE_MAX];
    mrp_resource_owner_t backup[MRP_RESOURCE_MAX];
    mrp_zone_t *zone;
    mrp_application_class_t *class;
    mrp_resource_set_t *rset;
    mrp_resource_t *res;
    mrp_resource_def_t *rdef;
    mrp_resource_mgr_ftbl_t *ftbl;
    mrp_resource_owner_t *owner, *old, *owners;
    mrp_resource_mask_t mask;
    mrp_resource_mask_t mandatory;
    mrp_resource_mask_t grant;
    mrp_resource_mask_t advice;
    void *clc, *rsc, *rc;
    uint32_t rid;
    uint32_t rcnt;
    bool force_release;
    bool changed;
    bool move;
    mrp_resource_event_t notify;
    uint32_t replyid;
    uint32_t nevent, maxev;
    event_t *events, *ev, *lastev;

    MRP_ASSERT(zoneid < MRP_ZONE_MAX, "invalid argument");

    zone = mrp_zone_find_by_id(zoneid);

    MRP_ASSERT(zone, "zone is not defined");

    if (!(maxev = mrp_get_resource_set_count()))
        return;

    nevent = 0;
    events = mrp_alloc(sizeof(event_t) * maxev);

    MRP_ASSERT(events, "Memory alloc failure. Can't update zone");

    reset_owners(zoneid, oldowners);
    manager_start_transaction(zone);

    rcnt = mrp_resource_definition_count();
    clc  = NULL;

    while ((class = mrp_application_class_iterate_classes(&clc))) {
        rsc = NULL;

        while ((rset=mrp_application_class_iterate_rsets(class,zoneid,&rsc))) {
            force_release = false;
            mandatory = rset->resource.mask.mandatory;
            grant = 0;
            advice = 0;
            rc = NULL;

            switch (rset->state) {

            case mrp_resource_acquire:
                while ((res = mrp_resource_set_iterate_resources(rset, &rc))) {
                    rdef  = res->def;
                    rid   = rdef->id;
                    owner = get_owner(zoneid, rid);

                    backup[rid] = *owner;

                    if (grant_ownership(owner, zone, class, rset, res))
                        grant |= ((mrp_resource_mask_t)1 << rid);
                    else {
                        if (owner->rset != rset)
                            force_release |= owner->modal;
                    }
                }
                owners = get_owner(zoneid, 0);
                if ((grant & mandatory) == mandatory &&
                    mrp_resource_lua_veto(zone, rset, owners, grant, reqset))
                {
                    advice = grant;
                }
                else {
                    /* rollback, ie. restore the backed up state */
                    rc = NULL;
                    while ((res=mrp_resource_set_iterate_resources(rset,&rc))){
                        rdef = res->def;
                        rid = rdef->id;
                        mask = (mrp_resource_mask_t)1 << rid;
                        owner = get_owner(zoneid, rid);
                        *owner = backup[rid];

                        if ((grant & mask)) {
                            if ((ftbl = rdef->manager.ftbl) && ftbl->free)
                                ftbl->free(zone, res, rdef->manager.userdata);
                        }

                        if (advice_ownership(owner, zone, class, rset, res))
                            advice |= mask;
                    }

                    grant = 0;

                    if ((advice & mandatory) != mandatory)
                        advice = 0;

                    mrp_resource_lua_set_owners(zone, owners);
                }
                break;

            case mrp_resource_release:
                while ((res = mrp_resource_set_iterate_resources(rset, &rc))) {
                    rdef  = res->def;
                    rid   = rdef->id;
                    owner = get_owner(zoneid, rid);

                    if (advice_ownership(owner, zone, class, rset, res))
                        advice |= ((mrp_resource_mask_t)1 << rid);
                }
                if ((advice & mandatory) != mandatory)
                    advice = 0;
                break;

            default:
                break;
            }

            changed = false;
            move    = false;
            notify  = 0;
            replyid = (reqset == rset && reqid == rset->request.id) ? reqid:0;


            if (force_release) {
                move = (rset->state != mrp_resource_release);
                notify = move ? MRP_RESOURCE_EVENT_RELEASE : 0;
                changed = move || rset->resource.mask.grant;
                rset->state = mrp_resource_release;
                rset->resource.mask.grant = 0;
            }
            else {
                if (grant == rset->resource.mask.grant) {
                    if (rset->state == mrp_resource_acquire &&
                        !grant && rset->dont_wait.current)
                    {
                        rset->state = mrp_resource_release;
                        rset->dont_wait.current = rset->dont_wait.client;

                        notify = MRP_RESOURCE_EVENT_RELEASE;
                        move = true;
                    }
                }
                else {
                    rset->resource.mask.grant = grant;
                    changed = true;

                    if (rset->state != mrp_resource_release &&
                        !grant && rset->auto_release.current)
                    {
                        rset->state = mrp_resource_release;
                        rset->auto_release.current = rset->auto_release.client;

                        notify = MRP_RESOURCE_EVENT_RELEASE;
                        move = true;
                    }
                }
            }

            if (notify) {
                mrp_resource_set_notify(rset, notify);
            }

            if (advice != rset->resource.mask.advice) {
                rset->resource.mask.advice = advice;
                changed = true;
            }

            if (replyid || changed) {
                ev = events + nevent++;

                ev->replyid = replyid;
                ev->rset    = rset;
                ev->move    = move;
            }
        } /* while rset */
    } /* while class */