diff options
author | 2021-02-17 08:57:56 +0200 | |
---|---|---|
committer | 2021-02-17 08:57:56 +0200 | |
commit | 26ab990a747ab675bcff32a40734dcb61468f652 (patch) | |
tree | ef820c67202a3fb97ff4b2ae5df7caf347403b58 /src/cache.c | |
parent | e5a7592b606f6e75981fd48b32b3593a1d7c7f77 (diff) | |
download | algos-ld1-26ab990a747ab675bcff32a40734dcb61468f652.tar.gz algos-ld1-26ab990a747ab675bcff32a40734dcb61468f652.tar.bz2 algos-ld1-26ab990a747ab675bcff32a40734dcb61468f652.zip |
Most of sorting an array in memory is wired up.
Signed-off-by: Gediminas Jakutis <gediminas@varciai.lt>
Diffstat (limited to 'src/cache.c')
-rw-r--r-- | src/cache.c | 44 |
1 files changed, 33 insertions, 11 deletions
diff --git a/src/cache.c b/src/cache.c index 0c99322..f8a2026 100644 --- a/src/cache.c +++ b/src/cache.c @@ -47,8 +47,10 @@ int cache_populate(struct stream * const in) break; } } + } else if (in->type == stream_in) { + try(1, err, ENOSYS, "populating cache from file is a TODO"); } else { - /* TODO */ + try(1, err, EINVAL, "cannot populate a non-reading stream cache"); } err: @@ -92,7 +94,7 @@ int cache_block_copy(struct stream const * const src, struct stream * const dest try(src->settings->access != cached || dest->settings->access != cached, err, EINVAL, "cannot cache-copy between uncached streams"); try(!src->cache, err, EINVAL, "no cache to transfer"); - try(!(src->n < dest->settings->to), err, EINVAL, "invalid copy size"); + try(src->n > dest->settings->to, err, EINVAL, "invalid copy size"); try(!dest->cache, err, EINVAL, "no cache to transfer to"); memcpy(dest->cache, src->cache_a + dest->settings->ss, (dest->settings->to - dest->settings->ss) * dest->settings->stride); @@ -109,7 +111,7 @@ int cache_list_copy(struct stream * const src, struct stream * const dest) try(src->settings->access != cached || dest->settings->access != cached, err, EINVAL, "cannot cache-copy between uncached streams"); try(!src->cache, err, EINVAL, "no cache to transfer"); - try(!(src->n < dest->settings->to), err, EINVAL, "invalid copy size"); + try(!(src->n > dest->settings->to), err, EINVAL, "invalid copy size"); try(!dest->cache, err, EINVAL, "no cache to transfer to"); while ((tmp = get(src))) { @@ -125,18 +127,38 @@ err: int cache_block_split(struct stream * const src, struct stream * const A, struct stream * const B) { int ret = 0; + struct settings tmp_settings; try(src->n < 2, err, EINVAL, "cannot split single element stream."); - /* copy everything, then change whatever's neccesary */ - *A = *B = *src; - - A->n = A->n / 2 + A->n % 2; - B->n = B->n / 2; + /* setting up minimal stream basics */ + A->n = src->n / 2; + B->n = src->n / 2 + (src->n & 1ul); A->index = B->index = 0; - B->cache_a = B->cache_a + A->n; - B->cache_l = (struct entry_l *) B->cache_a; - B->cache = (char *) B->cache_a; + A->parentid = B->parentid = random(); /* generate random parent ID that needs to match between children */ + A->type = B->type = stream_invalid; /* disallow any stream operations other than split/merge on children */ + A->fd = B->fd = -1; /* if we're splitting, these are for holding cache only */ + /* we only care about these three functions for these temporary streams */ + A->get_next_element_cache = B->get_next_element_cache = src->get_next_element_cache; + A->place_next_element_cache = B->place_next_element_cache = src->place_next_element_cache; + A->split = B->split = src->split; + + tmp_settings = *src->settings; + A->settings = B->settings = &tmp_settings; + + /* setting up A */ + tmp_settings.ss = 0; + tmp_settings.to = A->n; + try_s((ret = cache_create(A)), err); + try_s((ret = cache_block_copy(src, A)), err); + + /* setting up B */ + tmp_settings.ss = A->n; + tmp_settings.to = src->n; + try_s((ret = cache_create(B)), err); + try_s((ret = cache_block_copy(src, B)), err); + + A->settings = B->settings = &tmp_settings; err: return ret; |