2016-06-23 Chris Wilson <chris@xxxxxxxxxxxxxxxxxx>: > On Thu, Jun 23, 2016 at 12:29:50PM -0300, Gustavo Padovan wrote: > > -static void sync_file_add_pt(struct sync_file *sync_file, int *i, > > +static int sync_file_set_fence(struct sync_file *sync_file, > > + struct fence **fences) > > +{ > > + struct fence_array *array; > > + > > + if (sync_file->num_fences == 1) { > > + sync_file->fence = fences[0]; > > Straightforward pointer assignment. > > > + } else { > > + array = fence_array_create(sync_file->num_fences, fences, > > + fence_context_alloc(1), 1, false); > > + if (!array) > > + return -ENOMEM; > > + > > + sync_file->fence = &array->base; > > New reference. > > Imbalance will promptly go bang after we release the single fence[0]. > > Would fence_array_create(1, fence) returning fence_get(fence) be too > much of a hack? > > I would suggest dropping the exported fence_get_fences() and use a local > instead that could avoid the copy, e.g. > > static struct fence *get_fences(struct fence **fence, > unsigned int *num_fences) > { > if (fence_is_array(*fence)) { > struct fence_array *array = to_fence_array(*fence); > *num_fences = array->num_fences; > return array->fences; > } else { > *num_fences = 1; > return fence; > } > } > > sync_file_merge() { > int num_fences, num_a_fences, num_b_fences; > struct fence **fences, **a_fences, **b_fences; > > a_fences = get_fences(&a, &num_a_fences); > b_fences = get_fences(&b, &num_b_fences); > > num_fences = num_a_fences + num_b_fences; Yes. That is much cleaner solution. I did this initially but then tried to come up with .get_fences(), but that was the wrong road. > > > static void sync_file_free(struct kref *kref) > > { > > struct sync_file *sync_file = container_of(kref, struct sync_file, > > kref); > > - int i; > > - > > - for (i = 0; i < sync_file->num_fences; ++i) { > > - fence_remove_callback(sync_file->cbs[i].fence, > > - &sync_file->cbs[i].cb); > > - fence_put(sync_file->cbs[i].fence); > > - } > > > > + fence_remove_callback(sync_file->fence, &sync_file->cb); > > + fence_teardown(sync_file->fence); > > Hmm. Could we detect the removal of the last callback and propagate that > to the fence_array? (Rather then introduce a manual call to > fence_teardown.) Maybe. I'll look into ways to identify that. What I did during the development of this patch was to have a fence_array_destroy(), but then I moved to .teardown() in the hope to abstract the diff between fences and fence_arrays. Gustavo _______________________________________________ dri-devel mailing list dri-devel@xxxxxxxxxxxxxxxxxxxxx https://lists.freedesktop.org/mailman/listinfo/dri-devel