This is specifically the type of function I want to avoid. This is not extensible at all, so not a good fit for a plugin API. Also, parameter-heavy functions are generally hard to use correctly (it's sometimes necessary but in this case my proposal gives a better solution IMO).
But yours isn't very consistent in this respect either - sorting parameters are provided as arguments of tm_query_exec() while the rest is provided by the query setters.
If you want to keep the setters instead of function parameters it's fine - this wasn't the important thing in my comment. But I think it would be much more flexible if it could be applied to an arbitrary tag array instead of the hard-coded global or session tags. There's for instance no way to get tags for the current document only. I would prefer
``` GPtrArray *tm_query_filter(GPtrArray *tag_array, TMQuery *q, TMTagAttrType *sort_attr, TMTagAttrType *dedup_attr) ```
and it would filter the source tag_array whatever it is. In fact, I would even prefer splitting this one into two:
``` GPtrArray *tm_query_filter(GPtrArray *tag_array, TMQuery *q) ```
and
``` GPtrArray *tm_sort(GPtrArray *tag_array, TMTagAttrType *sort_attr, TMTagAttrType *dedup_attr) ```