decompiled_code:
const char *__fastcall xs_find(char *s1)
{
const char *v1; // r12

v1 = (const char *)xs_head;
if ( xs_head )
{
do
{
if ( !strcmp(s1, *((const char **)v1 + 2)) )
break;
v1 = *(const char **)v1;
}
while ( v1 );
}
return v1;
}

canonical_decompiled_code:
const char *__fastcall func1(char *s1)
{
const char *v1; // r12

v1 = (const char *)xs_head;
if ( xs_head )
{
do
{
if ( !strcmp(s1, *((const char **)v1 + 2)) )
break;
v1 = *(const char **)v1;
}
while ( v1 );
}
return v1;
}

original_code:
struct extra_slot *xs_find(const char *nick)
{
 struct extra_slot *xs;
 for((xs) = ((&xs_head)->lh_first); (xs)!= ((void *)0); (xs) = ((xs)->link.le_next))
 {
  if(strcmp(nick, xs->nick) == 0)
   return xs;
 }
 return ((void *)0);
}

canonical_original_code:
struct extra_slot *xs_find(char *nick)
{
 struct extra_slot *xs;
 for((xs) = ((&xs_head)->lh_first); (xs)!= ((void *)0); (xs) = ((xs)->link.le_next))
 {
  if(strcmp(nick, xs->nick) == 0)
   return xs;
 }
 return ((void *)0);
}

return_type: struct extra_slot { struct { struct extra_slot *le_next; struct extra_slot **le_prev; } link; char *nick; char *hub_address; int extra_slots; } *


repo: rufuscoder/Shakespeer

decompiled_code:
__int64 __fastcall extra_slots_lookup(char *a1)
{
const char *v1; // rax
__int64 result; // rax

v1 = xs_find(a1);
if ( v1 )
result = *((unsigned int *)v1 + 8);
else
result = 0xFFFFFFFFLL;
return result;
}

canonical_decompiled_code:
__int64 __fastcall func2(char *a1)
{
const char *v1; // rax
__int64 result; // rax

v1 = func1(a1);
if ( v1 )
result = *((unsigned int *)v1 + 8);
else
result = 0xFFFFFFFFLL;
return result;
}

original_code:
static int extra_slots_lookup(const char *nick)
{
 struct extra_slot *xs = xs_find(nick);
 return xs ? xs->extra_slots : -1;
}

canonical_original_code:
static int extra_slots_lookup(char *nick)
{
 struct extra_slot *xs = xs_find(nick);
 return xs ? xs->extra_slots : -1;
}

variable_types:
nick
char *

variable_types: struct extra_slot { struct { struct extra_slot *le_next; struct extra_slot **le_prev; } link; char *nick; char *hub_address; int extra_slots; } *

return_type: int


decompiled_code:
void __fastcall xs_set(char *s1, int a2)
{
char *v2; // rbx
unsigned int v3; // eax
_QWORD *v4; // rbp
bool v5; // zf
size_t v6; // rax
char *v7; // rbp
char v8; // al
char *v9; // rcx
unsigned int v10; // eax
__int64 v11; // r8
const char *v12; // rsi
__int64 v13; // rdx
char *v14; // rdx
unsigned int v15; // eax
_QWORD *v16; // rax

if ( !s1 )
{
v15 = getpid();
v11 = 72LL;
v12 = "[%d] (%s:%i) assert failed: nick";
v13 = v15;
goto LABEL_11;
}
if ( a2 < 0 )
{
v10 = getpid();
v11 = 73LL;
v12 = "[%d] (%s:%i) assert failed: extra_slots >= 0";
v13 = v10;
LABEL_11:
sp_log(16LL, v12, v13, "xs_set", v11);
return;
}
v2 = s1;
v3 = getpid();
sp_log(64LL, "[%d] (%s:%i) setting %i slots for [%s]", v3, "xs_set", 75LL, (unsigned int)a2, s1);
v4 = xs_find(s1);
if ( !a2 )
{
xs_free(v4);
if ( xs_loading )
return;
goto LABEL_8;
}
if ( !v4 )
{
v4 = calloc(1uLL, 0x28uLL);
v4[2] = strdup(s1);
v16 = xs_head;
*v4 = xs_head;
if ( v16 )
v16[1] = v4;
xs_head = v4;
v4[1] = &xs_head;
}
v5 = xs_loading == 0;
*((_DWORD *)v4 + 8) = a2;
if ( v5 )
{
LABEL_8:
v6 = strlen(s1);
v7 = (char *)malloc(2 * v6 + 1);
v8 = *s1;
v9 = v7;
if ( *s1 )
{
do
{
if ( v8 == 58 )
{
*v9 = 92;
v14 = v9 + 1;
}
else
{
v14 = v9;
if ( v8 == 92 )
{
*v9 = 92;
v14 = v9 + 1;
}
}
++v2;
*v14 = v8;
v9 = v14 + 1;
v8 = *v2;
}
while ( *v2 );
}
*v9 = 0;
fprintf(xs_fp, "%s:%i\n", v7, (unsigned int)a2);
free(v7);
}
}

canonical_decompiled_code:
void __fastcall func3(char *s1, int a2)
{
char *v2; // rbx
unsigned int v3; // eax
_QWORD *v4; // rbp
bool v5; // zf
size_t v6; // rax
char *v7; // rbp
char v8; // al
char *v9; // rcx
unsigned int v10; // eax
__int64 v11; // r8
const char *v12; // rsi
__int64 v13; // rdx
char *v14; // rdx
unsigned int v15; // eax
_QWORD *v16; // rax

if ( !s1 )
{
v15 = getpid();
v11 = 72LL;
v12 = "[%d] (%s:%i) assert failed: nick";
v13 = v15;
goto LABEL_11;
}
if ( a2 < 0 )
{
v10 = getpid();
v11 = 73LL;
v12 = "[%d] (%s:%i) assert failed: extra_slots >= 0";
v13 = v10;
LABEL_11:
sp_log(16LL, v12, v13, "xs_set", v11);
return;
}
v2 = s1;
v3 = getpid();
sp_log(64LL, "[%d] (%s:%i) setting %i slots for [%s]", v3, "xs_set", 75LL, (unsigned int)a2, s1);
v4 = func1(s1);
if ( !a2 )
{
func0(v4);
if ( xs_loading )
return;
goto LABEL_8;
}
if ( !v4 )
{
v4 = calloc(1uLL, 0x28uLL);
v4[2] = strdup(s1);
v16 = xs_head;
*v4 = xs_head;
if ( v16 )
v16[1] = v4;
xs_head = v4;
v4[1] = &xs_head;
}
v5 = xs_loading == 0;
*((_DWORD *)v4 + 8) = a2;
if ( v5 )
{
LABEL_8:
v6 = strlen(s1);
v7 = (char *)malloc(2 * v6 + 1);
v8 = *s1;
v9 = v7;
if ( *s1 )
{
do
{
if ( v8 == 58 )
{
*v9 = 92;
v14 = v9 + 1;
}
else
{
v14 = v9;
if ( v8 == 92 )
{
*v9 = 92;
v14 = v9 + 1;
}
}
++v2;
*v14 = v8;
v9 = v14 + 1;
v8 = *v2;
}
while ( *v2 );
}
*v9 = 0;
fprintf(xs_fp, "%s:%i\n", v7, (unsigned int)a2);
free(v7);
}
}

original_code:
void xs_set(const char *nick, int extra_slots)
{
 do { if(!(nick)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "nick", getpid(), __func__, 72); return; } } while(0);
 do { if(!(extra_slots >= 0)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "extra_slots >= 0", getpid(), __func__, 73); return; } } while(0);
 sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "setting %i slots for [%s]", getpid(), __func__, 75, extra_slots, nick);
 struct extra_slot *xs = xs_find(nick);
 if(extra_slots == 0)
 {
  xs_free(xs);
 }
 else
 {
  if(xs == ((void *)0))
  {
   xs = calloc(1, sizeof(struct extra_slot));
   xs->nick = strdup(nick);
   do { if (((xs)->link.le_next = (&xs_head)->lh_first) != ((void *)0)) (&xs_head)->lh_first->link.le_prev = &(xs)->link.le_next; (&xs_head)->lh_first = (xs); (xs)->link.le_prev = &(&xs_head)->lh_first; } while (0);
  }
  xs->extra_slots = extra_slots;
 }
 if(!xs_loading)
 {
  char *esc_nick = malloc(strlen(nick) * 2 + 1);
  char *ep = esc_nick;
  const char *np = nick;
  for(; *np; np++)
  {
   if(*np == ':' || *np == '\\')
    *ep++ = '\\';
   *ep++ = *np;
  }
  *ep = 0;
  fprintf(xs_fp, "%s:%i\n", esc_nick, extra_slots);
  free(esc_nick);
 }
}

canonical_original_code:
void xs_set(char *nick, int extra_slots)
{
 do { if(!(nick)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "nick", getpid(), __func__, 72); return; } } while(0);
 do { if(!(extra_slots >= 0)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "extra_slots >= 0", getpid(), __func__, 73); return; } } while(0);
 sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "setting %i slots for [%s]", getpid(), __func__, 75, extra_slots, nick);
 struct extra_slot *xs = xs_find(nick);
 if(extra_slots == 0)
 {
  xs_free(xs);
 }
 else
 {
  if(xs == ((void *)0))
  {
   xs = calloc(1, sizeof(struct extra_slot));
   xs->nick = strdup(nick);
   do { if (((xs)->link.le_next = (&xs_head)->lh_first) != ((void *)0)) (&xs_head)->lh_first->link.le_prev = &(xs)->link.le_next; (&xs_head)->lh_first = (xs); (xs)->link.le_prev = &(&xs_head)->lh_first; } while (0);
  }
  xs->extra_slots = extra_slots;
 }
 if(!xs_loading)
 {
  char *esc_nick = malloc(strlen(nick) * 2 + 1);
  char *ep = esc_nick;
  char *np = nick;
  for(; *np; np++)
  {
   if(*np == ':' || *np == '\\')
    *ep++ = '\\';
   *ep++ = *np;
  }
  *ep = 0;
  fprintf(xs_fp, "%s:%i\n", esc_nick, extra_slots);
  free(esc_nick);
 }
}

variable_types:
ep
char *

variable_types:
np
char *

return_type: void

user_defined_types: struct extra_slot { struct { struct extra_slot *le_next; struct extra_slot **le_prev; } link; char *nick; char *hub_address; int extra_slots; }


decompiled_code:
void extra_slots_parse()
{
char *v0; // rbp
unsigned int v1; // ebx
char *v2; // r12
int v3; // eax
unsigned int v4; // eax
int v5; // eax
const void *v6; // r12
size_t v7; // r13
_BYTE *v8; // rax
char *v9; // rax
unsigned int v10; // eax
char *nptr; // [rsp+8h] [rbp-40h] BYREF
size_t n; // [rsp+10h] [rbp-38h] BYREF
char *endptr; // [rsp+18h] [rbp-30h] BYREF

if ( xs_fp )
{
rewind(xs_fp);
v0 = 0LL;
v1 = 0;
while ( 1 )
{
v5 = fgetln(xs_fp, &n);
v6 = (const void *)v5;
nptr = (char *)v5;
if ( !v5 )
break;
v7 = n;
++v1;
v8 = (_BYTE *)(v5 + n - 1);
if ( *v8 == 10 )
{
*v8 = 0;
}
else
{
v9 = (char *)malloc(n + 1);
v0 = v9;
if ( !v9 )
_assert_fail("lbuf", "extra_slots.c", 0x83u, "extra_slots_parse");
memcpy(v9, v6, v7);
v0[v7] = 0;
nptr = v0;
}
v2 = (char *)q_strsep(&nptr, ":");
if ( *nptr && (v3 = strtol(nptr, &endptr, 10), v3 >= 0) && endptr && !*endptr )
{
xs_set(v2, v3);
}
else
{
v4 = getpid();
sp_log(16LL, "[%d] (%s:%i) failed to parse line %u\n", v4, "extra_slots_parse", 150LL, v1);
}
}
free(v0);
}
else
{
v10 = getpid();
sp_log(16LL, "[%d] (%s:%i) assert failed: xs_fp", v10, "extra_slots_parse", 114LL);
}
}

canonical_decompiled_code:
void func4()
{
char *v0; // rbp
unsigned int v1; // ebx
char *v2; // r12
int v3; // eax
unsigned int v4; // eax
int v5; // eax
const void *v6; // r12
size_t v7; // r13
_BYTE *v8; // rax
char *v9; // rax
unsigned int v10; // eax
char *nptr; // [rsp+8h] [rbp-40h] BYREF
size_t n; // [rsp+10h] [rbp-38h] BYREF
char *endptr; // [rsp+18h] [rbp-30h] BYREF

if ( xs_fp )
{
rewind(xs_fp);
v0 = 0LL;
v1 = 0;
while ( 1 )
{
v5 = fgetln(xs_fp, &n);
v6 = (const void *)v5;
nptr = (char *)v5;
if ( !v5 )
break;
v7 = n;
++v1;
v8 = (_BYTE *)(v5 + n - 1);
if ( *v8 == 10 )
{
*v8 = 0;
}
else
{
v9 = (char *)malloc(n + 1);
v0 = v9;
if ( !v9 )
_assert_fail("lbuf", "extra_slots.c", 0x83u, "extra_slots_parse");
memcpy(v9, v6, v7);
v0[v7] = 0;
nptr = v0;
}
v2 = (char *)q_strsep(&nptr, ":");
if ( *nptr && (v3 = strtol(nptr, &endptr, 10), v3 >= 0) && endptr && !*endptr )
{
func3(v2, v3);
}
else
{
v4 = getpid();
sp_log(16LL, "[%d] (%s:%i) failed to parse line %u\n", v4, "extra_slots_parse", 150LL, v1);
}
}
free(v0);
}
else
{
v10 = getpid();
sp_log(16LL, "[%d] (%s:%i) assert failed: xs_fp", v10, "extra_slots_parse", 114LL);
}
}

original_code:
static void extra_slots_parse(void)
{
 do { if(!(xs_fp)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "xs_fp", getpid(), __func__, 114); return; } } while(0);
 rewind(xs_fp);
 unsigned line_number = 0;
 char *buf, *lbuf = ((void *)0);
 size_t len;
 while((buf = fgetln(xs_fp, &len)) != ((void *)0))
 {
  ++line_number;
  if(buf[len - 1] == '\n')
   buf[len - 1] = 0;
  else
  {
   lbuf = malloc(len + 1);
   ((void) sizeof ((lbuf) ? 1 : 0), __extension__ ({ if (lbuf) ; else __assert_fail ("lbuf", "extra_slots.c", 131, __extension__ __PRETTY_FUNCTION__); }));
   memcpy(lbuf, buf, len);
   lbuf[len] = 0;
   buf = lbuf;
  }
  char *nick = q_strsep(&buf, ":");
  if(*buf == '\0')
   goto failed;
  char *endptr;
  int extra_slots = strtol(buf, &endptr, 10);
  if(extra_slots < 0 || endptr == ((void *)0) || *endptr != 0)
   goto failed;
  xs_set(nick, extra_slots);
  continue;
failed:
  sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "failed to parse line %u\n", getpid(), __func__, 150, line_number);
 }
 free(lbuf);
}

canonical_original_code:
static void extra_slots_parse()
{
 do { if(!(xs_fp)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "xs_fp", getpid(), __func__, 114); return; } } while(0);
 rewind(xs_fp);
 unsigned int line_number = 0;
 char *buf; char *lbuf = ((void *)0);
 unsigned long len;
 while((buf = fgetln(xs_fp, &len)) != ((void *)0))
 {
  ++line_number;
  if(buf[len - 1] == '\n')
   buf[len - 1] = 0;
  else
  {
   lbuf = malloc(len + 1);
   ((void) sizeof ((lbuf) ? 1 : 0), __extension__ ({ if (lbuf) ; else __assert_fail ("lbuf", "extra_slots.c", 131, __extension__ __PRETTY_FUNCTION__); }));
   memcpy(lbuf, buf, len);
   lbuf[len] = 0;
   buf = lbuf;
  }
  char *nick = q_strsep(&buf, ":");
  if(*buf == '\0')
   goto failed;
  char *endptr;
  int extra_slots = strtol(buf, &endptr, 10);
  if(extra_slots < 0 || endptr == ((void *)0) || *endptr != 0)
   goto failed;
  xs_set(nick, extra_slots);
  continue;
failed:
  sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "failed to parse line %u\n", getpid(), __func__, 150, line_number);
 }
 free(lbuf);
}

variable_types:
buf
char *

variable_types:
lbuf
char *

variable_types:
len
unsigned long

variable_types:
endptr
char *


decompiled_code:
__int64 extra_slots_init()
{
unsigned int v0; // eax
FILE *v1; // rbp
unsigned int v3; // eax
char *ptr; // [rsp+8h] [rbp-10h] BYREF

v0 = getpid();
sp_log(64LL, "[%d] (%s:%i) opening database %s", v0, "extra_slots_init", 159LL, "slots2.db");
if ( asprintf(&ptr, "%s/%s", global_working_directory, "slots2.db") == -1 )
{
v3 = getpid();
sp_log(64LL, "[%d] (%s:%i) asprintf did not return anything", v3, "extra_slots_init", 164LL);
}
v1 = fopen64(ptr, "a+");
xs_fp = v1;
free(ptr);
if ( v1 )
{
xs_loading = 1;
extra_slots_parse();
xs_loading = 0;
v1 = xs_fp;
}
setvbuf(v1, 0LL, 1, 0LL);
return 0LL;
}

canonical_decompiled_code:
__int64 func5()
{
unsigned int v0; // eax
FILE *v1; // rbp
unsigned int v3; // eax
char *ptr; // [rsp+8h] [rbp-10h] BYREF

v0 = getpid();
sp_log(64LL, "[%d] (%s:%i) opening database %s", v0, "extra_slots_init", 159LL, "slots2.db");
if ( asprintf(&ptr, "%s/%s", global_working_directory, "slots2.db") == -1 )
{
v3 = getpid();
sp_log(64LL, "[%d] (%s:%i) asprintf did not return anything", v3, "extra_slots_init", 164LL);
}
v1 = fopen64(ptr, "a+");
xs_fp = v1;
free(ptr);
if ( v1 )
{
xs_loading = 1;
func4();
xs_loading = 0;
v1 = xs_fp;
}
setvbuf(v1, 0LL, 1, 0LL);
return 0LL;
}

original_code:
int extra_slots_init(void)
{
 sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "opening database %s", getpid(), __func__, 159, "slots2.db");
 char *fname;
 int num_returned_bytes = asprintf(&fname, "%s/%s", global_working_directory, "slots2.db");
 if (num_returned_bytes == -1)
        sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "asprintf did not return anything", getpid(), __func__, 164);
 xs_fp = fopen(fname, "a+");
 free(fname);
 if (xs_fp) {
  xs_loading = 1;
  extra_slots_parse();
  xs_loading = 0;
 }
 setvbuf(xs_fp, ((void *)0), 1, 0);
 return 0;
}

canonical_original_code:
int extra_slots_init()
{
 sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "opening database %s", getpid(), __func__, 159, "slots2.db");
 char *fname;
 int num_returned_bytes = asprintf(&fname, "%s/%s", global_working_directory, "slots2.db");
 if (num_returned_bytes == -1)
        sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "asprintf did not return anything", getpid(), __func__, 164);
 xs_fp = fopen(fname, "a+");
 free(fname);
 if (xs_fp) {
  xs_loading = 1;
  extra_slots_parse();
  xs_loading = 0;
 }
 setvbuf(xs_fp, ((void *)0), 1, 0);
 return 0;
}

variable_types:
fname
char *


decompiled_code:
__int64 extra_slots_close()
{
void *v0; // rdi
__int64 result; // rax

v0 = xs_head;
for ( xs_loading = 1; xs_head; v0 = xs_head )
xs_free(v0);
fclose(xs_fp);
result = 0LL;
xs_fp = 0LL;
return result;
}

canonical_decompiled_code:
__int64 func6()
{
void *v0; // rdi
__int64 result; // rax

v0 = xs_head;
for ( xs_loading = 1; xs_head; v0 = xs_head )
func0(v0);
fclose(xs_fp);
result = 0LL;
xs_fp = 0LL;
return result;
}

original_code:
int extra_slots_close(void)
{
 xs_loading = 1;
 struct extra_slot *xs;
 while((xs = ((&xs_head)->lh_first)) != ((void *)0))
  xs_free(xs);
 fclose(xs_fp);
 xs_fp = ((void *)0);
 return 0;
}

canonical_original_code:
int extra_slots_close()
{
 xs_loading = 1;
 struct extra_slot *xs;
 while((xs = ((&xs_head)->lh_first)) != ((void *)0))
  xs_free(xs);
 fclose(xs_fp);
 xs_fp = ((void *)0);
 return 0;
}


decompiled_code:
__int64 __fastcall extra_slots_grant(char *s1, int a2)
{
int v2; // er12
const char *v3; // rax
int v4; // edx
__int64 v5; // rax
__int64 result; // rax
unsigned int v7; // eax
unsigned int v8; // eax
unsigned int v9; // eax
unsigned int v10; // eax

if ( xs_fp )
{
if ( s1 )
{
v2 = a2;
if ( a2 )
{
v3 = xs_find(s1);
if ( v3 )
{
v4 = 0;
if ( *((int *)v3 + 8) >= 0 )
v4 = *((_DWORD *)v3 + 8);
v2 = v4 + a2;
}
if ( v2 < 0 )
{
v8 = getpid();
sp_log(16LL, "[%d] (%s:%i) assert failed: extra_slots >= 0", v8, "extra_slots_grant", 212LL);
result = 0xFFFFFFFFLL;
}
else
{
xs_set(s1, v2);
v5 = nc_default();
nc_send_extra_slot_granted_notification(v5, s1, (unsigned int)v2);
result = 0LL;
}
}
else
{
v7 = getpid();
sp_log(16LL, "[%d] (%s:%i) assert failed: delta != 0", v7, "extra_slots_grant", 203LL);
result = 0LL;
}
}
else
{
v9 = getpid();
sp_log(16LL, "[%d] (%s:%i) assert failed: nick", v9, "extra_slots_grant", 202LL);
result = 0xFFFFFFFFLL;
}
}
else
{
v10 = getpid();
sp_log(16LL, "[%d] (%s:%i) assert failed: xs_fp", v10, "extra_slots_grant", 201LL);
result = 0xFFFFFFFFLL;
}
return result;
}

canonical_decompiled_code:
__int64 __fastcall func7(char *s1, int a2)
{
int v2; // er12
const char *v3; // rax
int v4; // edx
__int64 v5; // rax
__int64 result; // rax
unsigned int v7; // eax
unsigned int v8; // eax
unsigned int v9; // eax
unsigned int v10; // eax

if ( xs_fp )
{
if ( s1 )
{
v2 = a2;
if ( a2 )
{
v3 = func1(s1);
if ( v3 )
{
v4 = 0;
if ( *((int *)v3 + 8) >= 0 )
v4 = *((_DWORD *)v3 + 8);
v2 = v4 + a2;
}
if ( v2 < 0 )
{
v8 = getpid();
sp_log(16LL, "[%d] (%s:%i) assert failed: extra_slots >= 0", v8, "extra_slots_grant", 212LL);
result = 0xFFFFFFFFLL;
}
else
{
func3(s1, v2);
v5 = nc_default();
nc_send_extra_slot_granted_notification(v5, s1, (unsigned int)v2);
result = 0LL;
}
}
else
{
v7 = getpid();
sp_log(16LL, "[%d] (%s:%i) assert failed: delta != 0", v7, "extra_slots_grant", 203LL);
result = 0LL;
}
}
else
{
v9 = getpid();
sp_log(16LL, "[%d] (%s:%i) assert failed: nick", v9, "extra_slots_grant", 202LL);
result = 0xFFFFFFFFLL;
}
}
else
{
v10 = getpid();
sp_log(16LL, "[%d] (%s:%i) assert failed: xs_fp", v10, "extra_slots_grant", 201LL);
result = 0xFFFFFFFFLL;
}
return result;
}

original_code:
int extra_slots_grant(const char *nick, int delta)
{
 do { if(!(xs_fp)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "xs_fp", getpid(), __func__, 201); return (-1); } } while(0);
 do { if(!(nick)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "nick", getpid(), __func__, 202); return (-1); } } while(0);
 do { if(!(delta != 0)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "delta != 0", getpid(), __func__, 203); return (0); } } while(0);
 struct extra_slot *xs = xs_find(nick);
 int extra_slots = 0;
 if(xs && xs->extra_slots > 0)
  extra_slots = xs->extra_slots;
 extra_slots += delta;
 do { if(!(extra_slots >= 0)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "extra_slots >= 0", getpid(), __func__, 212); return (-1); } } while(0);
 xs_set(nick, extra_slots);
 nc_send_extra_slot_granted_notification(nc_default(), nick, extra_slots);
 return 0;
}

canonical_original_code:
int extra_slots_grant(char *nick, int delta)
{
 do { if(!(xs_fp)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "xs_fp", getpid(), __func__, 201); return (-1); } } while(0);
 do { if(!(nick)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "nick", getpid(), __func__, 202); return (-1); } } while(0);
 do { if(!(delta != 0)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "delta != 0", getpid(), __func__, 203); return (0); } } while(0);
 struct extra_slot *xs = xs_find(nick);
 int extra_slots = 0;
 if(xs && xs->extra_slots > 0)
  extra_slots = xs->extra_slots;
 extra_slots += delta;
 do { if(!(extra_slots >= 0)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "extra_slots >= 0", getpid(), __func__, 212); return (-1); } } while(0);
 xs_set(nick, extra_slots);
 nc_send_extra_slot_granted_notification(nc_default(), nick, extra_slots);
 return 0;
}

variable_types: delta int


decompiled_code:
__int64 __fastcall extra_slots_get_for_user(char *a1)
{
__int64 result; // rax

result = extra_slots_lookup(a1);
if ( (int)result < 0 )
result = 0LL;
return result;
}

canonical_decompiled_code:
__int64 __fastcall func8(char *a1)
{
__int64 result; // rax

result = func2(a1);
if ( (int)result < 0 )
result = 0LL;
return result;
}

original_code:
unsigned extra_slots_get_for_user(const char *nick)
{
 int s = extra_slots_lookup(nick);
 if(s < 0)
  s = 0;
 return s;
}

canonical_original_code:
unsigned int extra_slots_get_for_user(char *nick)
{
 int s = extra_slots_lookup(nick);
 if(s < 0)
  s = 0;
 return s;
}

variable_types: s int

return_type: unsigned int


decompiled_code:
__int64 __fastcall is_recently_searched(char *s2)
{
const char **v1; // rbx

v1 = (const char **)recent_searches_head;
if ( !recent_searches_head )
return 0LL;
while ( strcmp(*v1, s2) )
{
v1 = (const char **)v1[1];
if ( !v1 )
return 0LL;
}
return 1LL;
}

canonical_decompiled_code:
__int64 __fastcall func0(char *s2)
{
const char **v1; // rbx

v1 = (const char **)recent_searches_head;
if ( !recent_searches_head )
return 0LL;
while ( strcmp(*v1, s2) )
{
v1 = (const char **)v1[1];
if ( !v1 )
return 0LL;
}
return 1LL;
}

original_code:
static _Bool is_recently_searched(const char *tth)
{
    struct recent_search_entry *e;
    for((e) = ((&recent_searches_head)->tqh_first); (e) != ((void *)0); (e) = ((e)->link.tqe_next))
    {
        if(strcmp(e->tth, tth) == 0)
        {
            return 1;
        }
    }
    return 0;
}

canonical_original_code:
static _Bool is_recently_searched(char *tth)
{
    struct recent_search_entry *e;
    for((e) = ((&recent_searches_head)->tqh_first); (e) != ((void *)0); (e) = ((e)->link.tqe_next))
    {
        if(strcmp(e->tth, tth) == 0)
        {
            return 1;
        }
    }
    return 0;
}

variable_types:
tth
char *

variable_types: struct recent_search_entry { char *tth; struct { struct recent_search_entry *tqe_next; struct recent_search_entry **tqe_prev; } link; } *


decompiled_code:
char *queue_auto_search_get_tth()
{
int v0; // ebx
void **v1; // rbp
__int64 v2; // rax
_QWORD *v3; // rdx
__int64 *v4; // r12
unsigned int v5; // er13
__int64 *v6; // rbx
int v7; // ebp
char *v8; // r12
unsigned int v9; // eax
_QWORD *v10; // rax
__int64 *v11; // rdx
char *result; // rax
unsigned int v13; // eax

v0 = num_recent_searches - 1;
if ( num_recent_searches > 30 )
{
do
{
v1 = (void **)recent_searches_head;
v2 = *((_QWORD *)recent_searches_head + 1);
v3 = (_QWORD *)*((_QWORD *)recent_searches_head + 2);
if ( v2 )
*(_QWORD *)(v2 + 16) = v3;
else
off_388 = (__int64 *)*((_QWORD *)recent_searches_head + 2);
*v3 = v2;
free(*v1);
free(v1);
num_recent_searches = v0--;
}
while ( v0 != 29 );
}
v4 = 0LL;
v5 = 0;
v6 = *(__int64 **)(q_store + 24LL);
if ( !v6 )
goto LABEL_21;
do
{
if ( *((_BYTE *)v6 + 24) )
{
v7 = *((_DWORD *)v6 + 24);
if ( v7 )
{
if ( !(unsigned __int8)is_recently_searched((char *)v6 + 24) )
{
++v5;
if ( v4 && (v6[10] & 1) != 0 && v7 <= *((_DWORD *)v4 + 24) )
{
if ( v6[9] > (unsigned __int64)v4[9] )
v4 = v6;
}
else
{
v4 = v6;
}
}
}
}
v6 = (__int64 *)*v6;
}
while ( v6 );
if ( v4 )
{
v8 = strdup((const char *)v4 + 24);
v9 = getpid();
sp_log(64LL, "[%d] (%s:%i) found tth [%s]", v9, "queue_auto_search_get_tth", 116LL, v8);
v10 = calloc(1uLL, 0x18uLL);
v11 = off_388;
++num_recent_searches;
*v10 = v8;
v10[1] = 0LL;
v10[2] = v11;
*v11 = (__int64)v10;
off_388 = v10 + 1;
result = v8;
}
else
{
LABEL_21:
v13 = getpid();
sp_log(
64LL,
"[%d] (%s:%i) found no candidates for auto-search (%i possible)",
v13,
"queue_auto_search_get_tth",
125LL,
v5);
result = 0LL;
}
return result;
}

canonical_decompiled_code:
char *func1()
{
int v0; // ebx
void **v1; // rbp
__int64 v2; // rax
_QWORD *v3; // rdx
__int64 *v4; // r12
unsigned int v5; // er13
__int64 *v6; // rbx
int v7; // ebp
char *v8; // r12
unsigned int v9; // eax
_QWORD *v10; // rax
__int64 *v11; // rdx
char *result; // rax
unsigned int v13; // eax

v0 = num_recent_searches - 1;
if ( num_recent_searches > 30 )
{
do
{
v1 = (void **)recent_searches_head;
v2 = *((_QWORD *)recent_searches_head + 1);
v3 = (_QWORD *)*((_QWORD *)recent_searches_head + 2);
if ( v2 )
*(_QWORD *)(v2 + 16) = v3;
else
off_388 = (__int64 *)*((_QWORD *)recent_searches_head + 2);
*v3 = v2;
free(*v1);
free(v1);
num_recent_searches = v0--;
}
while ( v0 != 29 );
}
v4 = 0LL;
v5 = 0;
v6 = *(__int64 **)(q_store + 24LL);
if ( !v6 )
goto LABEL_21;
do
{
if ( *((_BYTE *)v6 + 24) )
{
v7 = *((_DWORD *)v6 + 24);
if ( v7 )
{
if ( !(unsigned __int8)func0((char *)v6 + 24) )
{
++v5;
if ( v4 && (v6[10] & 1) != 0 && v7 <= *((_DWORD *)v4 + 24) )
{
if ( v6[9] > (unsigned __int64)v4[9] )
v4 = v6;
}
else
{
v4 = v6;
}
}
}
}
v6 = (__int64 *)*v6;
}
while ( v6 );
if ( v4 )
{
v8 = strdup((const char *)v4 + 24);
v9 = getpid();
sp_log(64LL, "[%d] (%s:%i) found tth [%s]", v9, "queue_auto_search_get_tth", 116LL, v8);
v10 = calloc(1uLL, 0x18uLL);
v11 = off_388;
++num_recent_searches;
*v10 = v8;
v10[1] = 0LL;
v10[2] = v11;
*v11 = (__int64)v10;
off_388 = v10 + 1;
result = v8;
}
else
{
LABEL_21:
v13 = getpid();
sp_log(
64LL,
"[%d] (%s:%i) found no candidates for auto-search (%i possible)",
v13,
"queue_auto_search_get_tth",
125LL,
v5);
result = 0LL;
}
return result;
}

original_code:
static char *queue_auto_search_get_tth(void)
{
    while(num_recent_searches > 30)
    {
        struct recent_search_entry *e = ((&recent_searches_head)->tqh_first);
        do { if (((e)->link.tqe_next) != ((void *)0)) (e)->link.tqe_next->link.tqe_prev = (e)->link.tqe_prev; else (&recent_searches_head)->tqh_last = (e)->link.tqe_prev; *(e)->link.tqe_prev = (e)->link.tqe_next; } while (0);
        free(e->tth);
        free(e);
        --num_recent_searches;
    }
    int ncandidates = 0;
    queue_target_t *qt_candidate = ((void *)0);
    struct queue_target *qt;
    for((qt) = ((&q_store->targets)->tqh_first); (qt) != ((void *)0); (qt) = ((qt)->link.tqe_next))
    {
        if(qt->tth[0] == 0)
            continue;
        if(qt->priority == 0)
            continue;
        if(is_recently_searched(qt->tth))
            continue;
        ncandidates++;
        if(qt_candidate == ((void *)0) ||
           (qt->flags & 1) == 0 ||
           qt->priority > qt_candidate->priority ||
           qt->size > qt_candidate->size)
        {
            qt_candidate = qt;
        }
    }
    char *tth = 0;
    if(qt_candidate)
    {
        tth = strdup(qt_candidate->tth);
        sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "found tth [%s]", getpid(), __func__, 116, tth);
        struct recent_search_entry *e = calloc(1,
     sizeof(struct recent_search_entry));
        e->tth = tth;
        do { (e)->link.tqe_next = ((void *)0); (e)->link.tqe_prev = (&recent_searches_head)->tqh_last; *(&recent_searches_head)->tqh_last = (e); (&recent_searches_head)->tqh_last = &(e)->link.tqe_next; } while (0);
        ++num_recent_searches;
    }
    else
    {
        sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "found no candidates for auto-search (%i possible)", getpid(), __func__, 125, ncandidates);
    }
    return tth;
}

canonical_original_code:
static char *queue_auto_search_get_tth()
{
    while(num_recent_searches > 30)
    {
        struct recent_search_entry *e = ((&recent_searches_head)->tqh_first);
        do { if (((e)->link.tqe_next) != ((void *)0)) (e)->link.tqe_next->link.tqe_prev = (e)->link.tqe_prev; else (&recent_searches_head)->tqh_last = (e)->link.tqe_prev; *(e)->link.tqe_prev = (e)->link.tqe_next; } while (0);
        free(e->tth);
        free(e);
        --num_recent_searches;
    }
    int ncandidates = 0;
    struct queue_target *qt_candidate = ((void *)0);
    struct queue_target *qt;
    for((qt) = ((&q_store->targets)->tqh_first); (qt) != ((void *)0); (qt) = ((qt)->link.tqe_next))
    {
        if(qt->tth[0] == 0)
            continue;
        if(qt->priority == 0)
            continue;
        if(is_recently_searched(qt->tth))
            continue;
        ncandidates++;
        if(qt_candidate == ((void *)0) ||
           (qt->flags & 1) == 0 ||
           qt->priority > qt_candidate->priority ||
           qt->size > qt_candidate->size)
        {
            qt_candidate = qt;
        }
    }
    char *tth = 0;
    if(qt_candidate)
    {
        tth = strdup(qt_candidate->tth);
        sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "found tth [%s]", getpid(), __func__, 116, tth);
        struct recent_search_entry *e = calloc(1,
     sizeof(struct recent_search_entry));
        e->tth = tth;
        do { (e)->link.tqe_next = ((void *)0); (e)->link.tqe_prev = (&recent_searches_head)->tqh_last; *(&recent_searches_head)->tqh_last = (e); (&recent_searches_head)->tqh_last = &(e)->link.tqe_next; } while (0);
        ++num_recent_searches;
    }
    else
    {
        sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "found no candidates for auto-search (%i possible)", getpid(), __func__, 125, ncandidates);
    }
    return tth;
}

variable_types: ncandidates int

variable_types: struct queue_target { struct { struct queue_target *tqe_next; struct queue_target **tqe_prev; } link; char *filename; char tth[40]; char *target_directory; unsigned long size; unsigned int flags; long ctime; int priority; unsigned int seq; } *

return_type: char *

user_defined_types: struct recent_search_entry { char *tth; struct { struct recent_search_entry *tqe_next; struct recent_search_entry **tqe_prev; } link; }


decompiled_code:
__int64 queue_auto_search_init()
{
__int64 result; // rax

if ( global_auto_search_sources )
result = queue_schedule_auto_search_sources(1);
return result;
}

canonical_decompiled_code:
__int64 func4()
{
__int64 result; // rax

if ( global_auto_search_sources )
result = func2(1);
return result;
}

original_code:
void queue_auto_search_init(void)
{
    if(global_auto_search_sources)
    {
        queue_schedule_auto_search_sources(1);
    }
}

canonical_original_code:
void queue_auto_search_init()
{
    if(global_auto_search_sources)
    {
        queue_schedule_auto_search_sources(1);
    }
}


decompiled_code:
__int64 __fastcall share_tth_init_notifications(__int64 a1)
{
__int64 v1; // rax

v1 = nc_default();
return nc_add_tth_available_observer(v1, handle_tth_available_notification, a1);
}

canonical_decompiled_code:
__int64 __fastcall func1(__int64 a1)
{
__int64 v1; // rax

v1 = nc_default();
return nc_add_tth_available_observer(v1, handle_tth_available_notification, a1);
}

original_code:
void share_tth_init_notifications(share_t *share)
{
    nc_add_tth_available_observer(nc_default(),
            handle_tth_available_notification,
            share);
}

canonical_original_code:
void share_tth_init_notifications(struct share *share)
{
    nc_add_tth_available_observer(nc_default(),
            handle_tth_available_notification,
            share);
}

variable_types: struct share { struct { struct share_mountpoint { struct { struct share_mountpoint *le_next; struct share_mountpoint **le_prev; } link; char *local_root; char *virtual_root; struct share_stats { unsigned long size; unsigned long totsize; unsigned long dupsize; unsigned int nfiles; unsigned int ntotfiles; unsigned int nduplicates; } stats; _Bool scan_in_progress; _Bool removed; } *lh_first; } mountpoints; _Bool uptodate; int scanning; struct bloom { unsigned int length; unsigned char *filter; unsigned int collisions; } *bloom; char *cid; unsigned int listlen; struct file_tree { struct share_file { struct { struct share_file *rbe_left; struct share_file *rbe_right; struct share_file *rbe_parent; int rbe_color; } entry; struct { struct share_file *le_next; struct share_file **le_prev; } inode_link; struct { struct share_file *sle_next; } link; struct share_mountpoint *mp; char *partial_path; enum share_type { SHARE_TYPE_ANY=1, SHARE_TYPE_AUDIO=2, SHARE_TYPE_COMPRESSED=3, SHARE_TYPE_DOCUMENT=4, SHARE_TYPE_EXECUTABLE=5, SHARE_TYPE_IMAGE=6, SHARE_TYPE_MOVIE=7, SHARE_TYPE_DIRECTORY=8, SHARE_TYPE_TTH=9 } type; unsigned long size; unsigned long inode; } *rbh_root; } files; struct file_tree unhashed_files; struct { struct share_file *lh_first; } inodes[509]; } *

user_defined_types: struct share { struct { struct share_mountpoint *lh_first; } mountpoints; _Bool uptodate; int scanning; struct bloom *bloom; char *cid; unsigned int listlen; struct file_tree files; struct file_tree unhashed_files; struct { struct share_file *lh_first; } inodes[509]; }

user_defined_types: struct file_tree { struct share_file *rbh_root; }

user_defined_types: struct share_mountpoint { struct { struct share_mountpoint *le_next; struct share_mountpoint **le_prev; } link; char *local_root; char *virtual_root; struct share_stats stats; _Bool scan_in_progress; _Bool removed; }

user_defined_types: struct share_file { struct { struct share_file *rbe_left; struct share_file *rbe_right; struct share_file *rbe_parent; int rbe_color; } entry; struct { struct share_file *le_next; struct share_file **le_prev; } inode_link; struct { struct share_file *sle_next; } link; struct share_mountpoint *mp; char *partial_path; enum share_type type; unsigned long size; unsigned long inode; }


decompiled_code:
__int64 __fastcall handle_tth_available_notification(__int64 a1, __int64 a2, _QWORD *a3, __int64 a4)
{
_QWORD *v6; // r13
char *v7; // r12
__int64 v8; // r14
__int64 v9; // rax
__int64 v10; // rdx
int *v12; // rax
char *v13; // rbx
unsigned int v14; // eax
unsigned int v15; // eax
unsigned int v16; // eax
__int64 v17; // rax
const char *v18; // r12
char *v19; // rax
struct stat64 v20; // [rsp+0h] [rbp-B8h] BYREF

v6 = (_QWORD *)*a3;
v7 = (char *)share_complete_path(*a3);
if ( share_lookup_unhashed_file(a4, v7) )
{
file_tree_RB_REMOVE(a4 + 48, v6);
}
else
{
v15 = getpid();
sp_log(16LL, "[%d] (%s:%i) File [%s] not in unhashed tree!?", v15, "handle_tth_available_notification", 52LL, v7);
}
if ( !a3[1] )
goto LABEL_8;
if ( stat64(v7, &v20) )
{
v12 = _errno_location();
v13 = strerror(*v12);
v14 = getpid();
sp_log(16LL, "[%d] (%s:%i) %s: failed to lookup mtime: %s", v14, "handle_tth_available_notification", 69LL, v7, v13);
goto LABEL_8;
}
v8 = tth_store_lookup(global_tth_store, a3[1]);
if ( v8 )
{
tth_store_add_inode(global_tth_store, v6[11], v20.st_mtim.tv_sec, a3[1]);
*(_BYTE *)(a4 + 8) = 0;
if ( share_lookup_file_by_inode(a4, *(_QWORD *)(v8 + 32)) )
{
v9 = v6[7];
v10 = v6[10];
++*(_DWORD *)(v9 + 64);
*(_QWORD *)(v9 + 48) += v10;
LABEL_8:
free(v7);
share_remove_from_inode_table(a4, v6);
return share_file_free(v6);
}
tth_store_set_active_inode(global_tth_store, a3[1], v6[11]);
}
else
{
tth_store_add_entry(global_tth_store, a3[1], a3[2], 0LL);
tth_store_add_inode(global_tth_store, v6[11], v20.st_mtim.tv_sec, a3[1]);
*(_BYTE *)(a4 + 8) = 0;
tth_store_set_active_inode(global_tth_store, a3[1], v6[11]);
}
if ( share_lookup_file(a4, v7) )
{
v16 = getpid();
sp_log(16LL, "[%d] (%s:%i) File [%s] already in hashed tree!?", v16, "handle_tth_available_notification", 120LL, v7);
}
else
{
file_tree_RB_INSERT(a4 + 40, v6);
}
free(v7);
v17 = v6[7];
v18 = (const char *)v6[8];
*(_QWORD *)(v17 + 32) += v6[10];
++*(_DWORD *)(v17 + 56);
v19 = strrchr(v18, 47);
if ( v19 )
v18 = v19 + 1;
return bloom_add_filename(*(_QWORD *)(a4 + 16), v18);
}

canonical_decompiled_code:
__int64 __fastcall func0(__int64 a1, __int64 a2, _QWORD *a3, __int64 a4)
{
_QWORD *v6; // r13
char *v7; // r12
__int64 v8; // r14
__int64 v9; // rax
__int64 v10; // rdx
int *v12; // rax
char *v13; // rbx
unsigned int v14; // eax
unsigned int v15; // eax
unsigned int v16; // eax
__int64 v17; // rax
const char *v18; // r12
char *v19; // rax
struct stat64 v20; // [rsp+0h] [rbp-B8h] BYREF

v6 = (_QWORD *)*a3;
v7 = (char *)share_complete_path(*a3);
if ( share_lookup_unhashed_file(a4, v7) )
{
file_tree_RB_REMOVE(a4 + 48, v6);
}
else
{
v15 = getpid();
sp_log(16LL, "[%d] (%s:%i) File [%s] not in unhashed tree!?", v15, "handle_tth_available_notification", 52LL, v7);
}
if ( !a3[1] )
goto LABEL_8;
if ( stat64(v7, &v20) )
{
v12 = _errno_location();
v13 = strerror(*v12);
v14 = getpid();
sp_log(16LL, "[%d] (%s:%i) %s: failed to lookup mtime: %s", v14, "handle_tth_available_notification", 69LL, v7, v13);
goto LABEL_8;
}
v8 = tth_store_lookup(global_tth_store, a3[1]);
if ( v8 )
{
tth_store_add_inode(global_tth_store, v6[11], v20.st_mtim.tv_sec, a3[1]);
*(_BYTE *)(a4 + 8) = 0;
if ( share_lookup_file_by_inode(a4, *(_QWORD *)(v8 + 32)) )
{
v9 = v6[7];
v10 = v6[10];
++*(_DWORD *)(v9 + 64);
*(_QWORD *)(v9 + 48) += v10;
LABEL_8:
free(v7);
share_remove_from_inode_table(a4, v6);
return share_file_free(v6);
}
tth_store_set_active_inode(global_tth_store, a3[1], v6[11]);
}
else
{
tth_store_add_entry(global_tth_store, a3[1], a3[2], 0LL);
tth_store_add_inode(global_tth_store, v6[11], v20.st_mtim.tv_sec, a3[1]);
*(_BYTE *)(a4 + 8) = 0;
tth_store_set_active_inode(global_tth_store, a3[1], v6[11]);
}
if ( share_lookup_file(a4, v7) )
{
v16 = getpid();
sp_log(16LL, "[%d] (%s:%i) File [%s] already in hashed tree!?", v16, "handle_tth_available_notification", 120LL, v7);
}
else
{
file_tree_RB_INSERT(a4 + 40, v6);
}
free(v7);
v17 = v6[7];
v18 = (const char *)v6[8];
*(_QWORD *)(v17 + 32) += v6[10];
++*(_DWORD *)(v17 + 56);
v19 = strrchr(v18, 47);
if ( v19 )
v18 = v19 + 1;
return bloom_add_filename(*(_QWORD *)(a4 + 16), v18);
}

original_code:
static void handle_tth_available_notification(nc_t *nc,
        const char *channel,
        nc_tth_available_t *notification,
        void *user_data)
{
    share_t *share = user_data;
    share_file_t *file = notification->file;
    char *local_path = share_complete_path(file);
    if(share_lookup_unhashed_file(share, local_path) != ((void *)0))
 file_tree_RB_REMOVE(&share->unhashed_files, file);
    else
 sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "File [%s] not in unhashed tree!?", getpid(), __func__, 52, local_path);
    if(notification->tth == ((void *)0))
    {
 goto fail;
    }
    struct stat stbuf;
    if(stat(local_path, &stbuf) != 0)
    {
 sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "%s: failed to lookup mtime: %s", getpid(), __func__, 69, local_path, strerror((*__errno_location ())));
 goto fail;
    }
    struct tth_entry *te = tth_store_lookup(global_tth_store,
 notification->tth);
    if(te == ((void *)0))
    {
 tth_store_add_entry(global_tth_store,
     notification->tth,
     notification->leafdata_base64,
     0);
    }
    tth_store_add_inode(global_tth_store,
 file->inode, stbuf.st_mtim.tv_sec, notification->tth);
    share->uptodate = 0;
    if(te == ((void *)0))
    {
 tth_store_set_active_inode(global_tth_store,
  notification->tth, file->inode);
    }
    else
    {
 share_file_t *original_file =
     share_lookup_file_by_inode(share, te->active_inode);
 if(original_file)
 {
     file->mp->stats.nduplicates++;
     file->mp->stats.dupsize += file->size;
     goto fail;
 }
 else
 {
     tth_store_set_active_inode(global_tth_store,
  notification->tth, file->inode);
 }
    }
    if(share_lookup_file(share, local_path))
        sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "File [%s] already in hashed tree!?", getpid(), __func__, 120, local_path);
    else
    {
        file_tree_RB_INSERT(&share->files, file);
    }
    free(local_path);
    file->mp->stats.size += file->size;
    file->mp->stats.nfiles++;
    char *filename = strrchr(file->partial_path, '/');
    if(filename++ == ((void *)0))
 filename = file->partial_path;
    bloom_add_filename(share->bloom, filename);
    return;
fail:
    free(local_path);
    share_remove_from_inode_table(share, file);
    share_file_free(file);
}

canonical_original_code:
static void handle_tth_available_notification(struct notification_center *nc, char *channel, struct nc_tth_available *notification, void *user_data)
{
    struct share *share = user_data;
    struct share_file *file = notification->file;
    char *local_path = share_complete_path(file);
    if(share_lookup_unhashed_file(share, local_path) != ((void *)0))
 file_tree_RB_REMOVE(&share->unhashed_files, file);
    else
 sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "File [%s] not in unhashed tree!?", getpid(), __func__, 52, local_path);
    if(notification->tth == ((void *)0))
    {
 goto fail;
    }
    struct stat stbuf;
    if(stat(local_path, &stbuf) != 0)
    {
 sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "%s: failed to lookup mtime: %s", getpid(), __func__, 69, local_path, strerror((*__errno_location ())));
 goto fail;
    }
    struct tth_entry *te = tth_store_lookup(global_tth_store,
 notification->tth);
    if(te == ((void *)0))
    {
 tth_store_add_entry(global_tth_store,
     notification->tth,
     notification->leafdata_base64,
     0);
    }
    tth_store_add_inode(global_tth_store,
 file->inode, stbuf.st_mtim.tv_sec, notification->tth);
    share->uptodate = 0;
    if(te == ((void *)0))
    {
 tth_store_set_active_inode(global_tth_store,
  notification->tth, file->inode);
    }
    else
    {
 struct share_file *original_file = share_lookup_file_by_inode(share, te->active_inode);
 if(original_file)
 {
     file->mp->stats.nduplicates++;
     file->mp->stats.dupsize += file->size;
     goto fail;
 }
 else
 {
     tth_store_set_active_inode(global_tth_store,
  notification->tth, file->inode);
 }
    }
    if(share_lookup_file(share, local_path))
        sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "File [%s] already in hashed tree!?", getpid(), __func__, 120, local_path);
    else
    {
        file_tree_RB_INSERT(&share->files, file);
    }
    free(local_path);
    file->mp->stats.size += file->size;
    file->mp->stats.nfiles++;
    char *filename = strrchr(file->partial_path, '/');
    if(filename++ == ((void *)0))
 filename = file->partial_path;
    bloom_add_filename(share->bloom, filename);
    return;
fail:
    free(local_path);
    share_remove_from_inode_table(share, file);
    share_file_free(file);
}

variable_types: struct notification_center { struct { struct nc_observer { char *channel; void (*callback)(struct notification_center *nc, char *channel, void *data, void *user_data); void *user_data; struct { struct nc_observer *le_next; struct nc_observer **le_prev; } next; } *lh_first; } observers; } *

variable_types:
channel
char *

variable_types: struct nc_tth_available { void *file; char *tth; char *leafdata_base64; double mibs_per_sec; } *

variable_types: struct share_file { struct { struct share_file *rbe_left; struct share_file *rbe_right; struct share_file *rbe_parent; int rbe_color; } entry; struct { struct share_file *le_next; struct share_file **le_prev; } inode_link; struct { struct share_file *sle_next; } link; struct share_mountpoint { struct { struct share_mountpoint *le_next; struct share_mountpoint **le_prev; } link; char *local_root; char *virtual_root; struct share_stats { unsigned long size; unsigned long totsize; unsigned long dupsize; unsigned int nfiles; unsigned int ntotfiles; unsigned int nduplicates; } stats; _Bool scan_in_progress; _Bool removed; } *mp; char *partial_path; enum share_type { SHARE_TYPE_ANY=1, SHARE_TYPE_AUDIO=2, SHARE_TYPE_COMPRESSED=3, SHARE_TYPE_DOCUMENT=4, SHARE_TYPE_EXECUTABLE=5, SHARE_TYPE_IMAGE=6, SHARE_TYPE_MOVIE=7, SHARE_TYPE_DIRECTORY=8, SHARE_TYPE_TTH=9 } type; unsigned long size; unsigned long inode; } *

variable_types: struct stat { unsigned long st_dev; unsigned long st_ino; unsigned long st_nlink; unsigned int st_mode; unsigned int st_uid; unsigned int st_gid; int __pad0; unsigned long st_rdev; long st_size; long st_blksize; long st_blocks; struct timespec { long tv_sec; long tv_nsec; } st_atim; struct timespec st_mtim; struct timespec st_ctim; long __glibc_reserved[3]; }

variable_types: struct tth_entry { struct { struct tth_entry *rbe_left; struct tth_entry *rbe_right; struct tth_entry *rbe_parent; int rbe_color; } link; unsigned long active_inode; char tth[40]; long leafdata_offset; unsigned int leafdata_len; char *leafdata; } *

variable_types:
filename
char *

user_defined_types: struct stat { unsigned long st_dev; unsigned long st_ino; unsigned long st_nlink; unsigned int st_mode; unsigned int st_uid; unsigned int st_gid; int __pad0; unsigned long st_rdev; long st_size; long st_blksize; long st_blocks; struct timespec st_atim; struct timespec st_mtim; struct timespec st_ctim; long __glibc_reserved[3]; }

user_defined_types: struct notification_center { struct { struct nc_observer *lh_first; } observers; }

user_defined_types: struct bloom { unsigned int length; unsigned char *filter; unsigned int collisions; }


decompiled_code:
const char *__fastcall xerr_msg(__int64 a1)
{
const char *result; // rax

result = "unknown error";
if ( a1 )
{
result = *(const char **)(a1 + 8);
if ( !result )
result = "unknown error";
}
return result;
}

canonical_decompiled_code:
const char *__fastcall func0(__int64 a1)
{
const char *result; // rax

result = "unknown error";
if ( a1 )
{
result = *(const char **)(a1 + 8);
if ( !result )
result = "unknown error";
}
return result;
}

original_code:
const char *xerr_msg(xerr_t *xerr)
{
    return xerr && xerr->message ? xerr->message : "unknown error";
}

canonical_original_code:
char *xerr_msg(struct xerr *xerr)
{
    return xerr && xerr->message ? xerr->message : "unknown error";
}

variable_types: struct xerr { int code; char *message; } *


decompiled_code:
void xerr_set(__int64 a1, int a2, const char *a3, ...)
{
void **v4; // rax
unsigned int v5; // eax
gcc_va_list arg; // [rsp+8h] [rbp-E0h] BYREF

if ( a1 )
{
if ( *(_QWORD *)a1 )
_assert_fail("*xerr == NULL", "xerr.c", 0x2Du, "xerr_set");
v4 = (void **)calloc(1uLL, 0x10uLL);
*(_QWORD *)a1 = v4;
free(v4[1]);
*(_QWORD *)(*(_QWORD *)a1 + 8LL) = 0LL;
va_start(arg, a3);
if ( vasprintf((char **)(*(_QWORD *)a1 + 8LL), a3, arg) == -1 )
{
v5 = getpid();
sp_log(64LL, "[%d] (%s:%i) vasprintf did not return anything", v5, "xerr_set", 54LL);
}
**(_DWORD **)a1 = a2;
}
}

canonical_decompiled_code:
void func1(__int64 a1, int a2, const char *a3, ...)
{
void **v4; // rax
unsigned int v5; // eax
gcc_va_list arg; // [rsp+8h] [rbp-E0h] BYREF

if ( a1 )
{
if ( *(_QWORD *)a1 )
_assert_fail("*xerr == NULL", "xerr.c", 0x2Du, "xerr_set");
v4 = (void **)calloc(1uLL, 0x10uLL);
*(_QWORD *)a1 = v4;
free(v4[1]);
*(_QWORD *)(*(_QWORD *)a1 + 8LL) = 0LL;
va_start(arg, a3);
if ( vasprintf((char **)(*(_QWORD *)a1 + 8LL), a3, arg) == -1 )
{
v5 = getpid();
sp_log(64LL, "[%d] (%s:%i) vasprintf did not return anything", v5, "xerr_set", 54LL);
}
**(_DWORD **)a1 = a2;
}
}

original_code:
void xerr_set(xerr_t **xerr, int code, const char *fmt, ...)
{
    if(xerr == ((void *)0))
        return;
    ((void) sizeof ((*xerr == ((void *)0)) ? 1 : 0), __extension__ ({ if (*xerr == ((void *)0)) ; else __assert_fail ("*xerr == NULL", "xerr.c", 45, __extension__ __PRETTY_FUNCTION__); }));
    *xerr = calloc(1, sizeof(xerr_t));
    free((*xerr)->message);
    (*xerr)->message = 0;
    va_list ap;
    __builtin_va_start(ap,fmt);
    int num_returned_bytes = vasprintf(&(*xerr)->message, fmt, ap);
    if (num_returned_bytes == -1)
        sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "vasprintf did not return anything", getpid(), __func__, 54);
    __builtin_va_end(ap);
    (*xerr)->code = code;
}

canonical_original_code:
void xerr_set(struct xerr **xerr, int code, char *fmt, ...)
{
    if(xerr == ((void *)0))
        return;
    ((void) sizeof ((*xerr == ((void *)0)) ? 1 : 0), __extension__ ({ if (*xerr == ((void *)0)) ; else __assert_fail ("*xerr == NULL", "xerr.c", 45, __extension__ __PRETTY_FUNCTION__); }));
    *xerr = calloc(1, sizeof(xerr_t));
    free((*xerr)->message);
    (*xerr)->message = 0;
    __builtin_va_list ap;
    __builtin_va_start(ap,fmt);
    int num_returned_bytes = vasprintf(&(*xerr)->message, fmt, ap);
    if (num_returned_bytes == -1)
        sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "vasprintf did not return anything", getpid(), __func__, 54);
    __builtin_va_end(ap);
    (*xerr)->code = code;
}

variable_types: struct xerr { int code; char *message; } **

variable_types: code int

variable_types:
fmt
char *


decompiled_code:
void __fastcall xerr_free(void *ptr)
{
if ( ptr )
{
free(*((void **)ptr + 1));
free(ptr);
}
}

canonical_decompiled_code:
void __fastcall func2(void *ptr)
{
if ( ptr )
{
free(*((void **)ptr + 1));
free(ptr);
}
}

original_code:
void xerr_free(xerr_t *xerr)
{
    if(xerr)
    {
        free(xerr->message);
        free(xerr);
    }
}

canonical_original_code:
void xerr_free(struct xerr *xerr)
{
    if(xerr)
    {
        free(xerr->message);
        free(xerr);
    }
}

user_defined_types: struct xerr { int code; char *message; }


decompiled_code:
__int64 __fastcall queue_handle_filelist_finished_notification(__int64 a1, __int64 a2, __int64 a3)
{
__int64 result; // rax

result = is_filelist(*(_QWORD *)(a3 + 16));
if ( (_DWORD)result == 2 )
result = queue_match_filelist(*(char **)(a3 + 16), *(char **)(a3 + 8));
return result;
}

canonical_decompiled_code:
__int64 __fastcall func4(__int64 a1, __int64 a2, __int64 a3)
{
__int64 result; // rax

result = is_filelist(*(_QWORD *)(a3 + 16));
if ( (_DWORD)result == 2 )
result = func3(*(char **)(a3 + 16), *(char **)(a3 + 8));
return result;
}

original_code:
static void queue_handle_filelist_finished_notification(nc_t *nc,
        const char *channel,
        nc_filelist_finished_t *notification,
        void *user_data)
{
    if(is_filelist(notification->filename) == 2)
    {
        queue_match_filelist(notification->filename, notification->nick);
    }
    else if(notification->auto_matched == 1)
    {
    }
}

canonical_original_code:
static void queue_handle_filelist_finished_notification(struct notification_center *nc, char *channel, struct nc_filelist_finished *notification, void *user_data)
{
    if(is_filelist(notification->filename) == 2)
    {
        queue_match_filelist(notification->filename, notification->nick);
    }
    else if(notification->auto_matched == 1)
    {
    }
}

variable_types: struct nc_filelist_finished { char *hub_address; char *nick; char *filename; _Bool auto_matched; } *

user_defined_types: struct nc_observer { char *channel; void (*callback)(struct notification_center *nc, char *channel, void *data, void *user_data); void *user_data; struct { struct nc_observer *le_next; struct nc_observer **le_prev; } next; }


decompiled_code:
__int64 queue_match_init()
{
__int64 v0; // rax
__int64 v1; // rax

v0 = nc_default();
nc_add_search_response_observer(v0, queue_handle_search_response_notification, 0LL);
v1 = nc_default();
return nc_add_filelist_finished_observer(v1, queue_handle_filelist_finished_notification, 0LL);
}

canonical_decompiled_code:
__int64 func6()
{
__int64 v0; // rax
__int64 v1; // rax

v0 = nc_default();
nc_add_search_response_observer(v0, queue_handle_search_response_notification, 0LL);
v1 = nc_default();
return nc_add_filelist_finished_observer(v1, queue_handle_filelist_finished_notification, 0LL);
}

original_code:
void queue_match_init(void)
{
    nc_add_search_response_observer(nc_default(),
            queue_handle_search_response_notification, ((void *)0));
    nc_add_filelist_finished_observer(nc_default(),
            queue_handle_filelist_finished_notification, ((void *)0));
}

canonical_original_code:
void queue_match_init()
{
    nc_add_search_response_observer(nc_default(),
            queue_handle_search_response_notification, ((void *)0));
    nc_add_filelist_finished_observer(nc_default(),
            queue_handle_filelist_finished_notification, ((void *)0));
}


decompiled_code:
__int64 __fastcall fl_parse(char *file, _QWORD *a2)
{
int v2; // eax
int v3; // ebx
char *v4; // r12
char *v5; // rax
__int64 result; // rax
const char *v7; // r14
unsigned int v8; // eax
unsigned int v9; // eax
const char *v10; // rbx
unsigned int v11; // eax
unsigned int v12; // eax
int *v13; // rax
char *v14; // rbx
unsigned int v15; // eax
struct stat64 v16; // [rsp+0h] [rbp-148h] BYREF
struct stat64 v17; // [rsp+90h] [rbp-B8h] BYREF

v2 = is_filelist();
if ( !v2 )
{
v12 = getpid();
sp_log(16LL, "[%d] (%s:%i) assert failed: type != FILELIST_NONE", v12, "fl_parse", 41LL);
return 0LL;
}
v3 = v2;
v4 = strdup(file);
v5 = strrchr(v4, 46);
if ( !v5 || strcmp(v5, ".bz2") && strcmp(v5, ".DcLst") )
goto LABEL_5;
*v5 = 0;
v7 = v5 + 1;
if ( stat64(v4, &v16) )
goto LABEL_11;
if ( stat64(file, &v17) )
{
v13 = _errno_location();
v14 = strerror(*v13);
v15 = getpid();
sp_log(16LL, "[%d] (%s:%i) %s: %s", v15, "fl_parse", 62LL, file, v14);
free(v4);
return 0LL;
}
if ( v16.st_mtim.tv_sec < v17.st_mtim.tv_sec )
{
LABEL_11:
v9 = getpid();
sp_log(64LL, "[%d] (%s:%i) decompressing filelist [%s] -> [%s]", v9, "fl_parse", 79LL, file, v4);
if ( !strcmp(v7, "bz2") )
bz2_decode(file, v4, a2);
else
he3_decode(file, v4, a2);
if ( !a2 || !*a2 )
goto LABEL_5;
v10 = (const char *)xerr_msg();
v11 = getpid();
sp_log(16LL, "[%d] (%s:%i) failed to decompress filelist: %s", v11, "fl_parse", 86LL, v10);
return 0LL;
}
v8 = getpid();
sp_log(64LL, "[%d] (%s:%i) re-using decompressed filelist [%s]", v8, "fl_parse", 72LL, v4);
LABEL_5:
if ( v3 == 1 )
result = fl_parse_dclst(v4);
else
result = fl_parse_xml(v4);
return result;
}

canonical_decompiled_code:
__int64 __fastcall func0(char *file, _QWORD *a2)
{
int v2; // eax
int v3; // ebx
char *v4; // r12
char *v5; // rax
__int64 result; // rax
const char *v7; // r14
unsigned int v8; // eax
unsigned int v9; // eax
const char *v10; // rbx
unsigned int v11; // eax
unsigned int v12; // eax
int *v13; // rax
char *v14; // rbx
unsigned int v15; // eax
struct stat64 v16; // [rsp+0h] [rbp-148h] BYREF
struct stat64 v17; // [rsp+90h] [rbp-B8h] BYREF

v2 = is_filelist();
if ( !v2 )
{
v12 = getpid();
sp_log(16LL, "[%d] (%s:%i) assert failed: type != FILELIST_NONE", v12, "fl_parse", 41LL);
return 0LL;
}
v3 = v2;
v4 = strdup(file);
v5 = strrchr(v4, 46);
if ( !v5 || strcmp(v5, ".bz2") && strcmp(v5, ".DcLst") )
goto LABEL_5;
*v5 = 0;
v7 = v5 + 1;
if ( stat64(v4, &v16) )
goto LABEL_11;
if ( stat64(file, &v17) )
{
v13 = _errno_location();
v14 = strerror(*v13);
v15 = getpid();
sp_log(16LL, "[%d] (%s:%i) %s: %s", v15, "fl_parse", 62LL, file, v14);
free(v4);
return 0LL;
}
if ( v16.st_mtim.tv_sec < v17.st_mtim.tv_sec )
{
LABEL_11:
v9 = getpid();
sp_log(64LL, "[%d] (%s:%i) decompressing filelist [%s] -> [%s]", v9, "fl_parse", 79LL, file, v4);
if ( !strcmp(v7, "bz2") )
bz2_decode(file, v4, a2);
else
he3_decode(file, v4, a2);
if ( !a2 || !*a2 )
goto LABEL_5;
v10 = (const char *)xerr_msg();
v11 = getpid();
sp_log(16LL, "[%d] (%s:%i) failed to decompress filelist: %s", v11, "fl_parse", 86LL, v10);
return 0LL;
}
v8 = getpid();
sp_log(64LL, "[%d] (%s:%i) re-using decompressed filelist [%s]", v8, "fl_parse", 72LL, v4);
LABEL_5:
if ( v3 == 1 )
result = fl_parse_dclst(v4);
else
result = fl_parse_xml(v4);
return result;
}

original_code:
fl_dir_t *fl_parse(const char *filename, xerr_t **err)
{
    int type = is_filelist(filename);
    do { if(!(type != 0)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "type != FILELIST_NONE", getpid(), __func__, 41); return (((void *)0)); } } while(0);
    char *filename_noext = strdup(filename);
    char *ext = strrchr(filename_noext, '.');
    if(ext && (strcmp(ext, ".bz2") == 0 || strcmp(ext, ".DcLst") == 0))
    {
 *ext++ = 0;
 _Bool need_decompression = 1;
 struct stat stbuf;
 if(stat(filename_noext, &stbuf) == 0)
 {
     struct stat stbuf_orig;
     if(stat(filename, &stbuf_orig) != 0)
     {
  sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "%s: %s", getpid(), __func__, 62, filename, strerror((*__errno_location ())));
  free(filename_noext);
  return ((void *)0);
     }
     if(stbuf.st_mtim.tv_sec >= stbuf_orig.st_mtim.tv_sec)
     {
  need_decompression = 0;
  sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "re-using decompressed filelist [%s]", getpid(), __func__, 72, filename_noext);
     }
 }
 if(need_decompression)
 {
     sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "decompressing filelist [%s] -> [%s]", getpid(), __func__, 79, filename, filename_noext);
     if(strcmp(ext, "bz2") == 0)
  bz2_decode(filename, filename_noext, err);
     else
  he3_decode(filename, filename_noext, err);
     if(err && *err)
     {
  sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "failed to decompress filelist: %s", getpid(), __func__, 86, xerr_msg(*err));
  return ((void *)0);
     }
 }
    }
    if(type == 1)
        return fl_parse_dclst(filename_noext);
    else
        return fl_parse_xml(filename_noext);
    free(filename_noext);
}

canonical_original_code:
struct fl_dir *fl_parse(char *filename, struct xerr **err)
{
    int type = is_filelist(filename);
    do { if(!(type != 0)) { sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "assert failed: " "type != FILELIST_NONE", getpid(), __func__, 41); return (((void *)0)); } } while(0);
    char *filename_noext = strdup(filename);
    char *ext = strrchr(filename_noext, '.');
    if(ext && (strcmp(ext, ".bz2") == 0 || strcmp(ext, ".DcLst") == 0))
    {
 *ext++ = 0;
 _Bool need_decompression = 1;
 struct stat stbuf;
 if(stat(filename_noext, &stbuf) == 0)
 {
     struct stat stbuf_orig;
     if(stat(filename, &stbuf_orig) != 0)
     {
  sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "%s: %s", getpid(), __func__, 62, filename, strerror((*__errno_location ())));
  free(filename_noext);
  return ((void *)0);
     }
     if(stbuf.st_mtim.tv_sec >= stbuf_orig.st_mtim.tv_sec)
     {
  need_decompression = 0;
  sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "re-using decompressed filelist [%s]", getpid(), __func__, 72, filename_noext);
     }
 }
 if(need_decompression)
 {
     sp_log(LOG_LEVEL_DEBUG, "[%d] (%s:%i) " "decompressing filelist [%s] -> [%s]", getpid(), __func__, 79, filename, filename_noext);
     if(strcmp(ext, "bz2") == 0)
  bz2_decode(filename, filename_noext, err);
     else
  he3_decode(filename, filename_noext, err);
     if(err && *err)
     {
  sp_log(LOG_LEVEL_WARNING, "[%d] (%s:%i) " "failed to decompress filelist: %s", getpid(), __func__, 86, xerr_msg(*err));
  return ((void *)0);
     }
 }
    }
    if(type == 1)
        return fl_parse_dclst(filename_noext);
    else
        return fl_parse_xml(filename_noext);
    free(filename_noext);
}

variable_types: type int

variable_types:
ext
char *

return_type: struct fl_dir { struct { struct fl_dir *le_next; struct fl_dir **le_prev; } link; struct fl_file_list { struct fl_file { struct { struct fl_file *tqe_next; struct fl_file **tqe_prev; } link; char *name; enum share_type { SHARE_TYPE_ANY=1, SHARE_TYPE_AUDIO=2, SHARE_TYPE_COMPRESSED=3, SHARE_TYPE_DOCUMENT=4, SHARE_TYPE_EXECUTABLE=5, SHARE_TYPE_IMAGE=6, SHARE_TYPE_MOVIE=7, SHARE_TYPE_DIRECTORY=8, SHARE_TYPE_TTH=9 } type; unsigned long size; char *tth; struct fl_dir *dir; } *tqh_first; struct fl_file **tqh_last; } files; char *path; unsigned int nfiles; unsigned long size; } *

user_defined_types: struct timespec { long tv_sec; long tv_nsec; }

user_defined_types: struct fl_dir { struct { struct fl_dir *le_next; struct fl_dir **le_prev; } link; struct fl_file_list files; char *path; unsigned int nfiles; unsigned long size; }

user_defined_types: struct fl_file_list { struct fl_file *tqh_first; struct fl_file **tqh_last; }

user_defined_types: struct fl_file { struct { struct fl_file *tqe_next; struct fl_file **tqe_prev; } link; char *name; enum share_type type; unsigned long size; char *tth; struct fl_dir *dir; }


decompiled_code:
void __fastcall fl_free_dir(void *ptr)
{
_QWORD *v2; // rdi
_QWORD *v3; // rbx
_QWORD *v4; // rax

if ( ptr )
{
v2 = (_QWORD *)*((_QWORD *)ptr + 2);
if ( v2 )
{
v3 = (_QWORD *)*v2;
v4 = (_QWORD *)v2[1];
if ( *v2 )
{
do
{
v3[1] = v4;
*v4 = v3;
fl_free_file(v2);
v2 = v3;
v3 = (_QWORD *)*v3;
v4 = (_QWORD *)v2[1];
}
while ( v3 );
}
*((_QWORD *)ptr + 3) = v4;
*v4 = 0LL;
fl_free_file(v2);
}
free(*((void **)ptr + 4));
free(ptr);
}
}

original_code:
void fl_free_dir(fl_dir_t *dir)
{
    if(dir)
    {
        fl_file_t *f, *next;
        for(f = ((&dir->files)->tqh_first); f; f = next)
        {
            next = ((f)->link.tqe_next);
            do { if (((f)->link.tqe_next) != ((void *)0)) (f)->link.tqe_next->link.tqe_prev = (f)->link.tqe_prev; else (&dir->files)->tqh_last = (f)->link.tqe_prev; *(f)->link.tqe_prev = (f)->link.tqe_next; } while (0);
            fl_free_file(f);
        }
        free(dir->path);
        free(dir);
    }
}

canonical_original_code:
void fl_free_dir(struct fl_dir *dir)
{
    if(dir)
    {
        struct fl_file *f; struct fl_file *next;
        for(f = ((&dir->files)->tqh_first); f; f = next)
        {
            next = ((f)->link.tqe_next);
            do { if (((f)->link.tqe_next) != ((void *)0)) (f)->link.tqe_next->link.tqe_prev = (f)->link.tqe_prev; else (&dir->files)->tqh_last = (f)->link.tqe_prev; *(f)->link.tqe_prev = (f)->link.tqe_next; } while (0);
            fl_free_file(f);
        }
        free(dir->path);
        free(dir);
    }
}

variable_types: struct fl_dir { struct { struct fl_dir *le_next; struct fl_dir **le_prev; } link; struct fl_file_list { struct fl_file { struct { struct fl_file *tqe_next; struct fl_file **tqe_prev; } link; char *name; enum share_type { SHARE_TYPE_ANY=1, SHARE_TYPE_AUDIO=2, SHARE_TYPE_COMPRESSED=3, SHARE_TYPE_DOCUMENT=4, SHARE_TYPE_EXECUTABLE=5, SHARE_TYPE_IMAGE=6, SHARE_TYPE_MOVIE=7, SHARE_TYPE_DIRECTORY=8, SHARE_TYPE_TTH=9 } type; unsigned long size; char *tth; struct fl_dir *dir; } *tqh_first; struct fl_file **tqh_last; } files; char *path; unsigned int nfiles; unsigned long size; } *

variable_types: struct fl_file { struct { struct fl_file *tqe_next; struct fl_file **tqe_prev; } link; char *name; enum share_type { SHARE_TYPE_ANY=1, SHARE_TYPE_AUDIO=2, SHARE_TYPE_COMPRESSED=3, SHARE_TYPE_DOCUMENT=4, SHARE_TYPE_EXECUTABLE=5, SHARE_TYPE_IMAGE=6, SHARE_TYPE_MOVIE=7, SHARE_TYPE_DIRECTORY=8, SHARE_TYPE_TTH=9 } type; unsigned long size; char *tth; struct fl_dir { struct { struct fl_dir *le_next; struct fl_dir **le_prev; } link; struct fl_file_list { struct fl_file *tqh_first; struct fl_file **tqh_last; } files; char *path; unsigned int nfiles; unsigned long size; } *dir; } *


decompiled_code:
void __fastcall fl_free_file(void *ptr)
{
void *v2; // rdi

if ( ptr )
{
free(*((void **)ptr + 2));
free(*((void **)ptr + 5));
v2 = (void *)*((_QWORD *)ptr + 6);
if ( v2 )
fl_free_dir(v2);
free(ptr);
}
}

canonical_decompiled_code:
void __fastcall func2(void *ptr)
{
void *v2; // rdi

if ( ptr )
{
free(*((void **)ptr + 2));
free(*((void **)ptr + 5));
v2 = (void *)*((_QWORD *)ptr + 6);
if ( v2 )
func1(v2);
free(ptr);
}
}

original_code:
static void fl_free_file(fl_file_t *flf)
{
    if(flf)
    {
        free(flf->name);
        free(flf->tth);
        if(flf->dir)
            fl_free_dir(flf->dir);
        free(flf);
    }
}

canonical_original_code:
static void fl_free_file(struct fl_file *flf)
{
    if(flf)
    {
        free(flf->name);
        free(flf->tth);
        if(flf->dir)
            fl_free_dir(flf->dir);
        free(flf);
    }
}

user_defined_types: enum share_type { SHARE_TYPE_ANY=1, SHARE_TYPE_AUDIO=2, SHARE_TYPE_COMPRESSED=3, SHARE_TYPE_DOCUMENT=4, SHARE_TYPE_EXECUTABLE=5, SHARE_TYPE_IMAGE=6, SHARE_TYPE_MOVIE=7, SHARE_TYPE_DIRECTORY=8, SHARE_TYPE_TTH=9 }


decompiled_code:
unsigned int *__fastcall bloom_hash_key(_DWORD *a1, const char *a2, unsigned int *a3, unsigned int *a4, unsigned int *a5, unsigned int *a6, unsigned int *a7)
{
size_t v11; // rax
unsigned int v12; // eax
unsigned int v13; // edx
unsigned int *result; // rax
int v15[22]; // [rsp+0h] [rbp-58h] BYREF

if ( !a1 )
_assert_fail("bloom", "bloom.c", 0x5Bu, "bloom_hash_key");
if ( !a2 )
_assert_fail("key", "bloom.c", 0x5Cu, "bloom_hash_key");
v11 = strlen(a2);
tiger(a2, v11, v15);
*a3 = v15[0] % (unsigned int)(8 * *a1);
*a4 = v15[1] % (unsigned int)(8 * *a1);
*a5 = v15[2] % (unsigned int)(8 * *a1);
v12 = v15[4];
*a6 = v15[3] % (unsigned int)(8 * *a1);
v13 = v12 % (8 * *a1);
result = a7;
*a7 = v13;
return result;
}

canonical_decompiled_code:
unsigned int *__fastcall func0(_DWORD *a1, const char *a2, unsigned int *a3, unsigned int *a4, unsigned int *a5, unsigned int *a6, unsigned int *a7)
{
size_t v11; // rax
unsigned int v12; // eax
unsigned int v13; // edx
unsigned int *result; // rax
int v15[22]; // [rsp+0h] [rbp-58h] BYREF

if ( !a1 )
_assert_fail("bloom", "bloom.c", 0x5Bu, "bloom_hash_key");
if ( !a2 )
_assert_fail("key", "bloom.c", 0x5Cu, "bloom_hash_key");
v11 = strlen(a2);
tiger(a2, v11, v15);
*a3 = v15[0] % (unsigned int)(8 * *a1);
*a4 = v15[1] % (unsigned int)(8 * *a1);
*a5 = v15[2] % (unsigned int)(8 * *a1);
v12 = v15[4];
*a6 = v15[3] % (unsigned int)(8 * *a1);
v13 = v12 % (8 * *a1);
result = a7;
*a7 = v13;
return result;
}

original_code:
static void bloom_hash_key(bloom_t *bloom, const char *key,
        unsigned *h1, unsigned *h2, unsigned *h3, unsigned *h4, unsigned *h5)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 91, __extension__ __PRETTY_FUNCTION__); }));
    ((void) sizeof ((key) ? 1 : 0), __extension__ ({ if (key) ; else __assert_fail ("key", "bloom.c", 92, __extension__ __PRETTY_FUNCTION__); }));
    word64 res[3];
    tiger((word64 *)key, strlen(key), res);
    if(h1) *h1 = *(unsigned *)((unsigned char *)res+0) % (bloom->length * 8);
    if(h2) *h2 = *(unsigned *)((unsigned char *)res+4) % (bloom->length * 8);
    if(h3) *h3 = *(unsigned *)((unsigned char *)res+8) % (bloom->length * 8);
    if(h4) *h4 = *(unsigned *)((unsigned char *)res+12) % (bloom->length * 8);
    if(h5) *h5 = *(unsigned *)((unsigned char *)res+16) % (bloom->length * 8);
}

canonical_original_code:
static void bloom_hash_key(struct bloom *bloom, char *key, unsigned int *h1, unsigned int *h2, unsigned int *h3, unsigned int *h4, unsigned int *h5)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 91, __extension__ __PRETTY_FUNCTION__); }));
    ((void) sizeof ((key) ? 1 : 0), __extension__ ({ if (key) ; else __assert_fail ("key", "bloom.c", 92, __extension__ __PRETTY_FUNCTION__); }));
    unsigned long res[3];
    tiger((unsigned long *)key, strlen(key), res);
    if(h1) *h1 = *(unsigned int *)((unsigned char *)res+0) % (bloom->length * 8);
    if(h2) *h2 = *(unsigned int *)((unsigned char *)res+4) % (bloom->length * 8);
    if(h3) *h3 = *(unsigned int *)((unsigned char *)res+8) % (bloom->length * 8);
    if(h4) *h4 = *(unsigned int *)((unsigned char *)res+12) % (bloom->length * 8);
    if(h5) *h5 = *(unsigned int *)((unsigned char *)res+16) % (bloom->length * 8);
}

variable_types: struct bloom { unsigned int length; unsigned char *filter; unsigned int collisions; } *

variable_types:
key
char *

variable_types:
res
unsigned long [3]


decompiled_code:
__int64 __fastcall bloom_iterate_key(_DWORD *a1, unsigned __int8 *a2, __int64 (__fastcall *a3)(_DWORD *, _QWORD, _QWORD, _QWORD, _QWORD, _QWORD))
{
unsigned __int8 *v3; // rbx
int v5; // eax
int v6; // er12
__int64 v7; // rax
char *v8; // r14
unsigned int v9; // er15
int v11; // [rsp+Ch] [rbp-5Ch]
unsigned int v12; // [rsp+1Ch] [rbp-4Ch] BYREF
unsigned int v13; // [rsp+20h] [rbp-48h] BYREF
unsigned int v14; // [rsp+24h] [rbp-44h] BYREF
unsigned int v15; // [rsp+28h] [rbp-40h] BYREF
unsigned int v16[15]; // [rsp+2Ch] [rbp-3Ch] BYREF

if ( !a1 )
_assert_fail("bloom", "bloom.c", 0x73u, "bloom_iterate_key");
v3 = a2;
if ( !a2 )
_assert_fail("key", "bloom.c", 0x74u, "bloom_iterate_key");
v5 = g_utf8_strlen(a2, -1LL);
if ( v5 <= 3 )
return 0;
v6 = 0;
v11 = v5 - 3;
while ( 1 )
{
v7 = g_utf8_offset_to_pointer(v3, 4LL);
v8 = (char *)g_utf8_casefold(v3, v7 - (_QWORD)v3);
bloom_hash_key(a1, v8, &v12, &v13, &v14, &v15, v16);
v9 = a3(a1, v12, v13, v14, v15, v16[0]);
free(v8);
if ( v9 )
break;
++v6;
v3 += *(char *)(g_utf8_skip + *v3);
if ( v6 == v11 )
return 0;
}
return v9;
}

canonical_decompiled_code:
__int64 __fastcall func1(_DWORD *a1, unsigned __int8 *a2, __int64 (__fastcall *a3)(_DWORD *, _QWORD, _QWORD, _QWORD, _QWORD, _QWORD))
{
unsigned __int8 *v3; // rbx
int v5; // eax
int v6; // er12
__int64 v7; // rax
char *v8; // r14
unsigned int v9; // er15
int v11; // [rsp+Ch] [rbp-5Ch]
unsigned int v12; // [rsp+1Ch] [rbp-4Ch] BYREF
unsigned int v13; // [rsp+20h] [rbp-48h] BYREF
unsigned int v14; // [rsp+24h] [rbp-44h] BYREF
unsigned int v15; // [rsp+28h] [rbp-40h] BYREF
unsigned int v16[15]; // [rsp+2Ch] [rbp-3Ch] BYREF

if ( !a1 )
_assert_fail("bloom", "bloom.c", 0x73u, "bloom_iterate_key");
v3 = a2;
if ( !a2 )
_assert_fail("key", "bloom.c", 0x74u, "bloom_iterate_key");
v5 = g_utf8_strlen(a2, -1LL);
if ( v5 <= 3 )
return 0;
v6 = 0;
v11 = v5 - 3;
while ( 1 )
{
v7 = g_utf8_offset_to_pointer(v3, 4LL);
v8 = (char *)g_utf8_casefold(v3, v7 - (_QWORD)v3);
func0(a1, v8, &v12, &v13, &v14, &v15, v16);
v9 = a3(a1, v12, v13, v14, v15, v16[0]);
free(v8);
if ( v9 )
break;
++v6;
v3 += *(char *)(g_utf8_skip + *v3);
if ( v6 == v11 )
return 0;
}
return v9;
}

original_code:
static int bloom_iterate_key(bloom_t *bloom, const char *key,
        subkey_function_t func)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 115, __extension__ __PRETTY_FUNCTION__); }));
    ((void) sizeof ((key) ? 1 : 0), __extension__ ({ if (key) ; else __assert_fail ("key", "bloom.c", 116, __extension__ __PRETTY_FUNCTION__); }));
    ((void) sizeof ((func) ? 1 : 0), __extension__ ({ if (func) ; else __assert_fail ("func", "bloom.c", 117, __extension__ __PRETTY_FUNCTION__); }));
    int len = g_utf8_strlen(key, -1);
    if(len >= 4)
    {
        len -= 4;
        int i;
        const char *p = key;
        for(i = 0; i <= len; i++)
        {
            char *np = g_utf8_offset_to_pointer(p, 4);
            char *xkey = g_utf8_casefold(p, np - p);
            unsigned h1, h2, h3, h4, h5;
            bloom_hash_key(bloom, xkey, &h1, &h2, &h3, &h4, &h5);
            int rc = func(bloom, h1, h2, h3, h4, h5);
            free(xkey);
            if(rc != 0)
                return rc;
            p = (char *)((p) + g_utf8_skip[*(unsigned char *)(p)]);
        }
    }
    return 0;
}

canonical_original_code:
static int bloom_iterate_key(struct bloom *bloom, char *key, int (*func)(struct bloom *bloom, unsigned int h1, unsigned int h2, unsigned int h3, unsigned int h4, unsigned int h5))
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 115, __extension__ __PRETTY_FUNCTION__); }));
    ((void) sizeof ((key) ? 1 : 0), __extension__ ({ if (key) ; else __assert_fail ("key", "bloom.c", 116, __extension__ __PRETTY_FUNCTION__); }));
    ((void) sizeof ((func) ? 1 : 0), __extension__ ({ if (func) ; else __assert_fail ("func", "bloom.c", 117, __extension__ __PRETTY_FUNCTION__); }));
    int len = g_utf8_strlen(key, -1);
    if(len >= 4)
    {
        len -= 4;
        int i;
        char *p = key;
        for(i = 0; i <= len; i++)
        {
            char *np = g_utf8_offset_to_pointer(p, 4);
            char *xkey = g_utf8_casefold(p, np - p);
            unsigned int h1; unsigned int h2; unsigned int h3; unsigned int h4; unsigned int h5;
            bloom_hash_key(bloom, xkey, &h1, &h2, &h3, &h4, &h5);
            int rc = func(bloom, h1, h2, h3, h4, h5);
            free(xkey);
            if(rc != 0)
                return rc;
            p = (char *)((p) + g_utf8_skip[*(unsigned char *)(p)]);
        }
    }
    return 0;
}

variable_types: int (*)(struct bloom *bloom, unsigned int h1, unsigned int h2, unsigned int h3, unsigned int h4, unsigned int h5)

variable_types: len int

variable_types: i int

variable_types:
p
char *

variable_types:
np
char *

variable_types:
xkey
char *

variable_types: rc int


decompiled_code:
void __fastcall bloom_free(void *ptr)
{
if ( ptr )
{
free(*((void **)ptr + 1));
free(ptr);
}
}

original_code:
void bloom_free(bloom_t *bloom)
{
    if(bloom)
    {
        free(bloom->filter);
        free(bloom);
    }
}

canonical_original_code:
void bloom_free(struct bloom *bloom)
{
    if(bloom)
    {
        free(bloom->filter);
        free(bloom);
    }
}


decompiled_code:
__int64 __fastcall bloom_add_key_callback(__int64 a1, unsigned int a2, unsigned int a3, unsigned int a4, unsigned int a5, unsigned int a6)
{
bloom_set_bit(a1, a2);
bloom_set_bit(a1, a3);
bloom_set_bit(a1, a4);
bloom_set_bit(a1, a5);
bloom_set_bit(a1, a6);
return 0LL;
}

canonical_decompiled_code:
__int64 __fastcall func3(__int64 a1, unsigned int a2, unsigned int a3, unsigned int a4, unsigned int a5, unsigned int a6)
{
bloom_set_bit(a1, a2);
bloom_set_bit(a1, a3);
bloom_set_bit(a1, a4);
bloom_set_bit(a1, a5);
bloom_set_bit(a1, a6);
return 0LL;
}

original_code:
static int bloom_add_key_callback(bloom_t *bloom,
        unsigned h1, unsigned h2, unsigned h3, unsigned h4, unsigned h5)
{
    bloom_set_bit(bloom, h1);
    bloom_set_bit(bloom, h2);
    bloom_set_bit(bloom, h3);
    bloom_set_bit(bloom, h4);
    bloom_set_bit(bloom, h5);
    return 0;
}

canonical_original_code:
static int bloom_add_key_callback(struct bloom *bloom, unsigned int h1, unsigned int h2, unsigned int h3, unsigned int h4, unsigned int h5)
{
    bloom_set_bit(bloom, h1);
    bloom_set_bit(bloom, h2);
    bloom_set_bit(bloom, h3);
    bloom_set_bit(bloom, h4);
    bloom_set_bit(bloom, h5);
    return 0;
}


decompiled_code:
_BOOL8 __fastcall bloom_get_bit(__int64 a1, unsigned int a2)
{
__int64 v2; // rdx

if ( !a1 )
_assert_fail("bloom", "bloom.c", 0x4Bu, "bloom_get_bit");
v2 = a2 >> 3;
if ( *(_DWORD *)a1 <= (unsigned int)v2 )
_assert_fail("offset < bloom->length", "bloom.c", 0x4Eu, "bloom_get_bit");
return ((1 << (a2 & 7)) & *(unsigned __int8 *)(*(_QWORD *)(a1 + 8) + v2)) == 1 << (a2 & 7);
}

canonical_decompiled_code:
_BOOL8 __fastcall func4(__int64 a1, unsigned int a2)
{
__int64 v2; // rdx

if ( !a1 )
_assert_fail("bloom", "bloom.c", 0x4Bu, "bloom_get_bit");
v2 = a2 >> 3;
if ( *(_DWORD *)a1 <= (unsigned int)v2 )
_assert_fail("offset < bloom->length", "bloom.c", 0x4Eu, "bloom_get_bit");
return ((1 << (a2 & 7)) & *(unsigned __int8 *)(*(_QWORD *)(a1 + 8) + v2)) == 1 << (a2 & 7);
}

original_code:
int bloom_get_bit(bloom_t *bloom, unsigned bit)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 75, __extension__ __PRETTY_FUNCTION__); }));
    unsigned offset = bit >> 3;
    unsigned mask = 1 << (bit & 7);
    ((void) sizeof ((offset < bloom->length) ? 1 : 0), __extension__ ({ if (offset < bloom->length) ; else __assert_fail ("offset < bloom->length", "bloom.c", 78, __extension__ __PRETTY_FUNCTION__); }));
    return (bloom->filter[offset] & mask) == mask;
}

canonical_original_code:
int bloom_get_bit(struct bloom *bloom, unsigned int bit)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 75, __extension__ __PRETTY_FUNCTION__); }));
    unsigned int offset = bit >> 3;
    unsigned int mask = 1 << (bit & 7);
    ((void) sizeof ((offset < bloom->length) ? 1 : 0), __extension__ ({ if (offset < bloom->length) ; else __assert_fail ("offset < bloom->length", "bloom.c", 78, __extension__ __PRETTY_FUNCTION__); }));
    return (bloom->filter[offset] & mask) == mask;
}

variable_types:
bit
unsigned int

variable_types:
offset
unsigned int

variable_types:
mask
unsigned int


decompiled_code:
__int64 __fastcall bloom_check_key_callback(__int64 a1, unsigned int a2, unsigned int a3, unsigned int a4, unsigned int a5, unsigned int a6)
{
__int64 result; // rax

if ( bloom_get_bit(a1, a2) && bloom_get_bit(a1, a3) && bloom_get_bit(a1, a4) && bloom_get_bit(a1, a5) )
result = (unsigned int)-!bloom_get_bit(a1, a6);
else
result = 0xFFFFFFFFLL;
return result;
}

canonical_decompiled_code:
__int64 __fastcall func5(__int64 a1, unsigned int a2, unsigned int a3, unsigned int a4, unsigned int a5, unsigned int a6)
{
__int64 result; // rax

if ( func4(a1, a2) && func4(a1, a3) && func4(a1, a4) && func4(a1, a5) )
result = (unsigned int)-!func4(a1, a6);
else
result = 0xFFFFFFFFLL;
return result;
}

original_code:
static int bloom_check_key_callback(bloom_t *bloom,
        unsigned h1, unsigned h2, unsigned h3, unsigned h4, unsigned h5)
{
    if(bloom_get_bit(bloom, h1) == 1 &&
       bloom_get_bit(bloom, h2) == 1 &&
       bloom_get_bit(bloom, h3) == 1 &&
       bloom_get_bit(bloom, h4) == 1 &&
       bloom_get_bit(bloom, h5) == 1)
    {
        return 0;
    }
    return -1;
}

canonical_original_code:
static int bloom_check_key_callback(struct bloom *bloom, unsigned int h1, unsigned int h2, unsigned int h3, unsigned int h4, unsigned int h5)
{
    if(bloom_get_bit(bloom, h1) == 1 &&
       bloom_get_bit(bloom, h2) == 1 &&
       bloom_get_bit(bloom, h3) == 1 &&
       bloom_get_bit(bloom, h4) == 1 &&
       bloom_get_bit(bloom, h5) == 1)
    {
        return 0;
    }
    return -1;
}


decompiled_code:
__int64 __fastcall bloom_add_key(_DWORD *a1, unsigned __int8 *a2)
{
return bloom_iterate_key(
a1,
a2,
(__int64 (__fastcall *)(_DWORD *, _QWORD, _QWORD, _QWORD, _QWORD, _QWORD))bloom_add_key_callback);
}

canonical_decompiled_code:
__int64 __fastcall func6(_DWORD *a1, unsigned __int8 *a2)
{
return func1(
a1,
a2,
(__int64 (__fastcall *)(_DWORD *, _QWORD, _QWORD, _QWORD, _QWORD, _QWORD))bloom_add_key_callback);
}

original_code:
void bloom_add_key(bloom_t *bloom, const char *key)
{
    bloom_iterate_key(bloom, key, bloom_add_key_callback);
}

canonical_original_code:
void bloom_add_key(struct bloom *bloom, char *key)
{
    bloom_iterate_key(bloom, key, bloom_add_key_callback);
}


decompiled_code:
__int64 __fastcall bloom_add_filename(_DWORD *a1, __int64 a2)
{
__int64 v2; // rbp
__int64 v3; // rbx
unsigned __int8 *v4; // rsi

if ( !a1 )
_assert_fail("bloom", "bloom.c", 0xABu, "bloom_add_filename");
if ( !a2 )
_assert_fail("filename", "bloom.c", 0xACu, "bloom_add_filename");
v2 = arg_create(a2, "$.-_()[]{} ", 0LL);
if ( *(int *)v2 > 0 )
{
v3 = 0LL;
do
{
v4 = *(unsigned __int8 **)(*(_QWORD *)(v2 + 8) + 8 * v3++);
bloom_add_key(a1, v4);
}
while ( *(_DWORD *)v2 > (int)v3 );
}
return arg_free(v2);
}

canonical_decompiled_code:
__int64 __fastcall func7(_DWORD *a1, __int64 a2)
{
__int64 v2; // rbp
__int64 v3; // rbx
unsigned __int8 *v4; // rsi

if ( !a1 )
_assert_fail("bloom", "bloom.c", 0xABu, "bloom_add_filename");
if ( !a2 )
_assert_fail("filename", "bloom.c", 0xACu, "bloom_add_filename");
v2 = arg_create(a2, "$.-_()[]{} ", 0LL);
if ( *(int *)v2 > 0 )
{
v3 = 0LL;
do
{
v4 = *(unsigned __int8 **)(*(_QWORD *)(v2 + 8) + 8 * v3++);
func6(a1, v4);
}
while ( *(_DWORD *)v2 > (int)v3 );
}
return arg_free(v2);
}

original_code:
void bloom_add_filename(bloom_t *bloom, const char *filename)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 171, __extension__ __PRETTY_FUNCTION__); }));
    ((void) sizeof ((filename) ? 1 : 0), __extension__ ({ if (filename) ; else __assert_fail ("filename", "bloom.c", 172, __extension__ __PRETTY_FUNCTION__); }));
    arg_t *subkeys;
    int i;
    subkeys = arg_create(filename, "$.-_()[]{} ", 0);
    for(i = 0; i < subkeys->argc; i++)
        bloom_add_key(bloom, subkeys->argv[i]);
    arg_free(subkeys);
}

canonical_original_code:
void bloom_add_filename(struct bloom *bloom, char *filename)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 171, __extension__ __PRETTY_FUNCTION__); }));
    ((void) sizeof ((filename) ? 1 : 0), __extension__ ({ if (filename) ; else __assert_fail ("filename", "bloom.c", 172, __extension__ __PRETTY_FUNCTION__); }));
    struct arg_t *subkeys;
    int i;
    subkeys = arg_create(filename, "$.-_()[]{} ", 0);
    for(i = 0; i < subkeys->argc; i++)
        bloom_add_key(bloom, subkeys->argv[i]);
    arg_free(subkeys);
}

variable_types:
filename
char *

variable_types: struct arg_t { int argc; char **argv; } *


decompiled_code:
__int64 __fastcall bloom_check_key(_DWORD *a1, unsigned __int8 *a2)
{
return bloom_iterate_key(
a1,
a2,
(__int64 (__fastcall *)(_DWORD *, _QWORD, _QWORD, _QWORD, _QWORD, _QWORD))bloom_check_key_callback);
}

canonical_decompiled_code:
__int64 __fastcall func8(_DWORD *a1, unsigned __int8 *a2)
{
return func1(
a1,
a2,
(__int64 (__fastcall *)(_DWORD *, _QWORD, _QWORD, _QWORD, _QWORD, _QWORD))bloom_check_key_callback);
}

original_code:
int bloom_check_key(bloom_t *bloom, const char *key)
{
    return bloom_iterate_key(bloom, key, bloom_check_key_callback);
}

canonical_original_code:
int bloom_check_key(struct bloom *bloom, char *key)
{
    return bloom_iterate_key(bloom, key, bloom_check_key_callback);
}


decompiled_code:
__int64 __fastcall bloom_check_filename(_DWORD *a1, __int64 a2)
{
int *v2; // rax
int v3; // er12
int *v4; // rbp
__int64 v5; // rbx
int v6; // er13

if ( !a1 )
_assert_fail("bloom", "bloom.c", 0xD0u, "bloom_check_filename");
if ( !a2 )
_assert_fail("filename", "bloom.c", 0xD1u, "bloom_check_filename");
v2 = (int *)arg_create(a2, "$.-_()[]{} ", 0LL);
v3 = *v2;
v4 = v2;
if ( *v2 <= 0 )
{
v6 = 0;
}
else
{
v5 = 0LL;
while ( 1 )
{
v6 = v5;
if ( (unsigned int)bloom_check_key(a1, *(unsigned __int8 **)(*((_QWORD *)v4 + 1) + 8 * v5)) )
break;
v3 = *v4;
v6 = ++v5;
if ( *v4 <= (int)v5 )
goto LABEL_8;
}
v3 = *v4;
}
LABEL_8:
arg_free(v4);
return (unsigned int)-(v6 != v3);
}

canonical_decompiled_code:
__int64 __fastcall func9(_DWORD *a1, __int64 a2)
{
int *v2; // rax
int v3; // er12
int *v4; // rbp
__int64 v5; // rbx
int v6; // er13

if ( !a1 )
_assert_fail("bloom", "bloom.c", 0xD0u, "bloom_check_filename");
if ( !a2 )
_assert_fail("filename", "bloom.c", 0xD1u, "bloom_check_filename");
v2 = (int *)arg_create(a2, "$.-_()[]{} ", 0LL);
v3 = *v2;
v4 = v2;
if ( *v2 <= 0 )
{
v6 = 0;
}
else
{
v5 = 0LL;
while ( 1 )
{
v6 = v5;
if ( (unsigned int)func8(a1, *(unsigned __int8 **)(*((_QWORD *)v4 + 1) + 8 * v5)) )
break;
v3 = *v4;
v6 = ++v5;
if ( *v4 <= (int)v5 )
goto LABEL_8;
}
v3 = *v4;
}
LABEL_8:
arg_free(v4);
return (unsigned int)-(v6 != v3);
}

original_code:
int bloom_check_filename(bloom_t *bloom, const char *filename)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 208, __extension__ __PRETTY_FUNCTION__); }));
    ((void) sizeof ((filename) ? 1 : 0), __extension__ ({ if (filename) ; else __assert_fail ("filename", "bloom.c", 209, __extension__ __PRETTY_FUNCTION__); }));
    arg_t *subkeys;
    int i;
    subkeys = arg_create(filename, "$.-_()[]{} ", 0);
    for(i = 0; i < subkeys->argc; i++)
    {
        if(bloom_check_key(bloom, subkeys->argv[i]) != 0)
            break;
    }
    int rc = (i == subkeys->argc ? 0 : -1);
    arg_free(subkeys);
    return rc;
}

canonical_original_code:
int bloom_check_filename(struct bloom *bloom, char *filename)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 208, __extension__ __PRETTY_FUNCTION__); }));
    ((void) sizeof ((filename) ? 1 : 0), __extension__ ({ if (filename) ; else __assert_fail ("filename", "bloom.c", 209, __extension__ __PRETTY_FUNCTION__); }));
    struct arg_t *subkeys;
    int i;
    subkeys = arg_create(filename, "$.-_()[]{} ", 0);
    for(i = 0; i < subkeys->argc; i++)
    {
        if(bloom_check_key(bloom, subkeys->argv[i]) != 0)
            break;
    }
    int rc = (i == subkeys->argc ? 0 : -1);
    arg_free(subkeys);
    return rc;
}


decompiled_code:
void *__fastcall bloom_reset(void **a1)
{
if ( !a1 )
_assert_fail("bloom", "bloom.c", 0xE6u, "bloom_reset");
return memset(a1[1], 0, *(unsigned int *)a1);
}

canonical_decompiled_code:
void *__fastcall func10(void **a1)
{
if ( !a1 )
_assert_fail("bloom", "bloom.c", 0xE6u, "bloom_reset");
return memset(a1[1], 0, *(unsigned int *)a1);
}

original_code:
void bloom_reset(bloom_t *bloom)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 230, __extension__ __PRETTY_FUNCTION__); }));
    memset(bloom->filter, 0, bloom->length);
}

canonical_original_code:
void bloom_reset(struct bloom *bloom)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 230, __extension__ __PRETTY_FUNCTION__); }));
    memset(bloom->filter, 0, bloom->length);
}


decompiled_code:
void **__fastcall bloom_create(size_t size)
{
void **v1; // rax
void **v2; // r12

if ( !(_DWORD)size )
_assert_fail("length > 0", "bloom.c", 0x2Bu, "bloom_create");
v1 = (void **)malloc(0x18uLL);
*(_DWORD *)v1 = size;
v2 = v1;
v1[1] = malloc((unsigned int)size);
bloom_reset(v2);
return v2;
}

canonical_decompiled_code:
void **__fastcall func11(size_t size)
{
void **v1; // rax
void **v2; // r12

if ( !(_DWORD)size )
_assert_fail("length > 0", "bloom.c", 0x2Bu, "bloom_create");
v1 = (void **)malloc(0x18uLL);
*(_DWORD *)v1 = size;
v2 = v1;
v1[1] = malloc((unsigned int)size);
func10(v2);
return v2;
}

original_code:
bloom_t *bloom_create(unsigned length)
{
    bloom_t *bloom;
    ((void) sizeof ((length > 0) ? 1 : 0), __extension__ ({ if (length > 0) ; else __assert_fail ("length > 0", "bloom.c", 43, __extension__ __PRETTY_FUNCTION__); }));
    bloom = malloc(sizeof(bloom_t));
    bloom->length = length;
    bloom->filter = (unsigned char *)malloc(bloom->length);
    bloom_reset(bloom);
    return bloom;
}

canonical_original_code:
struct bloom *bloom_create(unsigned int length)
{
    struct bloom *bloom;
    ((void) sizeof ((length > 0) ? 1 : 0), __extension__ ({ if (length > 0) ; else __assert_fail ("length > 0", "bloom.c", 43, __extension__ __PRETTY_FUNCTION__); }));
    bloom = malloc(sizeof(bloom_t));
    bloom->length = length;
    bloom->filter = (unsigned char *)malloc(bloom->length);
    bloom_reset(bloom);
    return bloom;
}

variable_types:
length
unsigned int

return_type: struct bloom { unsigned int length; unsigned char *filter; unsigned int collisions; } *


decompiled_code:
__int64 __fastcall bloom_filled_bits(int *a1)
{
unsigned int v1; // er8
unsigned __int8 *v2; // rax
__int64 v3; // r10
unsigned __int8 *v4; // r9
unsigned __int8 *v5; // r10
int v6; // esi
int i; // ecx
bool v8; // al

if ( !a1 )
_assert_fail("bloom", "bloom.c", 0xEDu, "bloom_filled_bits");
v1 = *a1;
if ( *a1 )
{
v2 = (unsigned __int8 *)*((_QWORD *)a1 + 1);
v3 = v1 - 1;
v1 = 0;
v4 = v2 + 1;
v5 = &v2[v3 + 1];
while ( 1 )
{
v6 = *v2;
for ( i = 0; i != 8; ++i )
{
v8 = 1 << i == ((1 << i) & v6);
v1 += v8;
}
v2 = v4;
if ( v4 == v5 )
break;
++v4;
}
}
return v1;
}

canonical_decompiled_code:
__int64 __fastcall func12(int *a1)
{
unsigned int v1; // er8
unsigned __int8 *v2; // rax
__int64 v3; // r10
unsigned __int8 *v4; // r9
unsigned __int8 *v5; // r10
int v6; // esi
int i; // ecx
bool v8; // al

if ( !a1 )
_assert_fail("bloom", "bloom.c", 0xEDu, "bloom_filled_bits");
v1 = *a1;
if ( *a1 )
{
v2 = (unsigned __int8 *)*((_QWORD *)a1 + 1);
v3 = v1 - 1;
v1 = 0;
v4 = v2 + 1;
v5 = &v2[v3 + 1];
while ( 1 )
{
v6 = *v2;
for ( i = 0; i != 8; ++i )
{
v8 = 1 << i == ((1 << i) & v6);
v1 += v8;
}
v2 = v4;
if ( v4 == v5 )
break;
++v4;
}
}
return v1;
}

original_code:
unsigned bloom_filled_bits(bloom_t *bloom)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 237, __extension__ __PRETTY_FUNCTION__); }));
    unsigned tot = 0;
    unsigned i, j;
    for(i = 0; i < bloom->length; i++)
    {
        for(j = 0; j < 8; j++)
        {
            if((bloom->filter[i] & (1 << j)) == (1 << j))
                tot++;
        }
    }
    return tot;
}

canonical_original_code:
unsigned int bloom_filled_bits(struct bloom *bloom)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 237, __extension__ __PRETTY_FUNCTION__); }));
    unsigned int tot = 0;
    unsigned int i; unsigned int j;
    for(i = 0; i < bloom->length; i++)
    {
        for(j = 0; j < 8; j++)
        {
            if((bloom->filter[i] & (1 << j)) == (1 << j))
                tot++;
        }
    }
    return tot;
}

variable_types:
tot
unsigned int

variable_types:
i
unsigned int

variable_types:
j
unsigned int


decompiled_code:
float __fastcall bloom_filled_percent(int *a1)
{
if ( !a1 )
_assert_fail("bloom", "bloom.c", 0x100u, "bloom_filled_percent");
return (float)((float)(int)bloom_filled_bits(a1) * 100.0) / (float)(8 * *a1);
}

canonical_decompiled_code:
float __fastcall func13(int *a1)
{
if ( !a1 )
_assert_fail("bloom", "bloom.c", 0x100u, "bloom_filled_percent");
return (float)((float)(int)func12(a1) * 100.0) / (float)(8 * *a1);
}

original_code:
float bloom_filled_percent(bloom_t *bloom)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 256, __extension__ __PRETTY_FUNCTION__); }));
    unsigned tot = bloom_filled_bits(bloom);
    float percent = ((float)tot * 100) / (bloom->length * 8);
    return percent;
}

canonical_original_code:
float bloom_filled_percent(struct bloom *bloom)
{
    ((void) sizeof ((bloom) ? 1 : 0), __extension__ ({ if (bloom) ; else __assert_fail ("bloom", "bloom.c", 256, __extension__ __PRETTY_FUNCTION__); }));
    unsigned int tot = bloom_filled_bits(bloom);
    float percent = ((float)tot * 100) / (bloom->length * 8);
    return percent;
}

variable_types: struct bloom { unsigned int length; unsigned char *filter; unsigned int collisions; } *

variable_types: percent float

return_type: float


original_code:
void tt_init(TT_CONTEXT *ctx, unsigned int leafsize)
{
    ctx->count = 0;
    ctx->leaf[0] = 0;
    ctx->node[0] = 1;
    ctx->block = ctx->leaf + 1 ;
    ctx->index = 0;
    ctx->top = ctx->nodes;
    ctx->leafsize = leafsize;
    ctx->leaves = ((void *)0);
    ctx->leaves_len = 0;
    ctx->fin = 0;
}

canonical_original_code:
void tt_init(struct tt_context *ctx, unsigned int leafsize)
{
    ctx->count = 0;
    ctx->leaf[0] = 0;
    ctx->node[0] = 1;
    ctx->block = ctx->leaf + 1 ;
    ctx->index = 0;
    ctx->top = ctx->nodes;
    ctx->leafsize = leafsize;
    ctx->leaves = ((void *)0);
    ctx->leaves_len = 0;
    ctx->fin = 0;
}

variable_types: struct tt_context { unsigned long count; unsigned char leaf[-1]; unsigned char *block; unsigned char node[-1]; unsigned int index; unsigned char *top; unsigned char nodes[-1]; unsigned int leafsize; void *leaves; unsigned int leaves_len; int fin; } *

variable_types:
leafsize
unsigned int


original_code:
void tt_compose(TT_CONTEXT *ctx)
{
    u_int8_t *node = ctx->top - ((24+sizeof(uint32_t))*2);
    ((void) sizeof ((node >= ctx->nodes) ? 1 : 0), __extension__ ({ if (node >= ctx->nodes) ; else __assert_fail ("node >= ctx->nodes", "tigertree.c", 80, __extension__ __PRETTY_FUNCTION__); }));
    u_int32_t *bsp = (u_int32_t *)(node + 24);
    u_int32_t *bsp2 = (u_int32_t *)(node + (24+sizeof(uint32_t)) + 24);
    if(*bsp == ctx->leafsize)
    {
        tt_append_leaf(ctx, node);
        tt_append_leaf(ctx, node + (24+sizeof(uint32_t)));
    }
    else if(ctx->fin && *bsp2 <= ctx->leafsize && *bsp > ctx->leafsize)
    {
        tt_append_leaf(ctx, node + (24+sizeof(uint32_t)));
    }
    memmove(ctx->node + 1, node, 24);
    memmove(ctx->node + 1 + 24, node + (24+sizeof(uint32_t)), 24);
    tiger((u_int64_t *)(ctx->node), (u_int64_t)((24*2) + 1), (u_int64_t *)(ctx->top));
    ((u_int64_t *)node)[0] = (((u_int64_t *)ctx->top)[0]);
    ((u_int64_t *)node)[1] = (((u_int64_t *)ctx->top)[1]);
    ((u_int64_t *)node)[2] = (((u_int64_t *)ctx->top)[2]);
    *bsp *= 2;
    *bsp2 *= 2;
    ctx->top -= (24+sizeof(uint32_t));
}

canonical_original_code:
void tt_compose(struct tt_context *ctx)
{
    unsigned int *node = ctx->top - ((24+sizeof(uint32_t))*2);
    ((void) sizeof ((node >= ctx->nodes) ? 1 : 0), __extension__ ({ if (node >= ctx->nodes) ; else __assert_fail ("node >= ctx->nodes", "tigertree.c", 80, __extension__ __PRETTY_FUNCTION__); }));
    unsigned int *bsp = (u_int32_t *)(node + 24);
    unsigned int *bsp2 = (u_int32_t *)(node + (24+sizeof(uint32_t)) + 24);
    if(*bsp == ctx->leafsize)
    {
        tt_append_leaf(ctx, node);
        tt_append_leaf(ctx, node + (24+sizeof(unsigned int)));
    }
    else if(ctx->fin && *bsp2 <= ctx->leafsize && *bsp > ctx->leafsize)
    {
        tt_append_leaf(ctx, node + (24+sizeof(unsigned int)));
    }
    memmove(ctx->node + 1, node, 24);
    memmove(ctx->node + 1 + 24, node + (24+sizeof(unsigned int)), 24);
    tiger((unsigned int *)(ctx->node), (u_int64_t)((24*2) + 1), (unsigned int *)(ctx->top));
    ((unsigned int *)node)[0] = (((unsigned int *)ctx->top)[0]);
    ((unsigned int *)node)[1] = (((unsigned int *)ctx->top)[1]);
    ((unsigned int *)node)[2] = (((unsigned int *)ctx->top)[2]);
    *bsp *= 2;
    *bsp2 *= 2;
    ctx->top -= (24+sizeof(unsigned int));
}

variable_types:
node
unsigned int *

variable_types:
bsp
unsigned int *

user_defined_types: struct tt_context { unsigned long count; unsigned char leaf[-1]; unsigned char *block; unsigned char node[-1]; unsigned int index; unsigned char *top; unsigned char nodes[-1]; unsigned int leafsize; void *leaves; unsigned int leaves_len; int fin; }


original_code:
static void tt_block(TT_CONTEXT *ctx)
{
    u_int64_t b;
    tiger((u_int64_t *)ctx->leaf, (u_int64_t)ctx->index + 1, (u_int64_t *)ctx->top);
    ((u_int64_t *)ctx->top)[0] = (((u_int64_t *)ctx->top)[0]);
    ((u_int64_t *)ctx->top)[1] = (((u_int64_t *)ctx->top)[1]);
    ((u_int64_t *)ctx->top)[2] = (((u_int64_t *)ctx->top)[2]);
    u_int32_t *bsp = (u_int32_t *)(ctx->top + 24);
    *bsp = 1024;
    ctx->top += (24+sizeof(uint32_t));
    ++ctx->count;
    b = ctx->count;
    while((b & 0x01) == 0)
    {
        tt_compose(ctx);
        b = b >> 1;
    }
}

canonical_original_code:
static void tt_block(struct tt_context *ctx)
{
    unsigned int b;
    tiger((unsigned int *)ctx->leaf, (unsigned int)ctx->index + 1, (unsigned int *)ctx->top);
    ((unsigned int *)ctx->top)[0] = (((unsigned int *)ctx->top)[0]);
    ((unsigned int *)ctx->top)[1] = (((unsigned int *)ctx->top)[1]);
    ((unsigned int *)ctx->top)[2] = (((unsigned int *)ctx->top)[2]);
    unsigned int *bsp = (u_int32_t *)(ctx->top + 24);
    *bsp = 1024;
    ctx->top += (24+sizeof(unsigned int));
    ++ctx->count;
    b = ctx->count;
    while((b & 0x01) == 0)
    {
        tt_compose(ctx);
        b = b >> 1;
    }
}

variable_types:
b
unsigned int


decompiled_code:
char *__fastcall tt_final(__int64 a1)
{
char *result; // rax

if ( *(_DWORD *)(a1 + 1100) || (result = (char *)(a1 + 1112), *(_QWORD *)(a1 + 1104) == a1 + 1112) )
result = tt_block(a1);
return result;
}

canonical_decompiled_code:
char *__fastcall func3(__int64 a1)
{
char *result; // rax

if ( *(_DWORD *)(a1 + 1100) || (result = (char *)(a1 + 1112), *(_QWORD *)(a1 + 1104) == a1 + 1112) )
result = func2(a1);
return result;
}

original_code:
static void tt_final(TT_CONTEXT *ctx)
{
    if((ctx->index > 0) || (ctx->top == ctx->nodes))
    {
        tt_block(ctx);
    }
}

canonical_original_code:
static void tt_final(struct tt_context *ctx)
{
    if((ctx->index > 0) || (ctx->top == ctx->nodes))
    {
        tt_block(ctx);
    }
}


original_code:
void tt_update(TT_CONTEXT *ctx, u_int8_t *buffer, u_int32_t len)
{
    ((void) sizeof ((ctx->index <= 1024) ? 1 : 0), __extension__ ({ if (ctx->index <= 1024) ; else __assert_fail ("ctx->index <= BLOCKSIZE", "tigertree.c", 132, __extension__ __PRETTY_FUNCTION__); }));
    if(ctx->index)
    {
        unsigned left = 1024 - ctx->index;
        if(len < left)
        {
            memmove(ctx->block + ctx->index, buffer, len);
            ctx->index += len;
            return;
        }
        else
        {
            memmove(ctx->block + ctx->index, buffer, left);
            ctx->index = 1024;
            tt_block(ctx);
            buffer += left;
            len -= left;
        }
    }
    while(len >= 1024)
    {
        memmove(ctx->block, buffer, 1024);
        ctx->index = 1024;
        tt_block(ctx);
        buffer += 1024;
        len -= 1024;
    }
    if((ctx->index = len))
    {
        memmove(ctx->block, buffer, len);
    }
}

canonical_original_code:
void tt_update(struct tt_context *ctx, unsigned int *buffer, unsigned int len)
{
    ((void) sizeof ((ctx->index <= 1024) ? 1 : 0), __extension__ ({ if (ctx->index <= 1024) ; else __assert_fail ("ctx->index <= BLOCKSIZE", "tigertree.c", 132, __extension__ __PRETTY_FUNCTION__); }));
    if(ctx->index)
    {
        unsigned int left = 1024 - ctx->index;
        if(len < left)
        {
            memmove(ctx->block + ctx->index, buffer, len);
            ctx->index += len;
            return;
        }
        else
        {
            memmove(ctx->block + ctx->index, buffer, left);
            ctx->index = 1024;
            tt_block(ctx);
            buffer += left;
            len -= left;
        }
    }
    while(len >= 1024)
    {
        memmove(ctx->block, buffer, 1024);
        ctx->index = 1024;
        tt_block(ctx);
        buffer += 1024;
        len -= 1024;
    }
    if((ctx->index = len))
    {
        memmove(ctx->block, buffer, len);
    }
}

variable_types:
buffer
unsigned int *

variable_types:
len
unsigned int

variable_types:
left
unsigned int


decompiled_code:
void *__fastcall tt_digest(__int64 a1, void *a2)
{
__int64 v2; // rax
void *result; // rax

if ( *(_DWORD *)(a1 + 1100) > 0x400u )
_assert_fail("ctx->index <= BLOCKSIZE", "tigertree.c", 0xB4u, "tt_digest");
tt_final(a1);
v2 = *(_QWORD *)(a1 + 1104);
*(_DWORD *)(a1 + 2700) = 1;
if ( a1 + 1112 < (unsigned __int64)(v2 - 28) )
{
do
tt_compose(a1);
while ( a1 + 1112 < (unsigned __int64)(*(_QWORD *)(a1 + 1104) - 28LL) );
}
result = (void *)*(unsigned int *)(a1 + 2696);
if ( !(_DWORD)result )
result = tt_append_leaf(a1, (const __m128i *)(a1 + 1112));
if ( a2 )
result = memmove(a2, (const void *)(a1 + 1112), 0x18uLL);
return result;
}

canonical_decompiled_code:
void *__fastcall func5(__int64 a1, void *a2)
{
__int64 v2; // rax
void *result; // rax

if ( *(_DWORD *)(a1 + 1100) > 0x400u )
_assert_fail("ctx->index <= BLOCKSIZE", "tigertree.c", 0xB4u, "tt_digest");
func3(a1);
v2 = *(_QWORD *)(a1 + 1104);
*(_DWORD *)(a1 + 2700) = 1;
if ( a1 + 1112 < (unsigned __int64)(v2 - 28) )
{
do
func1(a1);
while ( a1 + 1112 < (unsigned __int64)(*(_QWORD *)(a1 + 1104) - 28LL) );
}
result = (void *)*(unsigned int *)(a1 + 2696);
if ( !(_DWORD)result )
result = tt_append_leaf(a1, (const __m128i *)(a1 + 1112));
if ( a2 )
result = memmove(a2, (const void *)(a1 + 1112), 0x18uLL);
return result;
}

original_code:
void tt_digest(TT_CONTEXT *ctx, u_int8_t *s)
{
    ((void) sizeof ((ctx->index <= 1024) ? 1 : 0), __extension__ ({ if (ctx->index <= 1024) ; else __assert_fail ("ctx->index <= BLOCKSIZE", "tigertree.c", 180, __extension__ __PRETTY_FUNCTION__); }));
    tt_final(ctx);
    ctx->fin = 1;
    while((ctx->top - (24+sizeof(uint32_t))) > ctx->nodes)
    {
        tt_compose(ctx);
    }
    if(ctx->leaves_len == 0)
        tt_append_leaf(ctx, ctx->nodes);
    if(s)
        memmove(s, ctx->nodes, 24);
}

canonical_original_code:
void tt_digest(struct tt_context *ctx, unsigned int *s)
{
    ((void) sizeof ((ctx->index <= 1024) ? 1 : 0), __extension__ ({ if (ctx->index <= 1024) ; else __assert_fail ("ctx->index <= BLOCKSIZE", "tigertree.c", 180, __extension__ __PRETTY_FUNCTION__); }));
    tt_final(ctx);
    ctx->fin = 1;
    while((ctx->top - (24+sizeof(unsigned int))) > ctx->nodes)
    {
        tt_compose(ctx);
    }
    if(ctx->leaves_len == 0)
        tt_append_leaf(ctx, ctx->nodes);
    if(s)
        memmove(s, ctx->nodes, 24);
}

variable_types:
s
unsigned int *


original_code:
void tt_destroy(TT_CONTEXT *ctx)
{
    if(ctx && ctx->leaves)
    {
        free(ctx->leaves);
        ctx->leaves = 0;
    }
}

canonical_original_code:
void tt_destroy(struct tt_context *ctx)
{
    if(ctx && ctx->leaves)
    {
        free(ctx->leaves);
        ctx->leaves = 0;
    }
}


decompiled_code:
__int64 __fastcall tt_base32(__int64 a1)
{
return base32_encode(a1 + 1112, 24LL);
}

canonical_decompiled_code:
__int64 __fastcall func7(__int64 a1)
{
return base32_encode(a1 + 1112, 24LL);
}

original_code:
char *tt_base32(TT_CONTEXT *ctx)
{
    return base32_encode((char *)ctx->nodes, 24);
}

canonical_original_code:
char *tt_base32(struct tt_context *ctx)
{
    return base32_encode((char *)ctx->nodes, 24);
}