swap_func(a, b, (int)size);
 }
 
+typedef int (*cmp_func_t)(const void *, const void *);
+typedef int (*cmp_r_func_t)(const void *, const void *, const void *);
+#define _CMP_WRAPPER ((cmp_r_func_t)0L)
+
+static int do_cmp(const void *a, const void *b,
+                 cmp_r_func_t cmp, const void *priv)
+{
+       if (cmp == _CMP_WRAPPER)
+               return ((cmp_func_t)(priv))(a, b);
+       return cmp(a, b, priv);
+}
+
 /**
  * parent - given the offset of the child, find the offset of the parent.
  * @i: the offset of the heap element whose parent is sought.  Non-zero.
 }
 
 /**
- * sort - sort an array of elements
+ * sort_r - sort an array of elements
  * @base: pointer to data to sort
  * @num: number of elements
  * @size: size of each element
  * @cmp_func: pointer to comparison function
  * @swap_func: pointer to swap function or NULL
+ * @priv: third argument passed to comparison function
  *
  * This function does a heapsort on the given array.  You may provide
  * a swap_func function if you need to do something more than a memory
  * O(n*n) worst-case behavior and extra memory requirements that make
  * it less suitable for kernel use.
  */
-void sort(void *base, size_t num, size_t size,
-         int (*cmp_func)(const void *, const void *),
-         void (*swap_func)(void *, void *, int size))
+void sort_r(void *base, size_t num, size_t size,
+           int (*cmp_func)(const void *, const void *, const void *),
+           void (*swap_func)(void *, void *, int size),
+           const void *priv)
 {
        /* pre-scale counters for performance */
        size_t n = num * size, a = (num/2) * size;
                 * average, 3/4 worst-case.)
                 */
                for (b = a; c = 2*b + size, (d = c + size) < n;)
-                       b = cmp_func(base + c, base + d) >= 0 ? c : d;
+                       b = do_cmp(base + c, base + d, cmp_func, priv) >= 0 ? c : d;
                if (d == n)     /* Special case last leaf with no sibling */
                        b = c;
 
                /* Now backtrack from "b" to the correct location for "a" */
-               while (b != a && cmp_func(base + a, base + b) >= 0)
+               while (b != a && do_cmp(base + a, base + b, cmp_func, priv) >= 0)
                        b = parent(b, lsbit, size);
                c = b;                  /* Where "a" belongs */
                while (b != a) {        /* Shift it into place */
                }
        }
 }
+EXPORT_SYMBOL(sort_r);
+
+void sort(void *base, size_t num, size_t size,
+         int (*cmp_func)(const void *, const void *),
+         void (*swap_func)(void *, void *, int size))
+{
+       return sort_r(base, num, size, _CMP_WRAPPER, swap_func, cmp_func);
+}
 EXPORT_SYMBOL(sort);