hi,
like on so many occasions already, my original hasty response to ``dynamic etern/subpatch instantiation'' post was not precise.
I must say, first of all, that in all cases reported below, it is hard to find any real bugs. These are `misfeatures', which do not break any promises -- and the safeguards could have been omitted for performance sake, or code simplicity, or whatever other reason...
original ``duplicated toplevel patch'' crash. The proof is here (toppatch.pd can be any patch file, [del 1000] is inserted in order to wait through any window raising delays):
#N canvas 213 96 518 300 12; #X obj 25 41 loadbang; #X msg 25 91 bang ; pd open toppatch.pd . ; pd open toppatch.pd .; #X obj 25 176 del 1000; #X msg 25 231 ; pd-toppatch.pd menuclose; #X connect 0 0 1 0; #X connect 1 0 2 0; #X connect 2 0 3 0;
static void bindlist_anything(t_bindlist *x, t_symbol *s, int argc, t_atom *argv) { t_bindelem *e = x->b_list; #if CRASHY /* the loop we have now */ for (e = x->b_list; e; e = e->e_next) pd_typedmess(e->e_who, s, argc, argv); #else /* safer loop */ while (e) { t_pd *who = e->e_who; e = e->e_next; pd_typedmess(who, s, argc, argv); } #endif }
theme in both cases was self-destruction, but my example was much more nasty. A direct cause of crashing in this case was such:
#N canvas 296 127 450 300 12; #X obj 44 40 loadbang; #X obj 44 79 del 1000; #X msg 44 117 ; pd-crash find r ; x please do not crash; #N canvas 43 0 376 332 crash 1; #X obj 110 138 outlet; #X obj 110 68 r x; #X connect 1 0 0 0; #X restore 44 202 pd crash; #X msg 44 239 ; pd-crash cut; #X connect 0 0 1 0; #X connect 1 0 2 0; #X connect 3 0 4 0;
void outlet_anything(t_outlet *x, t_symbol *s, int argc, t_atom *argv) { t_outconnect *oc = x->o_connections; char c; if (&c < stacklimit) outlet_stackerror(x); #if CRASHY /* the loop we have now */ else for (oc = x->o_connections; oc; oc = oc->oc_next) typedmess(oc->oc_to, s, argc, argv); #else /* safer loop */ else while (oc) { t_pd *dest = oc->oc_to; oc = oc->oc_next; typedmess(dest, s, argc, argv); } #endif }
the two safeguards are not applied to bang message, i.e. we need to embellish also bindlist_bang() and outlet_bang().
a [del 1000] object inserted after any patch-modifying loadbang.
Btw. under Gnome this delay may need to be even longer (I think there is a window raising bug in Gnome or Sawfish; in my Gnome system it is so annoying, that I finally deleted `after-raise' command from pdtk_canvas_new in pd.tk; no such trouble under fvwm2).
be crashes, if the fatal message was clicked, instead of being loadbanged. For example, using safer version of outlet_bang(), the following (if named `crash-message.pd') will not crash upon loading, but will crash after clicking ``please do not crash'' message.
#N canvas 296 127 424 295 12; #X obj 44 18 loadbang; #X obj 44 65 del 1000; #X msg 44 112 ; pd-crash-message.pd selectall ; x please do not crash; #X obj 44 195 r x; #X msg 44 243 ; pd-crash-message.pd cut; #X connect 0 0 1 0; #X connect 1 0 2 0; #X connect 3 0 4 0;
The simplest safeguard would be just an insertion of ``if (!y) return;'' into message_click().
any canvas which is not visible.
Crashtof