X-Git-Url: http://info.iut-bm.univ-fcomte.fr/pub/gitweb/simgrid.git/blobdiff_plain/5d153de8eb3f64313d265a111e3a3ebf7062e88c..97aa0e698984b850ad794879f10e2978e4ec94fe:/src/xbt/dynar.c diff --git a/src/xbt/dynar.c b/src/xbt/dynar.c index 7e7512bee2..f979c2188a 100644 --- a/src/xbt/dynar.c +++ b/src/xbt/dynar.c @@ -523,7 +523,9 @@ xbt_dynar_remove_at(xbt_dynar_t const dynar, /** @brief Returns the position of the element in the dynar * - * Raises not_found_error if not found. + * Raises not_found_error if not found. If you have less than 2 millions elements, + * you probably want to use #xbt_dynar_search_or_negative() instead, so that you + * don't have to TRY/CATCH on element not found. */ unsigned int xbt_dynar_search(xbt_dynar_t const dynar, void *const elem) { @@ -541,6 +543,26 @@ unsigned int xbt_dynar_search(xbt_dynar_t const dynar, void *const elem) dynar); } +/** @brief Returns the position of the element in the dynar (or -1 if not found) + * + * Note that usually, the dynar indices are unsigned integers. If you have more + * than 2 million elements in your dynar, this very function will not work (but the other will). + */ +signed int xbt_dynar_search_or_negative(xbt_dynar_t const dynar, void *const elem) +{ + unsigned long it; + + _dynar_lock(dynar); + for (it = 0; it < dynar->used; it++) + if (!memcmp(_xbt_dynar_elm(dynar, it), elem, dynar->elmsize)) { + _dynar_unlock(dynar); + return it; + } + + _dynar_unlock(dynar); + return -1; +} + /** @brief Returns a boolean indicating whether the element is part of the dynar */ int xbt_dynar_member(xbt_dynar_t const dynar, void *const elem) { @@ -736,36 +758,35 @@ XBT_PUBLIC(void) xbt_dynar_three_way_partition(xbt_dynar_t const dynar, int_f_pvoid_t color) { _dynar_lock(dynar); - unsigned long size = xbt_dynar_length(dynar); - void *data = dynar->data; unsigned long int i; unsigned long int p = -1; - unsigned long int q = size; - unsigned long elmsize = dynar->elmsize; + unsigned long int q = dynar->used; + const unsigned long elmsize = dynar->elmsize; void *tmp = xbt_malloc(elmsize); - -#define swap(a,b) do { \ - memcpy(tmp, a , elmsize); \ - memcpy( a , b , elmsize); \ - memcpy( b , tmp, elmsize); \ - } while(0) + void *elm; for (i = 0; i < q;) { - unsigned long int datai = ((unsigned long int) data) + i*elmsize; - int colori = color((void *) datai); + void *elmi = _xbt_dynar_elm(dynar, i); + int colori = color(elmi); - if(colori==0) { - unsigned long int datap = ((unsigned long int) data) + (++p)*elmsize; - swap((void *) datai, (void *) datap); + if (colori == 1) { ++i; - } else if (colori==2) { - unsigned long int dataq = ((unsigned long int) data) + (--q)*elmsize; - swap((void *) datai, (void *) dataq); } else { - ++i; + if (colori == 0) { + elm = _xbt_dynar_elm(dynar, ++p); + ++i; + } else { /* colori == 2 */ + elm = _xbt_dynar_elm(dynar, --q); + } + if (elm != elmi) { + memcpy(tmp, elm, elmsize); + memcpy(elm, elmi, elmsize); + memcpy(elmi, tmp, elmsize); + } } } _dynar_unlock(dynar); + xbt_free(tmp); } /** @brief Transform a dynar into a NULL terminated array