[PD] variable receive objects?

Jonathan Wilkes jancsika at yahoo.com
Sun Jun 24 02:50:39 CEST 2012





----- Original Message -----
> From: Ivica Ico Bukvic <ico at vt.edu>
> To: Miller Puckette <msp at ucsd.edu>
> Cc: pd-list at iem.at
> Sent: Saturday, June 23, 2012 6:36 PM
> Subject: Re: [PD] variable receive objects?
> 
> 
> 
> Miller Puckette <msp at ucsd.edu> wrote:
> 
>> Hmm.. I'm still looking for a solution that doesn't require adding
>> extra
>> stuff to bindlist_bang() etc.
> 
> In the meantime for those eager to work with dynamic receives, the fix below is 
> now in the pd-l2otk trunk on the github.
> 
> Coming up next in the land o' pd-l2ork, universal presets ;-)

Sounds neat!

-Jonathan

> 
> Best wishes,
> 
> Ico
> 
>> 
>> cheers
>> M
>> 
>> On Wed, Jun 20, 2012 at 06:09:22PM -0400, Ivica Ico Bukvic wrote:
>>>  On 06/20/2012 05:38 PM, Miller Puckette wrote:
>>>  >[snip]
>>>  >I'm just saying that the automatic varable t_bindelem *e should 
> be
>> declared
>>>  >at the beginning of the block - no worries about
>> change_bindlist_via_graph.
>>>  Ah, now I get it :-). Fixed.
>>>  >I think bindlist_bang() etc are more critical than pd_unbind as 
> they
>> naturally
>>>  >get called many times while a patch is running whereas pd_unbind is
>> typically
>>>  >called only when objects are deleted.  So moving checks from
>> pd_unbind()
>>>  >to  bindlist_bang() etc decreases pd's run-time efficiency.
>>>  >
>>>  >cheers
>>>  >M
>>>  OK, how about the attached patch where now I use the
>>>  change_bindlist_via_graph variable and increment it by one every
>>>  time something needs to be unbound so when you return back to the
>>>  bindlist_bang() or whatever call was issued, only if
>>>  change_bindlist_via_graph > 1 should it call unbind. Now it avoids
>>>  entering the bindlist_cleanup unless it absolutely has to...
>>> 
>>>  Attached is also a patch that illustrates your case presented
>>>  earlier which crashed pd-l2ork prior to applying this latest version
>>>  of the patch.
>>> 
>>>  Cheers!
>>> 
>>>  -- 
>>>  Ivica Ico Bukvic, D.M.A
>>>  Composition, Music Technology
>>>  Director, DISIS Interactive Sound&  Intermedia Studio
>>>  Director, L2Ork Linux Laptop Orchestra
>>>  Head, ICAT IMPACT Studio
>>>  Virginia Tech
>>>  Department of Music
>>>  Blacksburg, VA 24061-0240
>>>  (540) 231-6139
>>>  (540) 231-5034 (fax)
>>>  disis.music.vt.edu
>>>  l2ork.music.vt.edu
>>>  ico.bukvic.net
>>> 
>> 
>>>  --- m_pd.c.old    2012-06-20 17:51:43.845040884 -0400
>>>  +++ m_pd.c    2012-06-20 18:06:02.047009570 -0400
>>>  @@ -146,48 +146,101 @@
>>>       t_bindelem *b_list;
>>>   } t_bindlist;
>>>   
>>>  +static int change_bindlist_via_graph = 0;
>>>  +
>>>  +static void bindlist_cleanup(t_bindlist *x)
>>>  +{
>>>  +    //fprintf(stderr,"bindlist_cleanup\n");
>>>  +    t_bindelem *e, *e2;
>>>  +    if (x->b_list->e_who == NULL)
>>>  +    {
>>>  +        e = x->b_list;
>>>  +        x->b_list = e->e_next;
>>>  +        freebytes(e, sizeof(t_bindelem));
>>>  +        //fprintf(stderr,"success B1a\n");
>>>  +    }
>>>  +    for (e = x->b_list; e2 = e->e_next; e = e2)
>>>  +        if (e2->e_who == NULL)
>>>  +    {
>>>  +        e->e_next = e2->e_next;
>>>  +        freebytes(e2, sizeof(t_bindelem));
>>>  +        //fprintf(stderr,"success B1b\n");
>>>  +        break;
>>>  +    }
>>>  +    if (!x->b_list->e_next)
>>>  +    {
>>>  +        freebytes(x->b_list, sizeof(t_bindelem));
>>>  +        pd_free(&x->b_pd);
>>>  +        //fprintf(stderr,"success B2\n");
>>>  +    }
>>>  +}
>>>  +
>>>   static void bindlist_bang(t_bindlist *x)
>>>   {
>>>       t_bindelem *e;
>>>  +    change_bindlist_via_graph = 1;
>>>       for (e = x->b_list; e; e = e->e_next)
>>>  -        pd_bang(e->e_who);
>>>  +        if (e->e_who != NULL) pd_bang(e->e_who);
>>>  +    if (change_bindlist_via_graph > 1)
>>>  +        bindlist_cleanup(x);
>>>  +    change_bindlist_via_graph = 0;
>>>   }
>>>   
>>>   static void bindlist_float(t_bindlist *x, t_float f)
>>>   {
>>>       t_bindelem *e;
>>>  +    change_bindlist_via_graph = 1;
>>>       for (e = x->b_list; e; e = e->e_next)
>>>  -        pd_float(e->e_who, f);
>>>  +        if (e->e_who != NULL) pd_float(e->e_who, f);
>>>  +    if (change_bindlist_via_graph > 1)
>>>  +        bindlist_cleanup(x);
>>>  +    change_bindlist_via_graph = 0;
>>>   }
>>>   
>>>   static void bindlist_symbol(t_bindlist *x, t_symbol *s)
>>>   {
>>>       t_bindelem *e;
>>>  +    change_bindlist_via_graph = 1;
>>>       for (e = x->b_list; e; e = e->e_next)
>>>  -        pd_symbol(e->e_who, s);
>>>  +        if (e->e_who != NULL) pd_symbol(e->e_who, s);
>>>  +    if (change_bindlist_via_graph > 1)
>>>  +        bindlist_cleanup(x);
>>>  +    change_bindlist_via_graph = 0;
>>>   }
>>>   
>>>   static void bindlist_pointer(t_bindlist *x, t_gpointer *gp)
>>>   {
>>>       t_bindelem *e;
>>>  +    change_bindlist_via_graph = 1;
>>>       for (e = x->b_list; e; e = e->e_next)
>>>  -        pd_pointer(e->e_who, gp);
>>>  +        if (e->e_who != NULL) pd_pointer(e->e_who, gp);
>>>  +    if (change_bindlist_via_graph > 1)
>>>  +        bindlist_cleanup(x);
>>>  +    change_bindlist_via_graph = 0;
>>>   }
>>>   
>>>   static void bindlist_list(t_bindlist *x, t_symbol *s,
>>>       int argc, t_atom *argv)
>>>   {
>>>       t_bindelem *e;
>>>  +    change_bindlist_via_graph = 1;
>>>       for (e = x->b_list; e; e = e->e_next)
>>>  -        pd_list(e->e_who, s, argc, argv);
>>>  +        if (e->e_who != NULL) pd_list(e->e_who, s, argc, argv);
>>>  +    if (change_bindlist_via_graph > 1)
>>>  +        bindlist_cleanup(x);
>>>  +    change_bindlist_via_graph = 0;
>>>   }
>>>   
>>>   static void bindlist_anything(t_bindlist *x, t_symbol *s,
>>>       int argc, t_atom *argv)
>>>   {
>>>       t_bindelem *e;
>>>  +    change_bindlist_via_graph = 1;
>>>       for (e = x->b_list; e; e = e->e_next)
>>>  -        pd_typedmess(e->e_who, s, argc, argv);
>>>  +        if (e->e_who != NULL) pd_typedmess(e->e_who, s, argc, 
> argv);
>>>  +    if (change_bindlist_via_graph > 1)
>>>  +        bindlist_cleanup(x);
>>>  +    change_bindlist_via_graph = 0;
>>>   }
>>>   
>>>   void m_pd_setup(void)
>>>  @@ -204,6 +257,7 @@
>>>   
>>>   void pd_bind(t_pd *x, t_symbol *s)
>>>   {
>>>  +    //fprintf(stderr,"pd_bind %s\n", s->s_name);
>>>       if (s->s_thing)
>>>       {
>>>           if (*s->s_thing == bindlist_class)
>>>  @@ -217,7 +271,7 @@
>>>           }
>>>           else
>>>           {
>>>  -            //fprintf(stderr,"pd_unbind option 1B 
> %lx\n", (t_int)x);
>>>  +            //fprintf(stderr,"pd_bind option 1B %lx\n", 
> (t_int)x);
>>>               t_bindlist *b = (t_bindlist *)pd_new(bindlist_class);
>>>               t_bindelem *e1 = (t_bindelem
>> *)getbytes(sizeof(t_bindelem));
>>>               t_bindelem *e2 = (t_bindelem
>> *)getbytes(sizeof(t_bindelem));
>>>  @@ -237,6 +291,7 @@
>>>   
>>>   void pd_unbind(t_pd *x, t_symbol *s)
>>>   {
>>>  +    //fprintf(stderr,"pd_unbind %s\n", s->s_name);
>>>       if (s->s_thing == x) {
>>>           //fprintf(stderr,"pd_unbind option A %lx\n", 
> (t_int)x);
>>>           s->s_thing = 0;
>>>  @@ -247,30 +302,56 @@
>>>               goes down to one, get rid of the bindlist and bind the
>> symbol
>>>               straight to the remaining element. */
>>>   
>>>  +            /* in pd-l2ork, we however also check whether changes to 
> the
>> bindlist
>>>  +            occur via graph (through code execution, e.g. dynamic 
> change of
>> receives)
>>>  +            and if so, we do not deallocate memory until the entire
>> bindlist_<datatype>
>>>  +            function is complete with its execution, after which we 
> call
>>>  +            bindlist_cleanup(). we control the execution via static 
> int
>> variable
>>>  +            change_bindlist_via_graph */
>>>  +
>>>           //fprintf(stderr,"pd_unbind option B %lx\n", 
> (t_int)x);
>>>   
>>>           t_bindlist *b = (t_bindlist *)s->s_thing;
>>>           t_bindelem *e, *e2;
>>>           if ((e = b->b_list)->e_who == x)
>>>           {
>>>  -            b->b_list = e->e_next;
>>>  -            freebytes(e, sizeof(t_bindelem));
>>>  +            if (change_bindlist_via_graph) {
>>>  +                change_bindlist_via_graph++;
>>>  +                e->e_who = NULL;
>>>  +            } else {
>>>  +                b->b_list = e->e_next;
>>>  +                freebytes(e, sizeof(t_bindelem));
>>>  +            }
>>>               //fprintf(stderr,"success B1a\n");
>>>           }
>>>           else for (e = b->b_list; e2 = e->e_next; e = e2)
>>>               if (e2->e_who == x)
>>>           {
>>>  -            e->e_next = e2->e_next;
>>>  -            freebytes(e2, sizeof(t_bindelem));
>>>  +            if (change_bindlist_via_graph) {
>>>  +                change_bindlist_via_graph++;
>>>  +                e2->e_who = NULL;
>>>  +            } else {
>>>  +                e->e_next = e2->e_next;
>>>  +                freebytes(e2, sizeof(t_bindelem));
>>>  +            }
>>>               //fprintf(stderr,"success B1b\n");
>>>               break;
>>>           }
>>>  -        if (!b->b_list->e_next)
>>>  +
>>>  +        int count_valid = 0;
>>>  +        for (e = b->b_list; e; e = e->e_next)
>>>           {
>>>  +            if (e->e_who != NULL)
>>>  +                count_valid++;
>>>  +
>>>  +        }
>>>  +        if (count_valid == 1) {
>>>               s->s_thing = b->b_list->e_who;
>>>  -            freebytes(b->b_list, sizeof(t_bindelem));
>>>  -            pd_free(&b->b_pd);
>>>  -            ///fprintf(stderr,"success B3\n");
>>>  +            if (!change_bindlist_via_graph) {
>>>  +                freebytes(b->b_list, sizeof(t_bindelem));
>>>  +                pd_free(&b->b_pd);
>>>  +            }
>>>  +            //fprintf(stderr,"success B2\n");
>>>           }
>>>       }
>>>       else pd_error(x, "%s: couldn't unbind", 
> s->s_name);
> 
> 
> Ivica Ico Bukvic, D.M.A
> Composition, Music Technology
> Director, DISIS Interactive Sound & Intermedia Studio
> Director, L2Ork Linux Laptop Orchestra
> Head, ICAT IMPACT Studio
> Virginia Tech
> Department of Music
> Blacksburg, VA 24061-0240
> (540) 231-6139
> (540) 231-5034 (fax)
> disis.music.vt.edu
> l2ork.music.vt.edu
> ico.bukvic.net
> 
> _______________________________________________
> Pd-list at iem.at mailing list
> UNSUBSCRIBE and account-management -> 
> http://lists.puredata.info/listinfo/pd-list
> 



More information about the Pd-list mailing list