mirror of
https://github.com/ckolivas/lrzip.git
synced 2025-12-06 07:12:00 +01:00
add some gross bucketing to implement a queue for freeing stream_info structs after an operation has completed (in library mode ONLY; no changes will occur during regular execution) to fix some leaks
This commit is contained in:
parent
949c6d7a97
commit
63141a1035
|
|
@ -337,6 +337,10 @@ struct rzip_control {
|
|||
const char *util_infile;
|
||||
char delete_infile;
|
||||
const char *util_outfile;
|
||||
#define STREAM_BUCKET_SIZE 20
|
||||
size_t sinfo_buckets;
|
||||
size_t sinfo_idx;
|
||||
struct stream_info **sinfo_queue;
|
||||
char delete_outfile;
|
||||
FILE *outputfile;
|
||||
char library_mode : 1;
|
||||
|
|
|
|||
17
rzip.c
17
rzip.c
|
|
@ -1117,9 +1117,18 @@ retry:
|
|||
|
||||
void rzip_control_free(rzip_control *control)
|
||||
{
|
||||
if (!control) return;
|
||||
size_t x;
|
||||
if (!control) return;
|
||||
|
||||
free(control->tmpdir);
|
||||
if (control->suffix && control->suffix[0]) free(control->suffix);
|
||||
free(control);
|
||||
free(control->tmpdir);
|
||||
free(control->outname);
|
||||
free(control->outdir);
|
||||
if (control->suffix && control->suffix[0]) free(control->suffix);
|
||||
|
||||
for (x = 0; x < control->sinfo_idx; x++) {
|
||||
free(control->sinfo_queue[x]->s);
|
||||
free(control->sinfo_queue[x]);
|
||||
}
|
||||
free(control->sinfo_queue);
|
||||
free(control);
|
||||
}
|
||||
|
|
|
|||
23
stream.c
23
stream.c
|
|
@ -1797,11 +1797,28 @@ int close_stream_out(rzip_control *control, void *ss)
|
|||
for (i = 0; i < sinfo->num_streams; i++)
|
||||
rewrite_encrypted(control, sinfo, sinfo->s[i].last_headofs);
|
||||
}
|
||||
if (control->library_mode) {
|
||||
if (!control->sinfo_buckets) {
|
||||
/* no streams added */
|
||||
control->sinfo_queue = calloc(STREAM_BUCKET_SIZE + 1, sizeof(void*));
|
||||
if (!control->sinfo_queue) return -1;
|
||||
control->sinfo_buckets++;
|
||||
} else if (control->sinfo_idx == STREAM_BUCKET_SIZE * control->sinfo_buckets + 1) {
|
||||
/* all buckets full, create new bucket */
|
||||
void *tmp;
|
||||
|
||||
tmp = realloc(control->sinfo_queue, (++control->sinfo_buckets * STREAM_BUCKET_SIZE + 1) * sizeof(void*));
|
||||
if (!tmp) return -1;
|
||||
control->sinfo_queue = tmp;
|
||||
memset(control->sinfo_queue + control->sinfo_idx, 0, ((control->sinfo_buckets * STREAM_BUCKET_SIZE + 1) - control->sinfo_idx) * sizeof(void*));
|
||||
}
|
||||
control->sinfo_queue[control->sinfo_idx++] = sinfo;
|
||||
}
|
||||
#if 0
|
||||
/* These cannot be freed because their values are read after the next
|
||||
* stream has started so they're not properly freed and just dropped on
|
||||
* program exit! FIXME */
|
||||
/* These cannot be freed immediately because their values are read after the next
|
||||
* stream has started. Instead (in library mode), they are stored and only freed
|
||||
* after the entire operation has completed.
|
||||
*/
|
||||
free(sinfo->s);
|
||||
free(sinfo);
|
||||
#endif
|
||||
|
|
|
|||
Loading…
Reference in a new issue