mirror of
https://github.com/sheumann/hush.git
synced 2024-12-28 22:30:05 +00:00
patch: simplify double list helpers
function old new delta dlist_free - 29 +29 fail_hunk 130 132 +2 patch_main 1987 1982 -5 dlist_add 59 54 -5 TOY_llist_pop 9 - -9 TOY_llist_free 54 - -54 ------------------------------------------------------------------------------ (add/remove: 1/2 grow/shrink: 1/2 up/down: 31/-73) Total: -42 bytes Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
This commit is contained in:
parent
b82ae98ea4
commit
400ff226c2
@ -56,75 +56,64 @@
|
|||||||
|
|
||||||
#include "libbb.h"
|
#include "libbb.h"
|
||||||
|
|
||||||
|
|
||||||
|
// libbb candidate?
|
||||||
|
|
||||||
struct double_list {
|
struct double_list {
|
||||||
struct double_list *next;
|
struct double_list *next;
|
||||||
struct double_list *prev;
|
struct double_list *prev;
|
||||||
char *data;
|
char *data;
|
||||||
};
|
};
|
||||||
|
|
||||||
// Return the first item from the list, advancing the list (which must be called
|
|
||||||
// as &list)
|
|
||||||
static
|
|
||||||
void *TOY_llist_pop(void *list)
|
|
||||||
{
|
|
||||||
// I'd use a void ** for the argument, and even accept the typecast in all
|
|
||||||
// callers as documentation you need the &, except the stupid compiler
|
|
||||||
// would then scream about type-punned pointers. Screw it.
|
|
||||||
void **llist = (void **)list;
|
|
||||||
void **next = (void **)*llist;
|
|
||||||
*llist = *next;
|
|
||||||
|
|
||||||
return (void *)next;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Free all the elements of a linked list
|
// Free all the elements of a linked list
|
||||||
// if freeit!=NULL call freeit() on each element before freeing it.
|
// Call freeit() on each element before freeing it.
|
||||||
static
|
static
|
||||||
void TOY_llist_free(void *list, void (*freeit)(void *data))
|
void dlist_free(struct double_list *list, void (*freeit)(void *data))
|
||||||
{
|
{
|
||||||
while (list) {
|
while (list) {
|
||||||
void *pop = TOY_llist_pop(&list);
|
void *pop = list;
|
||||||
if (freeit) freeit(pop);
|
list = list->next;
|
||||||
else free(pop);
|
freeit(pop);
|
||||||
|
// Bail out also if list is circular.
|
||||||
// End doubly linked list too.
|
if (list == pop) break;
|
||||||
if (list==pop) break;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
//Override bbox's names
|
|
||||||
#define llist_pop TOY_llist_pop
|
|
||||||
#define llist_free TOY_llist_free
|
|
||||||
|
|
||||||
// Add an entry to the end off a doubly linked list
|
// Add an entry before "list" element in (circular) doubly linked list
|
||||||
static
|
static
|
||||||
struct double_list *dlist_add(struct double_list **list, char *data)
|
struct double_list *dlist_add(struct double_list **list, char *data)
|
||||||
{
|
{
|
||||||
struct double_list *line = xmalloc(sizeof(struct double_list));
|
struct double_list *llist;
|
||||||
|
struct double_list *line = xmalloc(sizeof(*line));
|
||||||
|
|
||||||
line->data = data;
|
line->data = data;
|
||||||
if (*list) {
|
llist = *list;
|
||||||
line->next = *list;
|
if (llist) {
|
||||||
line->prev = (*list)->prev;
|
struct double_list *p;
|
||||||
(*list)->prev->next = line;
|
line->next = llist;
|
||||||
(*list)->prev = line;
|
p = line->prev = llist->prev;
|
||||||
} else *list = line->next = line->prev = line;
|
// (list is circular, we assume p is never NULL)
|
||||||
|
p->next = line;
|
||||||
|
llist->prev = line;
|
||||||
|
} else
|
||||||
|
*list = line->next = line->prev = line;
|
||||||
|
|
||||||
return line;
|
return line;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
struct globals {
|
struct globals {
|
||||||
char *infile;
|
char *infile;
|
||||||
long prefix;
|
long prefix;
|
||||||
|
|
||||||
struct double_list *current_hunk;
|
struct double_list *current_hunk;
|
||||||
|
|
||||||
long oldline, oldlen, newline, newlen;
|
long oldline, oldlen, newline, newlen;
|
||||||
long linenum;
|
long linenum;
|
||||||
int context, state, filein, fileout, hunknum;
|
int context, state, hunknum;
|
||||||
|
int filein, fileout;
|
||||||
char *tempname;
|
char *tempname;
|
||||||
|
|
||||||
// was toys.foo:
|
|
||||||
int exitval;
|
int exitval;
|
||||||
};
|
};
|
||||||
#define TT (*ptr_to_globals)
|
#define TT (*ptr_to_globals)
|
||||||
@ -193,7 +182,6 @@ static void finish_oldfile(void)
|
|||||||
static void fail_hunk(void)
|
static void fail_hunk(void)
|
||||||
{
|
{
|
||||||
if (!TT.current_hunk) return;
|
if (!TT.current_hunk) return;
|
||||||
TT.current_hunk->prev->next = NULL;
|
|
||||||
|
|
||||||
fdprintf(2, "Hunk %d FAILED %ld/%ld.\n", TT.hunknum, TT.oldline, TT.newline);
|
fdprintf(2, "Hunk %d FAILED %ld/%ld.\n", TT.hunknum, TT.oldline, TT.newline);
|
||||||
TT.exitval = 1;
|
TT.exitval = 1;
|
||||||
@ -202,7 +190,8 @@ static void fail_hunk(void)
|
|||||||
// this file and advance to next file.
|
// this file and advance to next file.
|
||||||
|
|
||||||
TT.state = 2;
|
TT.state = 2;
|
||||||
llist_free(TT.current_hunk, do_line);
|
TT.current_hunk->prev->next = NULL;
|
||||||
|
dlist_free(TT.current_hunk, do_line);
|
||||||
TT.current_hunk = NULL;
|
TT.current_hunk = NULL;
|
||||||
|
|
||||||
// Abort the copy and delete the temporary file.
|
// Abort the copy and delete the temporary file.
|
||||||
@ -308,7 +297,8 @@ static int apply_one_hunk(void)
|
|||||||
fdprintf(2, "NOT: %s\n", plist->data);
|
fdprintf(2, "NOT: %s\n", plist->data);
|
||||||
|
|
||||||
TT.state = 3;
|
TT.state = 3;
|
||||||
check = llist_pop(&buf);
|
check = buf;
|
||||||
|
buf = buf->next;
|
||||||
check->prev->next = buf;
|
check->prev->next = buf;
|
||||||
buf->prev = check->prev;
|
buf->prev = check->prev;
|
||||||
do_line(check);
|
do_line(check);
|
||||||
@ -335,13 +325,13 @@ static int apply_one_hunk(void)
|
|||||||
out:
|
out:
|
||||||
// We have a match. Emit changed data.
|
// We have a match. Emit changed data.
|
||||||
TT.state = "-+"[reverse ^ dummy_revert];
|
TT.state = "-+"[reverse ^ dummy_revert];
|
||||||
llist_free(TT.current_hunk, do_line);
|
dlist_free(TT.current_hunk, do_line);
|
||||||
TT.current_hunk = NULL;
|
TT.current_hunk = NULL;
|
||||||
TT.state = 1;
|
TT.state = 1;
|
||||||
done:
|
done:
|
||||||
if (buf) {
|
if (buf) {
|
||||||
buf->prev->next = NULL;
|
buf->prev->next = NULL;
|
||||||
llist_free(buf, do_line);
|
dlist_free(buf, do_line);
|
||||||
}
|
}
|
||||||
|
|
||||||
return TT.state;
|
return TT.state;
|
||||||
|
Loading…
Reference in New Issue
Block a user