decompiled_code:
__int64 __fastcall avl_apply(_QWORD *a1, unsigned int (__fastcall *a2)(_QWORD, __int64), __int64 a3, unsigned int a4, unsigned int a5)
{
switch ( a5 )
{
case 2u:
return avl_inapply(a1, a2, a3, a4);
case 3u:
return avl_postapply(a1, (__int64 (__fastcall *)(_QWORD, __int64))a2, a3, a4);
case 1u:
return avl_preapply(a1, (__int64 (__fastcall *)(_QWORD, __int64))a2, a3, a4);
}
fprintf(stderr, "Invalid traversal type %d\n", a5);
return 0xFFFFFFFFLL;
}

canonical_decompiled_code:
__int64 __fastcall func6(_QWORD *a1, unsigned int (__fastcall *a2)(_QWORD, __int64), __int64 a3, unsigned int a4, unsigned int a5)
{
switch ( a5 )
{
case 2u:
return func0(a1, a2, a3, a4);
case 3u:
return func1(a1, (__int64 (__fastcall *)(_QWORD, __int64))a2, a3, a4);
case 1u:
return func2(a1, (__int64 (__fastcall *)(_QWORD, __int64))a2, a3, a4);
}
fprintf(stderr, "Invalid traversal type %d\n", a5);
return 0xFFFFFFFFLL;
}

original_code:
int
avl_apply( Avlnode *root, AVL_APPLY fn, void* arg, int stopflag, int type )
{
 switch ( type ) {
 case 2:
  return( avl_inapply( root, fn, arg, stopflag ) );
 case 1:
  return( avl_preapply( root, fn, arg, stopflag ) );
 case 3:
  return( avl_postapply( root, fn, arg, stopflag ) );
 default:
  fprintf( stderr, "Invalid traversal type %d\n", type );
  return( -1 );
 }
}

canonical_original_code:
int avl_apply(struct avlnode *root, int (*fn)(void *, void *), void *arg, int stopflag, int type)
{
 switch ( type ) {
 case 2:
  return( avl_inapply( root, fn, arg, stopflag ) );
 case 1:
  return( avl_preapply( root, fn, arg, stopflag ) );
 case 3:
  return( avl_postapply( root, fn, arg, stopflag ) );
 default:
  fprintf( stderr, "Invalid traversal type %d\n", type );
  return( -1 );
 }
}

variable_types: struct avlnode { void *avl_data; struct avlnode *avl_link[2]; char avl_bits[2]; char avl_bf; } *

variable_types:
fn
int (*)(void *, void *)

variable_types: type int


repo: mistotebe/skeeter

decompiled_code:
__int64 __fastcall avl_prefixapply(_QWORD *a1, __int64 a2, unsigned int (__fastcall *a3)(_QWORD, __int64), __int64 a4, __int64 (__fastcall *a5)(__int64, _QWORD), int a6, unsigned int a7)
{
_QWORD *v7; // r15
int v11; // eax
__int64 v12; // rdi

v7 = a1;
if ( !a1 )
return 4294967290LL;
while ( 1 )
{
v11 = a5(a2, *v7);
if ( !v11 )
break;
if ( v11 >= 0 )
{
LABEL_6:
v7 = (_QWORD *)v7[2];
if ( !v7 )
return 4294967290LL;
}
else
{
v7 = (_QWORD *)v7[1];
if ( !v7 )
return 4294967290LL;
}
}
if ( a3(*v7, a4) != a7 )
{
v12 = v7[1];
if ( !v12 || (unsigned int)avl_prefixapply(v12, a2, (_DWORD)a3, a4, (_DWORD)a5, a6, a7) != a7 )
goto LABEL_6;
}
return a7;
}

original_code:
int
avl_prefixapply(
    Avlnode *root,
    void* data,
    AVL_CMP fmatch,
    void* marg,
    AVL_CMP fcmp,
    void* carg,
    int stopflag
)
{
 int cmp;
 if ( root == 0 )
  return( (-6) );
 cmp = (*fcmp)( data, root->avl_data );
 if ( cmp == 0 ) {
  if ( (*fmatch)( root->avl_data, marg ) == stopflag )
   return( stopflag );
  if ( root->avl_link[0] != 0 )
   if ( avl_prefixapply( root->avl_link[0], data, fmatch,
       marg, fcmp, carg, stopflag ) == stopflag )
    return( stopflag );
  if ( root->avl_link[1] != 0 )
   return( avl_prefixapply( root->avl_link[1], data, fmatch,
       marg, fcmp, carg, stopflag ) );
  else
   return( (-6) );
 } else if ( cmp < 0 ) {
  if ( root->avl_link[0] != 0 )
   return( avl_prefixapply( root->avl_link[0], data, fmatch,
       marg, fcmp, carg, stopflag ) );
 } else {
  if ( root->avl_link[1] != 0 )
   return( avl_prefixapply( root->avl_link[1], data, fmatch,
       marg, fcmp, carg, stopflag ) );
 }
 return( (-6) );
}

canonical_original_code:
int avl_prefixapply(struct avlnode *root, void *data, int (*fmatch)(void *, void *), void *marg, int (*fcmp)(void *, void *), void *carg, int stopflag)
{
 int cmp;
 if ( root == 0 )
  return( (-6) );
 cmp = (*fcmp)( data, root->avl_data );
 if ( cmp == 0 ) {
  if ( (*fmatch)( root->avl_data, marg ) == stopflag )
   return( stopflag );
  if ( root->avl_link[0] != 0 )
   if ( avl_prefixapply( root->avl_link[0], data, fmatch,
       marg, fcmp, carg, stopflag ) == stopflag )
    return( stopflag );
  if ( root->avl_link[1] != 0 )
   return( avl_prefixapply( root->avl_link[1], data, fmatch,
       marg, fcmp, carg, stopflag ) );
  else
   return( (-6) );
 } else if ( cmp < 0 ) {
  if ( root->avl_link[0] != 0 )
   return( avl_prefixapply( root->avl_link[0], data, fmatch,
       marg, fcmp, carg, stopflag ) );
 } else {
  if ( root->avl_link[1] != 0 )
   return( avl_prefixapply( root->avl_link[1], data, fmatch,
       marg, fcmp, carg, stopflag ) );
 }
 return( (-6) );
}

variable_types:
data
void *

variable_types:
fmatch
int (*)(void *, void *)

variable_types:
marg
void *

variable_types:
fcmp
int (*)(void *, void *)

variable_types:
carg
void *

variable_types: stopflag int

variable_types: cmp int

return_type: int

user_defined_types: struct avlnode { void *avl_data; struct avlnode *avl_link[2]; char avl_bits[2]; char avl_bf; }


decompiled_code:
__int64 __fastcall avl_free(_QWORD *a1, void (__fastcall *a2)(_QWORD))
{
int v3; // ebx
__int64 v4; // rdi

if ( !a1 )
return 0LL;
v3 = 0;
if ( a1[1] )
v3 = ((__int64 (*)(void))avl_free)();
v4 = a1[2];
if ( v4 )
v3 += avl_free(v4, a2);
if ( a2 )
a2(*a1);
ber_memfree(a1);
return (unsigned int)(v3 + 1);
}

canonical_decompiled_code:
__int64 __fastcall func8(_QWORD *a1, void (__fastcall *a2)(_QWORD))
{
int v3; // ebx
__int64 v4; // rdi

if ( !a1 )
return 0LL;
v3 = 0;
if ( a1[1] )
v3 = ((__int64 (*)(void))avl_free)();
v4 = a1[2];
if ( v4 )
v3 += func8(v4, a2);
if ( a2 )
a2(*a1);
ber_memfree(a1);
return (unsigned int)(v3 + 1);
}

original_code:
int
avl_free( Avlnode *root, AVL_FREE dfree )
{
 int nleft, nright;
 if ( root == 0 )
  return( 0 );
 nleft = nright = 0;
 if ( root->avl_link[0] != 0 )
  nleft = avl_free( root->avl_link[0], dfree );
 if ( root->avl_link[1] != 0 )
  nright = avl_free( root->avl_link[1], dfree );
 if ( dfree )
  (*dfree)( root->avl_data );
 ber_memfree( root );
 return( nleft + nright + 1 );
}

canonical_original_code:
int avl_free(struct avlnode *root, void (*dfree)(void *))
{
 int nleft; int nright;
 if ( root == 0 )
  return( 0 );
 nleft = nright = 0;
 if ( root->avl_link[0] != 0 )
  nleft = avl_free( root->avl_link[0], dfree );
 if ( root->avl_link[1] != 0 )
  nright = avl_free( root->avl_link[1], dfree );
 if ( dfree )
  (*dfree)( root->avl_data );
 ber_memfree( root );
 return( nleft + nright + 1 );
}

variable_types:
dfree
void (*)(void *)

variable_types: nleft int

variable_types: nright int


decompiled_code:
__int64 __fastcall avl_find(_QWORD *a1, __int64 a2, __int64 (__fastcall *a3)(__int64, _QWORD))
{
_QWORD *v4; // rbx
int i; // eax

if ( !a1 )
return 0LL;
v4 = a1;
for ( i = a3(a2, *a1); ; i = a3(a2, *v4) )
{
if ( !i )
return *v4;
v4 = (_QWORD *)v4[(i > 0) + 1];
if ( !v4 )
break;
}
return 0LL;
}

canonical_decompiled_code:
__int64 __fastcall func9(_QWORD *a1, __int64 a2, __int64 (__fastcall *a3)(__int64, _QWORD))
{
_QWORD *v4; // rbx
int i; // eax

if ( !a1 )
return 0LL;
v4 = a1;
for ( i = a3(a2, *a1); ; i = a3(a2, *v4) )
{
if ( !i )
return *v4;
v4 = (_QWORD *)v4[(i > 0) + 1];
if ( !v4 )
break;
}
return 0LL;
}

original_code:
void*
avl_find( Avlnode *root, const void* data, AVL_CMP fcmp )
{
 int cmp;
 while ( root != 0 && (cmp = (*fcmp)( data, root->avl_data )) != 0 ) {
  cmp = cmp > 0;
  root = root->avl_link[cmp];
 }
 return( root ? root->avl_data : 0 );
}

canonical_original_code:
void *avl_find(struct avlnode *root, void *data, int (*fcmp)(void *, void *))
{
 int cmp;
 while ( root != 0 && (cmp = (*fcmp)( data, root->avl_data )) != 0 ) {
  cmp = cmp > 0;
  root = root->avl_link[cmp];
 }
 return( root ? root->avl_data : 0 );
}

return_type: void *


decompiled_code:
__int64 __fastcall avl_find_lin(_QWORD *a1, __int64 a2, __int64 (__fastcall *a3)(__int64, _QWORD))
{
_QWORD *v4; // rbx
int i; // eax
__int64 v6; // rdi
__int64 result; // rax

if ( !a1 )
return 0LL;
v4 = a1;
for ( i = a3(a2, *a1); ; i = a3(a2, *v4) )
{
if ( !i )
return *v4;
v6 = v4[1];
if ( v6 )
{
result = avl_find_lin(v6, a2, a3);
if ( result )
return result;
}
v4 = (_QWORD *)v4[2];
if ( !v4 )
break;
}
return 0LL;
}

canonical_decompiled_code:
__int64 __fastcall func10(_QWORD *a1, __int64 a2, __int64 (__fastcall *a3)(__int64, _QWORD))
{
_QWORD *v4; // rbx
int i; // eax
__int64 v6; // rdi
__int64 result; // rax

if ( !a1 )
return 0LL;
v4 = a1;
for ( i = a3(a2, *a1); ; i = a3(a2, *v4) )
{
if ( !i )
return *v4;
v6 = v4[1];
if ( v6 )
{
result = func10(v6, a2, a3);
if ( result )
return result;
}
v4 = (_QWORD *)v4[2];
if ( !v4 )
break;
}
return 0LL;
}

original_code:
void*
avl_find_lin( Avlnode *root, const void* data, AVL_CMP fcmp )
{
 void* res;
 if ( root == 0 )
  return( ((void *)0) );
 if ( (*fcmp)( data, root->avl_data ) == 0 )
  return( root->avl_data );
 if ( root->avl_link[0] != 0 )
  if ( (res = avl_find_lin( root->avl_link[0], data, fcmp ))
      != ((void *)0) )
   return( res );
 if ( root->avl_link[1] == 0 )
  return( ((void *)0) );
 else
  return( avl_find_lin( root->avl_link[1], data, fcmp ) );
}

canonical_original_code:
void *avl_find_lin(struct avlnode *root, void *data, int (*fcmp)(void *, void *))
{
 void *res;
 if ( root == 0 )
  return( ((void *)0) );
 if ( (*fcmp)( data, root->avl_data ) == 0 )
  return( root->avl_data );
 if ( root->avl_link[0] != 0 )
  if ( (res = avl_find_lin( root->avl_link[0], data, fcmp ))
      != ((void *)0) )
   return( res );
 if ( root->avl_link[1] == 0 )
  return( ((void *)0) );
 else
  return( avl_find_lin( root->avl_link[1], data, fcmp ) );
}

variable_types:
res
void *


decompiled_code:
__int64 __fastcall avl_getfirst(_QWORD *a1)
{
__int64 v1; // rax

if ( avl_list )
{
ber_memfree(avl_list);
avl_list = 0LL;
}
avl_maxlist = 0;
avl_nextlist = 0;
if ( !a1 )
return 0LL;
avl_apply(a1, (unsigned int (__fastcall *)(_QWORD, __int64))avl_buildlist, 0LL, 0xFFFFFFFF, 2u);
v1 = avl_nextlist++;
return *(_QWORD *)(avl_list + 8 * v1);
}

canonical_decompiled_code:
__int64 __fastcall func11(_QWORD *a1)
{
__int64 v1; // rax

if ( avl_list )
{
ber_memfree(avl_list);
avl_list = 0LL;
}
avl_maxlist = 0;
avl_nextlist = 0;
if ( !a1 )
return 0LL;
func6(a1, (unsigned int (__fastcall *)(_QWORD, __int64))avl_buildlist, 0LL, 0xFFFFFFFF, 2u);
v1 = avl_nextlist++;
return *(_QWORD *)(avl_list + 8 * v1);
}

original_code:
void*
avl_getfirst( Avlnode *root )
{
 if ( avl_list ) {
  ber_memfree( (char *) avl_list);
  avl_list = (void* *) 0;
 }
 avl_maxlist = 0;
 avl_nextlist = 0;
 if ( root == 0 )
  return( 0 );
 (void) avl_apply( root, avl_buildlist, (void*) 0, -1, 2 );
 return( avl_list[ avl_nextlist++ ] );
}

canonical_original_code:
void *avl_getfirst(struct avlnode *root)
{
 if ( avl_list ) {
  ber_memfree( (char *) avl_list);
  avl_list = (void **) 0;
 }
 avl_maxlist = 0;
 avl_nextlist = 0;
 if ( root == 0 )
  return( 0 );
 (void) avl_apply( root, avl_buildlist, (void *) 0, -1, 2 );
 return( avl_list[ avl_nextlist++ ] );
}


decompiled_code:
__int64 avl_getnext()
{
__int64 v0; // r8

v0 = avl_list;
if ( !avl_list )
return v0;
if ( avl_nextlist != avl_maxlist )
return *(_QWORD *)(avl_list + 8LL * avl_nextlist++);
ber_memfree(avl_list);
avl_list = 0LL;
return 0LL;
}

canonical_decompiled_code:
__int64 func12()
{
__int64 v0; // r8

v0 = avl_list;
if ( !avl_list )
return v0;
if ( avl_nextlist != avl_maxlist )
return *(_QWORD *)(avl_list + 8LL * avl_nextlist++);
ber_memfree(avl_list);
avl_list = 0LL;
return 0LL;
}

original_code:
void*
avl_getnext( void )
{
 if ( avl_list == 0 )
  return( 0 );
 if ( avl_nextlist == avl_maxlist ) {
  ber_memfree( (void*) avl_list);
  avl_list = (void* *) 0;
  return( 0 );
 }
 return( avl_list[ avl_nextlist++ ] );
}

canonical_original_code:
void *avl_getnext()
{
 if ( avl_list == 0 )
  return( 0 );
 if ( avl_nextlist == avl_maxlist ) {
  ber_memfree( (void *) avl_list);
  avl_list = (void **) 0;
  return( 0 );
 }
 return( avl_list[ avl_nextlist++ ] );
}


decompiled_code:
__int64 avl_dup_error()
{
return 0xFFFFFFFFLL;
}

canonical_decompiled_code:
__int64 func13()
{
return 0xFFFFFFFFLL;
}

original_code:
int
avl_dup_error( void* left, void* right )
{
 return( -1 );
}

canonical_original_code:
int avl_dup_error(void *left, void *right)
{
 return( -1 );
}

variable_types:
left
void *

variable_types:
right
void *


decompiled_code:
__int64 avl_dup_ok()
{
return 0LL;
}

canonical_decompiled_code:
__int64 func14()
{
return 0LL;
}

original_code:
int
avl_dup_ok( void* left, void* right )
{
 return( 0 );
}

canonical_original_code:
int avl_dup_ok(void *left, void *right)
{
 return( 0 );
}


decompiled_code:
// attributes: thunk
void skeeter_syslog(int pri, const char *fmt, __gnuc_va_list ap)
{
vsyslog(pri, fmt, ap);
}

canonical_decompiled_code:
void func0(int pri, const char *fmt, __gnuc_va_list ap)
{
vsyslog(pri, fmt, ap);
}

original_code:
void
skeeter_syslog(int level, const char *format, va_list args)
{
    vsyslog(level, format, args);
}

canonical_original_code:
void skeeter_syslog(int level, char *format, __builtin_va_list args)
{
    vsyslog(level, format, args);
}

variable_types: level int

variable_types:
format
char *

return_type: void


decompiled_code:
int __fastcall skeeter_stderr(int a1, const char *a2, void *a3)
{
fprintf(stderr, "%s:\t", (&level_table)[2 * a1]);
vfprintf(stderr, a2, a3);
return fputc(10, stderr);
}

canonical_decompiled_code:
int __fastcall func1(int a1, const char *a2, void *a3)
{
fprintf(stderr, "%s:\t", (&level_table)[2 * a1]);
vfprintf(stderr, a2, a3);
return fputc(10, stderr);
}

original_code:
void
skeeter_stderr(int level, const char *format, va_list args)
{
    fprintf(stderr, "%s:\t", level_table[level].name);
    vfprintf(stderr, format, args);
    fprintf(stderr, "\n");
}

canonical_original_code:
void skeeter_stderr(int level, char *format, __builtin_va_list args)
{
    fprintf(stderr, "%s:\t", level_table[level].name);
    vfprintf(stderr, format, args);
    fprintf(stderr, "\n");
}


decompiled_code:
__int64 skeeter_log(__int64 a1, __int64 a2, ...)
{
__int64 result; // rax
gcc_va_list va; // [rsp+8h] [rbp-D0h] BYREF

if ( config[2] >= (int)a1 )
{
va_start(va, a2);
result = skeeter_vlog(a1, a2, va);
}
return result;
}

canonical_decompiled_code:
__int64 func2(__int64 a1, __int64 a2, ...)
{
__int64 result; // rax
gcc_va_list va; // [rsp+8h] [rbp-D0h] BYREF

if ( config[2] >= (int)a1 )
{
va_start(va, a2);
result = skeeter_vlog(a1, a2, va);
}
return result;
}

original_code:
void
skeeter_log(int level, const char *format, ...)
{
    va_list args;
    if (level > config.loglevel)
        return;
    __builtin_va_start(args,format);
    skeeter_vlog(level, format, args);
    __builtin_va_end(args);
}

canonical_original_code:
void skeeter_log(int level, char *format, ...)
{
    __builtin_va_list args;
    if (level > config.loglevel)
        return;
    __builtin_va_start(args,format);
    skeeter_vlog(level, format, args);
    __builtin_va_end(args);
}


decompiled_code:
__int64 __fastcall skeeter_event_log(__int64 a1, const char *a2)
{
return skeeter_log(a1, (__int64)"%s", a2);
}

canonical_decompiled_code:
__int64 __fastcall func4(__int64 a1, const char *a2)
{
return func2(a1, (__int64)"%s", a2);
}

original_code:
void skeeter_event_log(int severity, const char *msg)
{
    skeeter_log(severity, "%s", msg);
}

canonical_original_code:
void skeeter_event_log(int severity, char *msg)
{
    skeeter_log(severity, "%s", msg);
}

variable_types: severity int

variable_types:
msg
char *


decompiled_code:
char *__fastcall filter_get(__int64 *a1, __int64 a2)
{
int v2; // eax
size_t v3; // rbp
size_t v4; // r12
char *v5; // rax
char *v6; // r13
__int64 v7; // rbx
char *v8; // rcx
unsigned int v9; // eax
_BYTE *v11; // rax
size_t n[2]; // [rsp+0h] [rbp-48h] BYREF
size_t v13[2]; // [rsp+10h] [rbp-38h] BYREF

*(_OWORD *)n = 0LL;
*(_OWORD *)v13 = 0LL;
if ( (unsigned int)ldap_bv2escaped_filter_value(a2, n) )
{
v3 = n[0];
goto LABEL_13;
}
v2 = ldap_bv2escaped_filter_value(a2 + 16, v13);
v3 = n[0];
if ( v2 )
{
LABEL_13:
v6 = 0LL;
goto LABEL_14;
}
v4 = v13[0];
v5 = (char *)calloc(
*((_DWORD *)a1 + 4)
+ LODWORD(v13[0]) * *((_DWORD *)a1 + 6)
+ LODWORD(n[0]) * *((_DWORD *)a1 + 5)
+ *((_DWORD *)a1 + 7) * (LODWORD(v13[0]) + LODWORD(n[0]) + 1)
+ 1,
1uLL);
v6 = v5;
if ( v5 )
{
v7 = *a1;
if ( *a1 )
{
v8 = v5;
while ( 1 )
{
v9 = *(_DWORD *)v7;
if ( *(_DWORD *)v7 == 2 )
break;
if ( v9 > 2 )
{
if ( v9 != 3 )
_assert_fail("0", "filter.c", 0x96u, "filter_get");
v8 = (char *)memcpy(v8, *(const void **)(*(_QWORD *)(v7 + 8) + 8LL), **(_QWORD **)(v7 + 8))
+ **(_QWORD **)(v7 + 8);
goto LABEL_7;
}
if ( v9 )
goto LABEL_11;
v8 = (char *)memcpy(v8, (const void *)n[1], v3) + v3;
LABEL_7:
v7 = *(_QWORD *)(v7 + 16);
if ( !v7 )
goto LABEL_14;
}
v11 = memcpy(v8, (const void *)n[1], v3);
v11[v3] = 64;
v8 = &v11[v3 + 1];
LABEL_11:
v8 = (char *)memcpy(v8, (const void *)v13[1], v4) + v4;
goto LABEL_7;
}
}
LABEL_14:
if ( v3 )
ber_memfree(n[1]);
if ( v13[0] )
ber_memfree(v13[1]);
return v6;
}

canonical_decompiled_code:
char *__fastcall func1(__int64 *a1, __int64 a2)
{
int v2; // eax
size_t v3; // rbp
size_t v4; // r12
char *v5; // rax
char *v6; // r13
__int64 v7; // rbx
char *v8; // rcx
unsigned int v9; // eax
_BYTE *v11; // rax
size_t n[2]; // [rsp+0h] [rbp-48h] BYREF
size_t v13[2]; // [rsp+10h] [rbp-38h] BYREF

*(_OWORD *)n = 0LL;
*(_OWORD *)v13 = 0LL;
if ( (unsigned int)ldap_bv2escaped_filter_value(a2, n) )
{
v3 = n[0];
goto LABEL_13;
}
v2 = ldap_bv2escaped_filter_value(a2 + 16, v13);
v3 = n[0];
if ( v2 )
{
LABEL_13:
v6 = 0LL;
goto LABEL_14;
}
v4 = v13[0];
v5 = (char *)calloc(
*((_DWORD *)a1 + 4)
+ LODWORD(v13[0]) * *((_DWORD *)a1 + 6)
+ LODWORD(n[0]) * *((_DWORD *)a1 + 5)
+ *((_DWORD *)a1 + 7) * (LODWORD(v13[0]) + LODWORD(n[0]) + 1)
+ 1,
1uLL);
v6 = v5;
if ( v5 )
{
v7 = *a1;
if ( *a1 )
{
v8 = v5;
while ( 1 )
{
v9 = *(_DWORD *)v7;
if ( *(_DWORD *)v7 == 2 )
break;
if ( v9 > 2 )
{
if ( v9 != 3 )
_assert_fail("0", "filter.c", 0x96u, "filter_get");
v8 = (char *)memcpy(v8, *(const void **)(*(_QWORD *)(v7 + 8) + 8LL), **(_QWORD **)(v7 + 8))
+ **(_QWORD **)(v7 + 8);
goto LABEL_7;
}
if ( v9 )
goto LABEL_11;
v8 = (char *)memcpy(v8, (const void *)n[1], v3) + v3;
LABEL_7:
v7 = *(_QWORD *)(v7 + 16);
if ( !v7 )
goto LABEL_14;
}
v11 = memcpy(v8, (const void *)n[1], v3);
v11[v3] = 64;
v8 = &v11[v3 + 1];
LABEL_11:
v8 = (char *)memcpy(v8, (const void *)v13[1], v4) + v4;
goto LABEL_7;
}
}
LABEL_14:
if ( v3 )
ber_memfree(n[1]);
if ( v13[0] )
ber_memfree(v13[1]);
return v6;
}

original_code:
char *
filter_get(struct filter *filter, struct user_info *info)
{
    char *ptr, *result = ((void *)0);
    struct filter_part *item;
    struct berval esc_username = { .bv_len = 0 };
    struct berval esc_domainname = { .bv_len = 0 };
    int addr_len, total;
    if (ldap_bv2escaped_filter_value(&info->username, &esc_username))
        goto filter_get_done;
    if (ldap_bv2escaped_filter_value(&info->domain, &esc_domainname))
        goto filter_get_done;
    addr_len = esc_username.bv_len + 1 + esc_domainname.bv_len;
    total = filter->total_len;
    total += esc_username.bv_len * filter->occurrence[USER];
    total += esc_domainname.bv_len * filter->occurrence[DOMAIN];
    total += addr_len * filter->occurrence[ADDR];
    total++;
    result = calloc(total, sizeof(char));
    if (!result)
        goto filter_get_done;
    ptr = result;
    for ((item) = ((&filter->body)->stqh_first); (item); (item) = ((item)->next.stqe_next)) {
        switch(item->token_type) {
            case USER:
                memcpy((ptr), (&esc_username)->bv_val, (&esc_username)->bv_len); (ptr) += (&esc_username)->bv_len;;
                break;
            case DOMAIN:
                memcpy((ptr), (&esc_domainname)->bv_val, (&esc_domainname)->bv_len); (ptr) += (&esc_domainname)->bv_len;;
                break;
            case ADDR:
                memcpy((ptr), (&esc_username)->bv_val, (&esc_username)->bv_len); (ptr) += (&esc_username)->bv_len;;
                *ptr = '@'; ptr++;
                memcpy((ptr), (&esc_domainname)->bv_val, (&esc_domainname)->bv_len); (ptr) += (&esc_domainname)->bv_len;;
                break;
            case LITERAL:
                memcpy((ptr), (item->text)->bv_val, (item->text)->bv_len); (ptr) += (item->text)->bv_len;;
                break;
            default:
                ((void) sizeof ((0) ? 1 : 0), __extension__ ({ if (0) ; else __assert_fail ("0", "filter.c", 150, __extension__ __PRETTY_FUNCTION__); }));
        }
    }
filter_get_done:
    if (esc_username.bv_len) ber_memfree(esc_username.bv_val);
    if (esc_domainname.bv_len) ber_memfree(esc_domainname.bv_val);
    return result;
}

canonical_original_code:
char *filter_get(struct filter *filter, struct user_info *info)
{
    char *ptr; char *result = ((void *)0);
    struct filter_part *item;
    struct berval esc_username = { .bv_len = 0 };
    struct berval esc_domainname = { .bv_len = 0 };
    int addr_len; int total;
    if (ldap_bv2escaped_filter_value(&info->username, &esc_username))
        goto filter_get_done;
    if (ldap_bv2escaped_filter_value(&info->domain, &esc_domainname))
        goto filter_get_done;
    addr_len = esc_username.bv_len + 1 + esc_domainname.bv_len;
    total = filter->total_len;
    total += esc_username.bv_len * filter->occurrence[USER];
    total += esc_domainname.bv_len * filter->occurrence[DOMAIN];
    total += addr_len * filter->occurrence[ADDR];
    total++;
    result = calloc(total, sizeof(char));
    if (!result)
        goto filter_get_done;
    ptr = result;
    for ((item) = ((&filter->body)->stqh_first); (item); (item) = ((item)->next.stqe_next)) {
        switch(item->token_type) {
            case USER:
                memcpy((ptr), (&esc_username)->bv_val, (&esc_username)->bv_len); (ptr) += (&esc_username)->bv_len;;
                break;
            case DOMAIN:
                memcpy((ptr), (&esc_domainname)->bv_val, (&esc_domainname)->bv_len); (ptr) += (&esc_domainname)->bv_len;;
                break;
            case ADDR:
                memcpy((ptr), (&esc_username)->bv_val, (&esc_username)->bv_len); (ptr) += (&esc_username)->bv_len;;
                *ptr = '@'; ptr++;
                memcpy((ptr), (&esc_domainname)->bv_val, (&esc_domainname)->bv_len); (ptr) += (&esc_domainname)->bv_len;;
                break;
            case LITERAL:
                memcpy((ptr), (item->text)->bv_val, (item->text)->bv_len); (ptr) += (item->text)->bv_len;;
                break;
            default:
                ((void) sizeof ((0) ? 1 : 0), __extension__ ({ if (0) ; else __assert_fail ("0", "filter.c", 150, __extension__ __PRETTY_FUNCTION__); }));
        }
    }
filter_get_done:
    if (esc_username.bv_len) ber_memfree(esc_username.bv_val);
    if (esc_domainname.bv_len) ber_memfree(esc_domainname.bv_val);
    return result;
}

variable_types: struct filter { struct filterhead { struct filter_part { enum filter_token { USER=0, DOMAIN=1, ADDR=2, LITERAL=3 } token_type; struct berval { unsigned long bv_len; char *bv_val; } *text; struct { struct filter_part *stqe_next; } next; } *stqh_first; struct filter_part **stqh_last; } body; int total_len; int occurrence[-1]; } *

variable_types: struct user_info { struct berval username; char **attrs; } *

variable_types:
ptr
char *

variable_types:
result
char *

variable_types: total int

return_type: char *

user_defined_types: struct filter { struct filterhead body; int total_len; int occurrence[-1]; }

user_defined_types: struct filter_part { enum filter_token token_type; struct berval *text; struct { struct filter_part *stqe_next; } next; }

user_defined_types: struct filterhead { struct filter_part *stqh_first; struct filter_part **stqh_last; }


decompiled_code:
_BOOL8 __fastcall parse_options(int argc, char **argv, __int64 a3)
{
int v4; // eax
int longind[7]; // [rsp+Ch] [rbp-1Ch] BYREF

while ( 1 )
{
while ( 1 )
{
while ( 1 )
{
v4 = getopt_long(argc, argv, "f:dP:v", &options, longind);
if ( v4 == -1 )
return optind < argc;
if ( v4 != 100 )
break;
++*(_DWORD *)a3;
}
if ( v4 > 100 )
break;
if ( v4 )
{
if ( v4 != 80 )
return 1LL;
*(_QWORD *)(a3 + 24) = optarg;
}
}
if ( v4 != 102 )
break;
*(_QWORD *)(a3 + 16) = optarg;
}
if ( v4 == 118 )
{
puts("Skeeter");
exit(0);
}
return 1LL;
}

canonical_decompiled_code:
_BOOL8 __fastcall func0(int argc, char **argv, __int64 a3)
{
int v4; // eax
int longind[7]; // [rsp+Ch] [rbp-1Ch] BYREF

while ( 1 )
{
while ( 1 )
{
while ( 1 )
{
v4 = getopt_long(argc, argv, "f:dP:v", &options, longind);
if ( v4 == -1 )
return optind < argc;
if ( v4 != 100 )
break;
++*(_DWORD *)a3;
}
if ( v4 > 100 )
break;
if ( v4 )
{
if ( v4 != 80 )
return 1LL;
*(_QWORD *)(a3 + 24) = optarg;
}
}
if ( v4 != 102 )
break;
*(_QWORD *)(a3 + 16) = optarg;
}
if ( v4 == 118 )
{
puts("Skeeter");
exit(0);
}
return 1LL;
}

original_code:
int
parse_options(int argc, char **argv, struct config *config)
{
    int opt, option_index;
    while ((opt = getopt_long(argc, argv, shortopts,
                options, &option_index)) != -1)
    {
        switch (opt)
        {
            case 0:
                break;
            case 'd':
                config->debug++;
                break;
            case 'f':
                config->conffile = optarg;
                break;
            case 'P':
                config->pidfile = optarg;
                break;
            case 'v':
                printf("Skeeter\n");
                exit(0);
                break;
            default:
                return 1;
        }
    }
    if (optind < argc) {
        return 1;
    }
    return 0;
}

canonical_original_code:
int parse_options(int argc, char **argv, struct config *config)
{
    int opt; int option_index;
    while ((opt = getopt_long(argc, argv, shortopts,
                options, &option_index)) != -1)
    {
        switch (opt)
        {
            case 0:
                break;
            case 'd':
                config->debug++;
                break;
            case 'f':
                config->conffile = optarg;
                break;
            case 'P':
                config->pidfile = optarg;
                break;
            case 'v':
                printf("Skeeter\n");
                exit(0);
                break;
            default:
                return 1;
        }
    }
    if (optind < argc) {
        return 1;
    }
    return 0;
}

variable_types: argc int

variable_types:
argv
char **

variable_types: struct config { int debug; int loglevel; char *conffile; struct avlnode { void *avl_data; struct avlnode *avl_link[2]; char avl_bits[2]; char avl_bf; } *modules; } *

variable_types: opt int

user_defined_types: struct config { int debug; int loglevel; char *conffile; struct avlnode *modules; }


decompiled_code:
_BOOL8 init_ssl()
{
if ( ssl_initialized )
return 0LL;
ssl_initialized = 1;
OPENSSL_init_ssl(2097154LL, 0LL);
OPENSSL_init_ssl(0LL, 0LL);
return (unsigned int)RAND_poll() == 0;
}

canonical_decompiled_code:
_BOOL8 func0()
{
if ( ssl_initialized )
return 0LL;
ssl_initialized = 1;
OPENSSL_init_ssl(2097154LL, 0LL);
OPENSSL_init_ssl(0LL, 0LL);
return (unsigned int)RAND_poll() == 0;
}

original_code:
int
init_ssl(void)
{
    if (ssl_initialized)
        return 0;
    ssl_initialized = 1;
    OPENSSL_init_ssl(0x00200000L | 0x00000002L, ((void *)0));
    OPENSSL_init_ssl(0, ((void *)0));
    if (!RAND_poll())
        return 1;
    return 0;
}

canonical_original_code:
int init_ssl()
{
    if (ssl_initialized)
        return 0;
    ssl_initialized = 1;
    OPENSSL_init_ssl(0x00200000L | 0x00000002L, ((void *)0));
    OPENSSL_init_ssl(0, ((void *)0));
    if (!RAND_poll())
        return 1;
    return 0;
}


main

canonical_name: main

repo: mit-athena/reactivate

decompiled_code:
int __cdecl __noreturn main(int argc, const char **argv, const char **envp)
{
__uid_t v3; // eax
struct passwd *v4; // rax
struct passwd *v5; // rbx

if ( argc > 1 )
{
v3 = getuid();
v4 = getpwuid(v3);
v5 = v4;
if ( v4 )
{
if ( initgroups(v4->pw_name, v4->pw_gid) != -1 )
{
if ( !setgid(v5->pw_gid) )
{
if ( setuid(v5->pw_uid) )
{
perror("setuid() failed");
exit(1);
}
execvp(argv[1], (char *const *)argv + 1);
perror("execvp() failed");
exit(1);
}
perror("setgid() failed");
exit(1);
}
perror("initgroups() failed");
exit(1);
}
perror("getpwuid() failed");
exit(1);
}
fprintf(stderr, "Usage: %s command-to-wrap [args]\n", *argv);
exit(255);
}

original_code:
int main (int argc, char **argv) {
  struct passwd *pw;
  if (argc < 2) {
    fprintf(stderr, "Usage: %s command-to-wrap [args]\n", argv[0]);
    exit(255);
  }
  pw = getpwuid(getuid());
  if (pw == ((void *)0)) {
    perror("getpwuid() failed");
    exit(1);
  }
  if (initgroups(pw->pw_name, pw->pw_gid) == -1) {
    perror("initgroups() failed");
    exit(1);
  }
  if (setgid(pw->pw_gid)) {
    perror("setgid() failed");
    exit(1);
  }
  if (setuid(pw->pw_uid)) {
    perror("setuid() failed");
    exit(1);
  }
  execvp(argv[1], &argv[1]);
  perror("execvp() failed");
  exit(1);
}

canonical_original_code:
int main(int argc, char **argv) {
  struct passwd *pw;
  if (argc < 2) {
    fprintf(stderr, "Usage: %s command-to-wrap [args]\n", argv[0]);
    exit(255);
  }
  pw = getpwuid(getuid());
  if (pw == ((void *)0)) {
    perror("getpwuid() failed");
    exit(1);
  }
  if (initgroups(pw->pw_name, pw->pw_gid) == -1) {
    perror("initgroups() failed");
    exit(1);
  }
  if (setgid(pw->pw_gid)) {
    perror("setgid() failed");
    exit(1);
  }
  if (setuid(pw->pw_uid)) {
    perror("setuid() failed");
    exit(1);
  }
  execvp(argv[1], &argv[1]);
  perror("execvp() failed");
  exit(1);
}

variable_types: struct passwd { char *pw_name; char *pw_passwd; unsigned int pw_uid; unsigned int pw_gid; char *pw_gecos; char *pw_dir; char *pw_shell; } *


decompiled_code:
void __noreturn sig_cstack()
{
longjmp(jmp_env, 1);
}

canonical_decompiled_code:
void __noreturn func0()
{
longjmp(jmp_env, 1);
}

original_code:
static void
sig_cstack(int flag, siginfo_t* siginfo, void* ptr) {
    longjmp(jmp_env, 1);
}

canonical_original_code:
static void sig_cstack(int flag, struct siginfo_t *siginfo, void *ptr) {
    longjmp(jmp_env, 1);
}

variable_types: flag int

variable_types: struct siginfo_t { int si_signo; int si_errno; int si_code; int __pad0; union { int _pad[-1]; struct { int si_pid; unsigned int si_uid; } _kill; struct { int si_tid; int si_overrun; union sigval { int sival_int; void *sival_ptr; } si_sigval; } _timer; struct { int si_pid; unsigned int si_uid; union sigval si_sigval; } _rt; struct { int si_pid; unsigned int si_uid; int si_status; long si_utime; long si_stime; } _sigchld; struct { void *si_addr; short si_addr_lsb; union { struct { void *_lower; void *_upper; } _addr_bnd; unsigned int _pkey; } _bounds; } _sigfault; struct { long si_band; int si_fd; } _sigpoll; struct { void *_call_addr; int _syscall; unsigned int _arch; } _sigsys; } _sifields; } *

variable_types:
ptr
void *

user_defined_types: struct siginfo_t { int si_signo; int si_errno; int si_code; int __pad0; union { int _pad[-1]; struct { int si_pid; unsigned int si_uid; } _kill; struct { int si_tid; int si_overrun; union sigval si_sigval; } _timer; struct { int si_pid; unsigned int si_uid; union sigval si_sigval; } _rt; struct { int si_pid; unsigned int si_uid; int si_status; long si_utime; long si_stime; } _sigchld; struct { void *si_addr; short si_addr_lsb; union { struct { void *_lower; void *_upper; } _addr_bnd; unsigned int _pkey; } _bounds; } _sigfault; struct { long si_band; int si_fd; } _sigpoll; struct { void *_call_addr; int _syscall; unsigned int _arch; } _sigsys; } _sifields; }


decompiled_code:
void __noreturn sig_cstack_running_handler()
{
if ( dword_9B0[62 * Current_coroutine] )
longjmp((struct __jmp_buf_tag *)((char *)&xmmword_9B8 + 248 * Current_coroutine), 1);
fprintf(stderr, "Overflow handler is not installed, at %d.\n", Current_coroutine);
exit(1);
}

canonical_decompiled_code:
void __noreturn func1()
{
if ( dword_9B0[62 * Current_coroutine] )
longjmp((struct __jmp_buf_tag *)((char *)&xmmword_9B8 + 248 * Current_coroutine), 1);
fprintf(stderr, "Overflow handler is not installed, at %d.\n", Current_coroutine);
exit(1);
}

original_code:
static void
sig_cstack_running_handler(int flag, siginfo_t* siginfo, void* ptr) {
    if (CStack.stack_slot[Current_coroutine].jmp_buff_enable) {
 longjmp(CStack.stack_slot[Current_coroutine].jmp_buff, 1);
    }
    fprintf(stderr, "Overflow handler is not installed, at %d.\n", Current_coroutine);
    exit(1);
}

canonical_original_code:
static void sig_cstack_running_handler(int flag, struct siginfo_t *siginfo, void *ptr) {
    if (CStack.stack_slot[Current_coroutine].jmp_buff_enable) {
 longjmp(CStack.stack_slot[Current_coroutine].jmp_buff, 1);
    }
    fprintf(stderr, "Overflow handler is not installed, at %d.\n", Current_coroutine);
    exit(1);
}

user_defined_types: union sigval { int sival_int; void *sival_ptr; }


original_code:
static int
alloc_slot(int slot) {
    volatile int i;
    volatile long int *stack_frame;
    stack_frame = __builtin_alloca ((32*1024) * sizeof(long int));
    if (0 == _setjmp (jmp_env)) {
 for (i = ((32*1024) - 1) ; i >= 0 ; i--) {
     stack_frame[i] = 0;
 }
    } else {
 return slot;
    }
    CStack.stack_slot[slot].state = (0);
    CStack.stack_slot[slot].start_addr = (long int*)stack_frame;
    CStack.stack_slot[slot].end_addr = (long int*)
 ((void*)stack_frame + ((32*1024) * sizeof(long int)));
    if ((long int)(((void*)stack_frame + (1024))) & (0x0fff)) {
 CStack.stack_slot[slot].barrier_addr = (long int*)
     (((long int)((void*)stack_frame
     + (1024) + (0x1000))) & ~(0x0fff));
    } else {
 CStack.stack_slot[slot].barrier_addr = (long int*)
     ((void*)(stack_frame) + (1024));
    }
    CStack.stack_slot[slot].safe_addr = (long int*)
 ((void*)(CStack.stack_slot[slot].barrier_addr) + (0x1000));
    mprotect((void*)CStack.stack_slot[slot].barrier_addr, (0x1000), 0x1);
    GC_add_roots((void*)CStack.stack_slot[slot].safe_addr,
   (void*)CStack.stack_slot[slot].end_addr);
    slot ++;
    if (slot > (64)) return (slot-1);
    return alloc_slot(slot);
}

canonical_original_code:
static int alloc_slot(int slot) {
    int i;
    long *stack_frame;
    stack_frame = __builtin_alloca ((32*1024) * sizeof(long));
    if (0 == _setjmp (jmp_env)) {
 for (i = ((32*1024) - 1) ; i >= 0 ; i--) {
     stack_frame[i] = 0;
 }
    } else {
 return slot;
    }
    CStack.stack_slot[slot].state = (0);
    CStack.stack_slot[slot].start_addr = (long *)stack_frame;
    CStack.stack_slot[slot].end_addr = (long *)
 ((void *)stack_frame + ((32*1024) * sizeof(long)));
    if ((long)(((void *)stack_frame + (1024))) & (0x0fff)) {
 CStack.stack_slot[slot].barrier_addr = (long *)
     (((long)((void *)stack_frame
     + (1024) + (0x1000))) & ~(0x0fff));
    } else {
 CStack.stack_slot[slot].barrier_addr = (long *)
     ((void *)(stack_frame) + (1024));
    }
    CStack.stack_slot[slot].safe_addr = (long *)
 ((void *)(CStack.stack_slot[slot].barrier_addr) + (0x1000));
    mprotect((void *)CStack.stack_slot[slot].barrier_addr, (0x1000), 0x1);
    GC_add_roots((void *)CStack.stack_slot[slot].safe_addr,
   (void *)CStack.stack_slot[slot].end_addr);
    slot ++;
    if (slot > (64)) return (slot-1);
    return alloc_slot(slot);
}

variable_types: slot int

variable_types: i int


decompiled_code:
int init_cstack()
{
char *v0; // rdx
unsigned __int64 v1; // rdi
int v2; // ecx
int result; // eax
struct sigaltstack v4; // [rsp+0h] [rbp-168h] BYREF
struct sigaction v5; // [rsp+20h] [rbp-148h] BYREF
struct sigaction v6; // [rsp+C0h] [rbp-A8h] BYREF

v0 = (char *)&xmmword_9B8;
dword_984 = 0x40000;
do
{
v1 = (unsigned __int64)(v0 + 8);
v2 = (int)v0;
*((_DWORD *)v0 - 12) = -1;
v0 += 248;
*((_QWORD *)v0 - 36) = 0LL;
*((_QWORD *)v0 - 35) = 0LL;
*((_QWORD *)v0 - 34) = 0LL;
*((_QWORD *)v0 - 33) = 0LL;
*((_DWORD *)v0 - 64) = 0;
*((_QWORD *)v0 - 31) = 0LL;
*((_QWORD *)v0 - 7) = 0LL;
memset((void *)(v1 & 0xFFFFFFFFFFFFFFF8LL), 0, 8 * ((v2 - (v1 & 0xFFFFFFF8) + 200) >> 3));
}
while ( v0 != "Can't alloc altinative stack(1).\n" );
v4.ss_sp = (void *)GC_malloc(4096LL);
if ( !v4.ss_sp )
{
fwrite("Can't alloc altinative stack(1).\n", 1uLL, 0x21uLL, stderr);
exit(1);
}
v4.ss_size = 4096LL;
v4.ss_flags = 0;
if ( sigaltstack(&v4, 0LL) == -1 )
{
fwrite("Can't set altinative stack(1).\n", 1uLL, 0x1FuLL, stderr);
exit(1);
}
if ( sigaction(11, 0LL, &v6) == -1 )
{
fwrite("Can't save sigaction(1).\n", 1uLL, 0x19uLL, stderr);
exit(1);
}
sigemptyset(&v5.sa_mask);
sigaddset(&v5.sa_mask, 11);
v5.sa_handler = (__sighandler_t)sig_cstack;
v5.sa_flags = 402653188;
if ( sigaction(11, &v5, 0LL) == -1 )
{
fwrite("Can't set sigaction(1).\n", 1uLL, 0x18uLL, stderr);
exit(1);
}
CStack[0] = alloc_slot(0);
if ( sigaction(11, &v6, 0LL) == -1 )
{
fwrite("Can't restore sigaction.\n", 1uLL, 0x19uLL, stderr);
exit(1);
}
dword_988 = 1;
Current_coroutine = 0;
v4.ss_sp = (void *)GC_malloc(4096LL);
if ( !v4.ss_sp )
{
fwrite("Can't alloc altinative stack(2).\n", 1uLL, 0x21uLL, stderr);
exit(1);
}
v4.ss_size = 4096LL;
v4.ss_flags = 0;
if ( sigaltstack(&v4, 0LL) == -1 )
{
fwrite("Can't set altinative stack(2).\n", 1uLL, 0x1FuLL, stderr);
exit(1);
}
if ( sigaction(11, 0LL, &v6) == -1 )
{
fwrite("Can't save sigaction(2).\n", 1uLL, 0x19uLL, stderr);
exit(1);
}
sigemptyset(&v5.sa_mask);
sigaddset(&v5.sa_mask, 11);
v5.sa_handler = (__sighandler_t)sig_cstack_running_handler;
v5.sa_flags = 402653188;
result = sigaction(11, &v5, 0LL);
if ( result == -1 )
{
fwrite("Can't set sigaction(2).\n", 1uLL, 0x18uLL, stderr);
exit(1);
}
return result;
}

canonical_decompiled_code:
int func3()
{
char *v0; // rdx
unsigned __int64 v1; // rdi
int v2; // ecx
int result; // eax
struct sigaltstack v4; // [rsp+0h] [rbp-168h] BYREF
struct sigaction v5; // [rsp+20h] [rbp-148h] BYREF
struct sigaction v6; // [rsp+C0h] [rbp-A8h] BYREF

v0 = (char *)&xmmword_9B8;
dword_984 = 0x40000;
do
{
v1 = (unsigned __int64)(v0 + 8);
v2 = (int)v0;
*((_DWORD *)v0 - 12) = -1;
v0 += 248;
*((_QWORD *)v0 - 36) = 0LL;
*((_QWORD *)v0 - 35) = 0LL;
*((_QWORD *)v0 - 34) = 0LL;
*((_QWORD *)v0 - 33) = 0LL;
*((_DWORD *)v0 - 64) = 0;
*((_QWORD *)v0 - 31) = 0LL;
*((_QWORD *)v0 - 7) = 0LL;
memset((void *)(v1 & 0xFFFFFFFFFFFFFFF8LL), 0, 8 * ((v2 - (v1 & 0xFFFFFFF8) + 200) >> 3));
}
while ( v0 != "Can't alloc altinative stack(1).\n" );
v4.ss_sp = (void *)GC_malloc(4096LL);
if ( !v4.ss_sp )
{
fwrite("Can't alloc altinative stack(1).\n", 1uLL, 0x21uLL, stderr);
exit(1);
}
v4.ss_size = 4096LL;
v4.ss_flags = 0;
if ( sigaltstack(&v4, 0LL) == -1 )
{
fwrite("Can't set altinative stack(1).\n", 1uLL, 0x1FuLL, stderr);
exit(1);
}
if ( sigaction(11, 0LL, &v6) == -1 )
{
fwrite("Can't save sigaction(1).\n", 1uLL, 0x19uLL, stderr);
exit(1);
}
sigemptyset(&v5.sa_mask);
sigaddset(&v5.sa_mask, 11);
v5.sa_handler = (__sighandler_t)sig_cstack;
v5.sa_flags = 402653188;
if ( sigaction(11, &v5, 0LL) == -1 )
{
fwrite("Can't set sigaction(1).\n", 1uLL, 0x18uLL, stderr);
exit(1);
}
CStack[0] = func2(0);
if ( sigaction(11, &v6, 0LL) == -1 )
{
fwrite("Can't restore sigaction.\n", 1uLL, 0x19uLL, stderr);
exit(1);
}
dword_988 = 1;
Current_coroutine = 0;
v4.ss_sp = (void *)GC_malloc(4096LL);
if ( !v4.ss_sp )
{
fwrite("Can't alloc altinative stack(2).\n", 1uLL, 0x21uLL, stderr);
exit(1);
}
v4.ss_size = 4096LL;
v4.ss_flags = 0;
if ( sigaltstack(&v4, 0LL) == -1 )
{
fwrite("Can't set altinative stack(2).\n", 1uLL, 0x1FuLL, stderr);
exit(1);
}
if ( sigaction(11, 0LL, &v6) == -1 )
{
fwrite("Can't save sigaction(2).\n", 1uLL, 0x19uLL, stderr);
exit(1);
}
sigemptyset(&v5.sa_mask);
sigaddset(&v5.sa_mask, 11);
v5.sa_handler = (__sighandler_t)sig_cstack_running_handler;
v5.sa_flags = 402653188;
result = sigaction(11, &v5, 0LL);
if ( result == -1 )
{
fwrite("Can't set sigaction(2).\n", 1uLL, 0x18uLL, stderr);
exit(1);
}
return result;
}

original_code:
void
init_cstack() {
    int i, fin;
    stack_t ss;
    struct sigaction newsig, oldsig;
    CStack.slot_size = (32*1024) * sizeof(long int);
    for (i = 0 ; i < (64) ; i++) {
 CStack.stack_slot[i].state = (-1);
 CStack.stack_slot[i].start_addr = 0;
 CStack.stack_slot[i].barrier_addr = 0;
 CStack.stack_slot[i].safe_addr = 0;
 CStack.stack_slot[i].end_addr = 0;
 CStack.stack_slot[i].jmp_buff_enable = 0;
 memset(CStack.stack_slot[i].jmp_buff, 0, sizeof(jmp_buf));
    }
    ss.ss_sp = GC_malloc((4*1024));
    if (((void *)0) == ss.ss_sp) {
 fprintf(stderr, "Can't alloc altinative stack(1).\n");
 exit(1);
    }
    ss.ss_size = (4*1024);
    ss.ss_flags = 0;
    if (-1 == sigaltstack(&ss, ((void *)0))) {
 fprintf(stderr, "Can't set altinative stack(1).\n");
 exit(1);
    }
    if (-1 == sigaction(11, ((void *)0), &oldsig)) {
 fprintf(stderr, "Can't save sigaction(1).\n");
 exit(1);
    }
    sigemptyset(&newsig.sa_mask);
    sigaddset(&newsig.sa_mask, 11);
    newsig.__sigaction_handler.sa_sigaction = sig_cstack;
    newsig.sa_flags = 4 | 0x10000000 | 0x08000000;
    if (-1 == sigaction(11, &newsig, ((void *)0))) {
 fprintf(stderr, "Can't set sigaction(1).\n");
 exit(1);
    }
    fin = alloc_slot(0);
    CStack.number_of_slot = fin;
    if (-1 == sigaction(11, &oldsig, ((void *)0))) {
 fprintf(stderr, "Can't restore sigaction.\n");
 exit(1);
    }
    CStack.stack_slot[0].state = (1);
    Current_coroutine = 0;
    ss.ss_sp = GC_malloc((4*1024));
    if (((void *)0) == ss.ss_sp) {
 fprintf(stderr, "Can't alloc altinative stack(2).\n");
 exit(1);
    }
    ss.ss_size = (4*1024);
    ss.ss_flags = 0;
    if (-1 == sigaltstack(&ss, ((void *)0))) {
 fprintf(stderr, "Can't set altinative stack(2).\n");
 exit(1);
    }
    if (-1 == sigaction(11, ((void *)0), &oldsig)) {
 fprintf(stderr, "Can't save sigaction(2).\n");
 exit(1);
    }
    sigemptyset(&newsig.sa_mask);
    sigaddset(&newsig.sa_mask, 11);
    newsig.__sigaction_handler.sa_sigaction = sig_cstack_running_handler;
    newsig.sa_flags = 4 | 0x10000000 | 0x08000000;
    if (-1 == sigaction(11, &newsig, ((void *)0))) {
 fprintf(stderr, "Can't set sigaction(2).\n");
 exit(1);
    }
}

canonical_original_code:
void init_cstack() {
    int i; int fin;
    struct stack_t ss;
    struct sigaction newsig; struct sigaction oldsig;
    CStack.slot_size = (32*1024) * sizeof(long);
    for (i = 0 ; i < (64) ; i++) {
 CStack.stack_slot[i].state = (-1);
 CStack.stack_slot[i].start_addr = 0;
 CStack.stack_slot[i].barrier_addr = 0;
 CStack.stack_slot[i].safe_addr = 0;
 CStack.stack_slot[i].end_addr = 0;
 CStack.stack_slot[i].jmp_buff_enable = 0;
 memset(CStack.stack_slot[i].jmp_buff, 0, sizeof(jmp_buf));
    }
    ss.ss_sp = GC_malloc((4*1024));
    if (((void *)0) == ss.ss_sp) {
 fprintf(stderr, "Can't alloc altinative stack(1).\n");
 exit(1);
    }
    ss.ss_size = (4*1024);
    ss.ss_flags = 0;
    if (-1 == sigaltstack(&ss, ((void *)0))) {
 fprintf(stderr, "Can't set altinative stack(1).\n");
 exit(1);
    }
    if (-1 == sigaction(11, ((void *)0), &oldsig)) {
 fprintf(stderr, "Can't save sigaction(1).\n");
 exit(1);
    }
    sigemptyset(&newsig.sa_mask);
    sigaddset(&newsig.sa_mask, 11);
    newsig.__sigaction_handler.sa_sigaction = sig_cstack;
    newsig.sa_flags = 4 | 0x10000000 | 0x08000000;
    if (-1 == sigaction(11, &newsig, ((void *)0))) {
 fprintf(stderr, "Can't set sigaction(1).\n");
 exit(1);
    }
    fin = alloc_slot(0);
    CStack.number_of_slot = fin;
    if (-1 == sigaction(11, &oldsig, ((void *)0))) {
 fprintf(stderr, "Can't restore sigaction.\n");
 exit(1);
    }
    CStack.stack_slot[0].state = (1);
    Current_coroutine = 0;
    ss.ss_sp = GC_malloc((4*1024));
    if (((void *)0) == ss.ss_sp) {
 fprintf(stderr, "Can't alloc altinative stack(2).\n");
 exit(1);
    }
    ss.ss_size = (4*1024);
    ss.ss_flags = 0;
    if (-1 == sigaltstack(&ss, ((void *)0))) {
 fprintf(stderr, "Can't set altinative stack(2).\n");
 exit(1);
    }
    if (-1 == sigaction(11, ((void *)0), &oldsig)) {
 fprintf(stderr, "Can't save sigaction(2).\n");
 exit(1);
    }
    sigemptyset(&newsig.sa_mask);
    sigaddset(&newsig.sa_mask, 11);
    newsig.__sigaction_handler.sa_sigaction = sig_cstack_running_handler;
    newsig.sa_flags = 4 | 0x10000000 | 0x08000000;
    if (-1 == sigaction(11, &newsig, ((void *)0))) {
 fprintf(stderr, "Can't set sigaction(2).\n");
 exit(1);
    }
}

variable_types: fin int

variable_types: struct stack_t { void *ss_sp; int ss_flags; unsigned long ss_size; }

variable_types: struct sigaction { union { void (*sa_handler)(int); void (*sa_sigaction)(int, struct siginfo_t { int si_signo; int si_errno; int si_code; int __pad0; union { int _pad[-1]; struct { int si_pid; unsigned int si_uid; } _kill; struct { int si_tid; int si_overrun; union sigval { int sival_int; void *sival_ptr; } si_sigval; } _timer; struct { int si_pid; unsigned int si_uid; union sigval si_sigval; } _rt; struct { int si_pid; unsigned int si_uid; int si_status; long si_utime; long si_stime; } _sigchld; struct { void *si_addr; short si_addr_lsb; union { struct { void *_lower; void *_upper; } _addr_bnd; unsigned int _pkey; } _bounds; } _sigfault; struct { long si_band; int si_fd; } _sigpoll; struct { void *_call_addr; int _syscall; unsigned int _arch; } _sigsys; } _sifields; } *, void *); } __sigaction_handler; struct __sigset_t { unsigned long __val[-1]; } sa_mask; int sa_flags; void (*sa_restorer)(); }

user_defined_types: struct sigaction { union { void (*sa_handler)(int); void (*sa_sigaction)(int, struct siginfo_t *, void *); } __sigaction_handler; struct __sigset_t sa_mask; int sa_flags; void (*sa_restorer)(); }


decompiled_code:
__int64 cstack_get()
{
int *v0; // rax
unsigned int v1; // er12
int *v2; // rax
void *v3; // rdi
__int64 v4; // rdx

if ( CStack[0] <= 0 )
return 0xFFFFFFFFLL;
v0 = &dword_988;
v1 = 0;
while ( *v0 )
{
++v1;
v0 += 62;
if ( v1 == CStack[0] )
return 0xFFFFFFFFLL;
}
v2 = &CStack[62 * v1];
v3 = (void *)*((_QWORD *)v2 + 4);
v4 = *((_QWORD *)v2 + 5);
v2[2] = 1;
memset(v3, 0, (v4 - (__int64)v3) >> 3);
return v1;
}

canonical_decompiled_code:
__int64 func4()
{
int *v0; // rax
unsigned int v1; // er12
int *v2; // rax
void *v3; // rdi
__int64 v4; // rdx

if ( CStack[0] <= 0 )
return 0xFFFFFFFFLL;
v0 = &dword_988;
v1 = 0;
while ( *v0 )
{
++v1;
v0 += 62;
if ( v1 == CStack[0] )
return 0xFFFFFFFFLL;
}
v2 = &CStack[62 * v1];
v3 = (void *)*((_QWORD *)v2 + 4);
v4 = *((_QWORD *)v2 + 5);
v2[2] = 1;
memset(v3, 0, (v4 - (__int64)v3) >> 3);
return v1;
}

original_code:
int
cstack_get() {
    int i;
    for (i = 0 ; i < CStack.number_of_slot ; i++) {
 if ((0) == CStack.stack_slot[i].state) {
     CStack.stack_slot[i].state = (1);
     memset((void*)CStack.stack_slot[i].safe_addr, 0,
     CStack.stack_slot[i].end_addr - CStack.stack_slot[i].safe_addr);
     return i;
 }
    }
    return -1;
}

canonical_original_code:
int cstack_get() {
    int i;
    for (i = 0 ; i < CStack.number_of_slot ; i++) {
 if ((0) == CStack.stack_slot[i].state) {
     CStack.stack_slot[i].state = (1);
     memset((void *)CStack.stack_slot[i].safe_addr, 0,
     CStack.stack_slot[i].end_addr - CStack.stack_slot[i].safe_addr);
     return i;
 }
    }
    return -1;
}


decompiled_code:
int *__fastcall cstack_release(int a1)
{
int *result; // rax

if ( CStack[0] > a1 && a1 > 0 )
{
result = &CStack[62 * a1];
result[2] = 0;
result[12] = 0;
}
return result;
}

canonical_decompiled_code:
int *__fastcall func5(int a1)
{
int *result; // rax

if ( CStack[0] > a1 && a1 > 0 )
{
result = &CStack[62 * a1];
result[2] = 0;
result[12] = 0;
}
return result;
}

original_code:
void
cstack_release(int slot_id) {
    if ((slot_id >= CStack.number_of_slot) ||
 (slot_id < 1)) {
 return;
    }
    CStack.stack_slot[slot_id].state = (0);
    CStack.stack_slot[slot_id].jmp_buff_enable = 0;
}


decompiled_code:
__int64 cstack_list()
{
__int64 v0; // r14
__int64 v1; // rax
__int64 v2; // r13
int *v3; // rbx
int v4; // er12
const char *v5; // rdi
__int64 v6; // rax
__int64 v7; // rax
__int64 v8; // rax
__int64 v9; // rax
__int64 v10; // rax
__int64 v11; // rax
__int64 v12; // rbp

v0 = new_list(0LL);
v1 = new_integer_si((unsigned int)CStack[0]);
list_append(v0, v1);
v2 = new_list(0LL);
if ( CStack[0] > 0 )
{
v3 = &dword_988;
v4 = 0;
while ( 1 )
{
v12 = new_list(0LL);
if ( !*v3 )
break;
if ( *v3 == 1 )
{
v5 = "USE";
LABEL_5:
v6 = new_symbol(v5);
list_append(v12, v6);
v7 = new_integer_si((unsigned int)v3[2]);
list_append(v12, v7);
v8 = new_integer_si((unsigned int)v3[4]);
list_append(v12, v8);
v9 = new_integer_si((unsigned int)v3[6]);
list_append(v12, v9);
v10 = new_integer_si((unsigned int)v3[8]);
list_append(v12, v10);
v11 = new_integer_si((unsigned int)v3[10]);
list_append(v12, v11);
}
++v4;
v3 += 62;
list_append(v2, v12);
if ( CStack[0] <= v4 )
goto LABEL_9;
}
v5 = "FREE";
goto LABEL_5;
}
LABEL_9:
list_append(v0, v2);
return v0;
}

canonical_decompiled_code:
__int64 func6()
{
__int64 v0; // r14
__int64 v1; // rax
__int64 v2; // r13
int *v3; // rbx
int v4; // er12
const char *v5; // rdi
__int64 v6; // rax
__int64 v7; // rax
__int64 v8; // rax
__int64 v9; // rax
__int64 v10; // rax
__int64 v11; // rax
__int64 v12; // rbp

v0 = new_list(0LL);
v1 = new_integer_si((unsigned int)CStack[0]);
list_append(v0, v1);
v2 = new_list(0LL);
if ( CStack[0] > 0 )
{
v3 = &dword_988;
v4 = 0;
while ( 1 )
{
v12 = new_list(0LL);
if ( !*v3 )
break;
if ( *v3 == 1 )
{
v5 = "USE";
LABEL_5:
v6 = new_symbol(v5);
list_append(v12, v6);
v7 = new_integer_si((unsigned int)v3[2]);
list_append(v12, v7);
v8 = new_integer_si((unsigned int)v3[4]);
list_append(v12, v8);
v9 = new_integer_si((unsigned int)v3[6]);
list_append(v12, v9);
v10 = new_integer_si((unsigned int)v3[8]);
list_append(v12, v10);
v11 = new_integer_si((unsigned int)v3[10]);
list_append(v12, v11);
}
++v4;
v3 += 62;
list_append(v2, v12);
if ( CStack[0] <= v4 )
goto LABEL_9;
}
v5 = "FREE";
goto LABEL_5;
}
LABEL_9:
list_append(v0, v2);
return v0;
}

original_code:
Toy_Type*
cstack_list() {
    int i;
    Toy_Type *result, *slist, *elist;
    result = new_list(((void *)0));
    list_append(result, new_integer_si(CStack.number_of_slot));
    slist = new_list(((void *)0));
    for (i = 0 ; i < CStack.number_of_slot ; i++) {
 elist = new_list(((void *)0));
 switch (CStack.stack_slot[i].state) {
 case (0):
     list_append(elist, new_symbol("FREE"));
     list_append(elist,
   new_integer_si((long int)
           (long int)
           CStack.stack_slot[i].start_addr));
     list_append(elist,
   new_integer_si((long int)
           (long int)
           CStack.stack_slot[i].barrier_addr));
     list_append(elist,
   new_integer_si((long int)
           (long int)
           CStack.stack_slot[i].safe_addr));
     list_append(elist,
   new_integer_si((long int)
           (long int)
           CStack.stack_slot[i].end_addr));
     list_append(elist,
   new_integer_si((long int)
           (long int)
           CStack.stack_slot[i].jmp_buff_enable));
     break;
 case (1):
     list_append(elist, new_symbol("USE"));
     list_append(elist,
   new_integer_si((long int)
           (long int)
           CStack.stack_slot[i].start_addr));
     list_append(elist,
   new_integer_si((long int)
           (long int)
           CStack.stack_slot[i].barrier_addr));
     list_append(elist,
   new_integer_si((long int)
           (long int)
           CStack.stack_slot[i].safe_addr));
     list_append(elist,
   new_integer_si((long int)
           (long int)
           CStack.stack_slot[i].end_addr));
     list_append(elist,
   new_integer_si((long int)
           (long int)
           CStack.stack_slot[i].jmp_buff_enable));
     break;
 }
 list_append(slist, elist);
    }
    list_append(result, slist);
    return result;
}

canonical_original_code:
struct _toy_type *cstack_list() {
    int i;
    struct _toy_type *result; struct _toy_type *slist; struct _toy_type *elist;
    result = new_list(((void *)0));
    list_append(result, new_integer_si(CStack.number_of_slot));
    slist = new_list(((void *)0));
    for (i = 0 ; i < CStack.number_of_slot ; i++) {
 elist = new_list(((void *)0));
 switch (CStack.stack_slot[i].state) {
 case (0):
     list_append(elist, new_symbol("FREE"));
     list_append(elist,
   new_integer_si((long)
           (long)
           CStack.stack_slot[i].start_addr));
     list_append(elist,
   new_integer_si((long)
           (long)
           CStack.stack_slot[i].barrier_addr));
     list_append(elist,
   new_integer_si((long)
           (long)
           CStack.stack_slot[i].safe_addr));
     list_append(elist,
   new_integer_si((long)
           (long)
           CStack.stack_slot[i].end_addr));
     list_append(elist,
   new_integer_si((long)
           (long)
           CStack.stack_slot[i].jmp_buff_enable));
     break;
 case (1):
     list_append(elist, new_symbol("USE"));
     list_append(elist,
   new_integer_si((long)
           (long)
           CStack.stack_slot[i].start_addr));
     list_append(elist,
   new_integer_si((long)
           (long)
           CStack.stack_slot[i].barrier_addr));
     list_append(elist,
   new_integer_si((long)
           (long)
           CStack.stack_slot[i].safe_addr));
     list_append(elist,
   new_integer_si((long)
           (long)
           CStack.stack_slot[i].end_addr));
     list_append(elist,
   new_integer_si((long)
           (long)
           CStack.stack_slot[i].jmp_buff_enable));
     break;
 }
 list_append(slist, elist);
    }
    list_append(result, slist);
    return result;
}

variable_types: struct _toy_type { unsigned int tag; union _u { struct _symbol { struct _cell { int length; int allocsize; char *data; } *cell; unsigned int hash_index; } symbol; struct _ref { struct _cell *cell; unsigned int hash_index; } ref; struct _list { struct _toy_type *item; struct _toy_type *nextp; } list; struct __mpz_struct { int _mp_alloc; int _mp_size; unsigned long *_mp_d; } biginteger[1]; double real; struct _cell *string; struct _toy_type *statement_list; struct _statement { struct _toy_type *item_list; struct _toy_func_trace_info { int line; struct _toy_type *object_name; struct _toy_type *func_name; struct _toy_type *statement; } *trace_info; } statement; struct _toy_type *block_body; struct _toy_type *eval_body; struct _native { struct _toy_type *(*cfunc)(struct _toy_interp { char *name; int stack_size; int cur_func_stack; struct _toy_func_env { struct _hash { int bucket_size; struct hash_bucket { char *key; unsigned int index; struct _toy_type *item; struct hash_bucket *next; } **bucket; int items; int synonyms; } *localvar; struct _toy_func_env *upstack; struct _toy_type *tobe_bind_val; struct _toy_func_trace_info *trace_info; int script_id; } **func_stack; int cur_obj_stack; struct _toy_obj_env { struct _hash *cur_object_slot; struct _toy_type *cur_object; struct _toy_type *self; } **obj_stack; struct _hash *funcs; struct _hash *classes; struct _hash *globals; struct _hash *scripts; struct _toy_func_trace_info *trace_info; int script_id; struct _hash *gcache; int cache_hit; int cache_missing; int trace; int trace_fd; int cstack_id; void *cstack; int cstack_size; void *coroid; struct _toy_interp *co_parent; struct _toy_type *co_value; int co_calling; } *interp, struct _toy_type *posargs, struct _hash *namedargs, int arglen); struct _toy_type *argspec_list; } native; struct _object { struct _hash *slots; struct _toy_type *delegate_list; } object; struct _exception { struct _cell *code; struct _toy_type *msg_list; } exception; struct _closure { struct _toy_type *block_body; struct _toy_env { struct _toy_func_env *func_env; struct _toy_obj_env *object_env; struct _toy_type *tobe_bind_val; } *env; } closure; struct _func { struct _toy_argspec { struct _toy_type *list; int posarg_len; struct _array { int alloc_size; int cur_size; struct _toy_type *array; } *posarg_array; struct _hash *namedarg; } *argspec; struct _toy_type *closure; } func; struct _control { unsigned int code; struct _toy_type *ret_value; } control; void *container; struct _getmacro { struct _toy_type *obj; struct _toy_type *para; } getmacro; struct _initmacro { struct _toy_type *class; struct _toy_type *param; } initmacro; struct _alias { struct _hash *slot; struct _toy_type *key; } alias; struct _cell *rquote; struct _toy_type *bind_var; struct _hash *dict; struct _array *vector; struct _toy_coroutine { struct _toy_interp *interp; struct _toy_type *script; int state; void *coro_id; } *coroutine; } u; } *

user_defined_types: struct _toy_type { unsigned int tag; union _u u; }

user_defined_types: union _u { struct _symbol symbol; struct _ref ref; struct _list list; struct __mpz_struct biginteger[1]; double real; struct _cell *string; struct _toy_type *statement_list; struct _statement statement; struct _toy_type *block_body; struct _toy_type *eval_body; struct _native native; struct _object object; struct _exception exception; struct _closure closure; struct _func func; struct _control control; void *container; struct _getmacro getmacro; struct _initmacro initmacro; struct _alias alias; struct _cell *rquote; struct _toy_type *bind_var; struct _hash *dict; struct _array *vector; struct _toy_coroutine *coroutine; }

user_defined_types: struct _symbol { struct _cell *cell; unsigned int hash_index; }

user_defined_types: struct _statement { struct _toy_type *item_list; struct _toy_func_trace_info *trace_info; }

user_defined_types: struct _native { struct _toy_type *(*cfunc)(struct _toy_interp *interp, struct _toy_type *posargs, struct _hash *namedargs, int arglen); struct _toy_type *argspec_list; }

user_defined_types: struct _closure { struct _toy_type *block_body; struct _toy_env *env; }

user_defined_types: struct _func { struct _toy_argspec *argspec; struct _toy_type *closure; }

user_defined_types: struct _toy_argspec { struct _toy_type *list; int posarg_len; struct _array *posarg_array; struct _hash *namedarg; }

user_defined_types: struct _toy_interp { char *name; int stack_size; int cur_func_stack; struct _toy_func_env **func_stack; int cur_obj_stack; struct _toy_obj_env **obj_stack; struct _hash *funcs; struct _hash *classes; struct _hash *globals; struct _hash *scripts; struct _toy_func_trace_info *trace_info; int script_id; struct _hash *gcache; int cache_hit; int cache_missing; int trace; int trace_fd; int cstack_id; void *cstack; int cstack_size; void *coroid; struct _toy_interp *co_parent; struct _toy_type *co_value; int co_calling; }

user_defined_types: struct _toy_func_env { struct _hash *localvar; struct _toy_func_env *upstack; struct _toy_type *tobe_bind_val; struct _toy_func_trace_info *trace_info; int script_id; }

user_defined_types: struct _hash { int bucket_size; struct hash_bucket **bucket; int items; int synonyms; }


decompiled_code:
__int64 __fastcall cstack_get_start_addr(int a1)
{
__int64 result; // rax

if ( CStack[0] <= a1 || a1 < 0 )
result = 0LL;
else
result = qword_990[31 * a1];
return result;
}

canonical_decompiled_code:
__int64 __fastcall func7(int a1)
{
__int64 result; // rax

if ( CStack[0] <= a1 || a1 < 0 )
result = 0LL;
else
result = qword_990[31 * a1];
return result;
}

original_code:
void*
cstack_get_start_addr(int slot_id) {
    if ((slot_id >= CStack.number_of_slot) ||
 (slot_id < 0)) {
 return 0;
    }
    return (void*)CStack.stack_slot[slot_id].start_addr;
}

canonical_original_code:
void *cstack_get_start_addr(int slot_id) {
    if ((slot_id >= CStack.number_of_slot) ||
 (slot_id < 0)) {
 return 0;
    }
    return (void *)CStack.stack_slot[slot_id].start_addr;
}


decompiled_code:
__int64 __fastcall cstack_get_end_addr(int a1)
{
__int64 result; // rax

if ( CStack[0] <= a1 || a1 < 0 )
result = 0LL;
else
result = qword_9A8[31 * a1];
return result;
}

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

if ( CStack[0] <= a1 || a1 < 0 )
result = 0LL;
else
result = qword_9A8[31 * a1];
return result;
}

original_code:
void*
cstack_get_end_addr(int slot_id) {
    if ((slot_id >= CStack.number_of_slot) ||
 (slot_id < 0)) {
 return 0;
    }
    return (void*)CStack.stack_slot[slot_id].end_addr;
}

canonical_original_code:
void *cstack_get_end_addr(int slot_id) {
    if ((slot_id >= CStack.number_of_slot) ||
 (slot_id < 0)) {
 return 0;
    }
    return (void *)CStack.stack_slot[slot_id].end_addr;
}


decompiled_code:
__int64 cstack_get_size()
{
return (unsigned int)dword_984;
}

canonical_decompiled_code:
__int64 func9()
{
return (unsigned int)dword_984;
}

original_code:
int
cstack_get_size() {
    return CStack.slot_size;
}


decompiled_code:
__int64 __fastcall cstack_enter(int a1)
{
__int64 result; // rax

result = (unsigned int)Current_coroutine;
Current_coroutine = a1;
return result;
}

canonical_decompiled_code:
__int64 __fastcall func11(int a1)
{
__int64 result; // rax

result = (unsigned int)Current_coroutine;
Current_coroutine = a1;
return result;
}

original_code:
int
cstack_enter(int new_slot) {
    int old_slot;
    old_slot = Current_coroutine;
    Current_coroutine = new_slot;
    return old_slot;
}


decompiled_code:
void __fastcall cstack_leave(int a1)
{
Current_coroutine = a1;
}

canonical_decompiled_code:
void __fastcall func12(int a1)
{
Current_coroutine = a1;
}

original_code:
void
cstack_leave(int old_slot) {
    Current_coroutine = old_slot;
}


decompiled_code:
int __cdecl main(int argc, const char **argv, const char **envp)
{
const char *v3; // rsi
const char *v4; // rax
unsigned __int8 *v5; // rax
unsigned __int8 *v6; // rbp
int v7; // eax
__int64 v8; // rdi
const char *v9; // rax
__int64 v10; // r12
__int64 v11; // rax
_BYTE *v13; // rax
_BYTE *v14; // rbp
const char *v15; // rax
const char *v16; // r12
const char *v17; // rax
unsigned __int8 *v18; // rax
unsigned __int8 *v19; // rsi
int v20; // eax
const char *v21; // rax
__int64 v22; // rdi
const char *v23; // rax
_BYTE *v24; // rax
_BYTE *v25; // rbp
const char *v26; // rax
const char *v27; // rax
__int64 v28; // rdi
const char *v29; // rax
const char *v30; // rax
__int64 v31; // [rsp+8h] [rbp-1110h]
__int64 v32; // [rsp+10h] [rbp-1108h]
jmp_buf env; // [rsp+30h] [rbp-10E8h] BYREF
char v36; // [rsp+FFh] [rbp-1019h]
char s; // [rsp+100h] [rbp-1018h] BYREF
char v38[4094]; // [rsp+101h] [rbp-1017h] BYREF
char v39; // [rsp+10FFh] [rbp-19h]

while ( 1 )
{
v32 = new_interp("main", 1024LL, 0LL, (unsigned int)argc, argv, envp);
v31 = new_bulk();
if ( !setjmp(env) )
break;
fwrite("Catch the main co-routine stack overflow, to be restarted.\n", 1uLL, 0x3BuLL, stderr);
}
cstack_set_jmpbuff(0LL, env);
v3 = argv[1];
if ( v3 && (*v3 != 45 || v3[1]) )
{
if ( !(unsigned int)bulk_load_file(v31, v3) )
{
fprintf(stderr, "file not open: %s\n", argv[1]);
goto LABEL_6;
}
v18 = (unsigned __int8 *)toy_parse_start(v31);
v19 = v18;
if ( v18 )
{
v20 = *v18;
if ( v20 == 7 )
{
v24 = (_BYTE *)toy_eval_script(v32, v19);
v25 = v24;
if ( v24 && *v24 == 13 )
{
v30 = (const char *)to_string(v24);
fprintf(stdout, "EXCEPTION: %s\n", v30);
}
else
{
v26 = (const char *)toy_get_type_str(v24);
fprintf(stdout, "result[%s]=> ", v26);
v27 = (const char *)to_print(v25);
fprintf(stdout, "%s\n", v27);
}
}
else
{
if ( v20 != 13 )
{
v21 = (const char *)toy_get_type_str(v19);
fprintf(stderr, "parse error: type=%s\n", v21);
goto LABEL_6;
}
v22 = *((_QWORD *)v19 + 2);
if ( v22 )
{
if ( *(_BYTE *)v22 == 3 )
v22 = *(_QWORD *)(v22 + 8);
else
v22 = 0LL;
}
v23 = (const char *)to_string(v22);
fprintf(stderr, "parse error: %s\n", v23);
}
exit(0);
}
fwrite("no memory\n", 1uLL, 0xAuLL, stderr);
LABEL_6:
exit(1);
}
LABEL_8:
while ( !feof(stdin) )
{
fwrite("> ", 1uLL, 2uLL, stderr);
if ( !fgets(&s, 4096, stdin) )
break;
v39 = 0;
if ( s == 33 )
{
*(&v36 + strlen(&s)) = 0;
if ( (unsigned int)bulk_load_file(v31, v38) )
goto LABEL_12;
fprintf(stderr, "file not open: %s\n", v38);
}
else
{
bulk_set_string(v31, &s);
LABEL_12:
v5 = (unsigned __int8 *)toy_parse_start(v31);
v6 = v5;
if ( v5 )
{
v7 = *v5;
if ( v7 == 7 )
{
LABEL_28:
v13 = (_BYTE *)toy_eval_script(v32, v6);
v14 = v13;
if ( v13 && *v13 == 13 )
{
v17 = (const char *)to_string(v13);
fprintf(stdout, "EXCEPTION: %s\n", v17);
}
else
{
v15 = (const char *)toy_get_type_str(v13);
fprintf(stdout, "result[%s]=> ", v15);
v16 = (const char *)to_print(v14);
if ( strlen(v16) <= 0x200 )
fprintf(stdout, "%s\n", v16);
else
fprintf(stdout, "%-.512s ...\n", v16);
}
}
else if ( v7 == 13 )
{
v8 = *((_QWORD *)v6 + 2);
if ( v8 )
{
if ( *(_BYTE *)v8 == 3 )
v8 = *(_QWORD *)(v8 + 8);
else
v8 = 0LL;
}
v9 = (const char *)to_string(v8);
fprintf(stderr, "parse error: %s\n", v9);
if ( (unsigned int)cell_eq_str(*((_QWORD *)v6 + 1), "ErrParseClose") && s != 33 )
{
v10 = new_cell(&s);
while ( 1 )
{
fwrite("=> ", 1uLL, 3uLL, stderr);
if ( !fgets(&s, 4096, stdin) )
return 0;
v39 = 0;
cell_add_str(v10, &s);
bulk_set_string(v31, *(_QWORD *)(v10 + 8));
v11 = toy_parse_start(v31);
v6 = (unsigned __int8 *)v11;
if ( !v11 || *(_BYTE *)v11 != 13 )
goto LABEL_28;
if ( !(unsigned int)cell_eq_str(*(_QWORD *)(v11 + 8), "ErrParseClose") )
{
v28 = *((_QWORD *)v6 + 2);
if ( v28 )
{
if ( *(_BYTE *)v28 == 3 )
v28 = *(_QWORD *)(v28 + 8);
else
v28 = 0LL;
}
v29 = (const char *)to_string(v28);
fprintf(stderr, "parse error: %s\n", v29);
goto LABEL_8;
}
}
}
}
else
{
v4 = (const char *)toy_get_type_str(v6);
fprintf(stderr, "parse error: type=%s\n", v4);
}
}
else
{
fwrite("no memory\n", 1uLL, 0xAuLL, stderr);
}
}
}
return 0;
}

original_code:
int main(int argc, char **argv, char **envp) {
    char buff[(4096)];
    Toy_Type *any, *result;
    Toy_Type *script;
    Toy_Type *err;
    Bulk *b;
    Cell *c;
    Toy_Interp *interp;
    jmp_buf jmp_env;
error_reset:
    interp = new_interp("main", (1024), ((void *)0), argc, argv, envp);
    b = new_bulk();
    if (0 == _setjmp (jmp_env)) {
 cstack_set_jmpbuff(0, &jmp_env);
    } else {
 fprintf(stderr, "Catch the main co-routine stack overflow, to be restarted.\n");
 goto error_reset;
    }
    if (argv[1] && (strcmp(argv[1], "-") != 0)) {
 if (0 == bulk_load_file(b, argv[1])) {
     fprintf(stderr, "file not open: %s\n", argv[1]);
     exit(1);
 }
 any = toy_parse_start(b);
 if (((void *)0) == any) {
     fprintf(stderr, "no memory\n");
     exit(1);
 }
 switch (((any==((void *)0))?-1:((0x000000ff) & (any->tag)))) {
 case 13:
     err = any;
     fprintf(stderr, "parse error: %s\n",
      to_string((((err->u.exception.msg_list)==((void *)0))?((void *)0):(((((err->u.exception.msg_list)==((void *)0))?-1:((0x000000ff) & ((err->u.exception.msg_list)->tag)))==3)?(err->u.exception.msg_list)->u.list.item:((void *)0)))));
     exit(0);
 case 7:
     script = any;
     result = toy_eval_script(interp, script);
     if (((result==((void *)0))?-1:((0x000000ff) & (result->tag))) != 13) {
  fprintf(stdout, "result[%s]=> ", toy_get_type_str(result));
  fprintf(stdout, "%s\n", to_print(result));
     } else {
  fprintf(stdout, "EXCEPTION: %s\n", to_string(result));
     }
     exit(0);
 default:
     fprintf(stderr, "parse error: type=%s\n", toy_get_type_str(any));
     exit(1);
 }
    }
    while (! feof(stdin)) {
 fputs("> ", stderr);
 if (((void *)0) == fgets(buff, (4096), stdin)) break;
 buff[(4096)-1] = 0;
 if (buff[0] == '!') {
     buff[strlen(buff)-1] = 0;
     if (0 == bulk_load_file(b, &buff[1])) {
  fprintf(stderr, "file not open: %s\n", &buff[1]);
  continue;
     }
 } else {
     bulk_set_string(b, buff);
 }
 any = toy_parse_start(b);
 if (((void *)0) == any) {
     fprintf(stderr, "no memory\n");
 } else {
     switch (((any==((void *)0))?-1:((0x000000ff) & (any->tag)))) {
     case 13:
  err = any;
  fprintf(stderr, "parse error: %s\n",
   to_string((((err->u.exception.msg_list)==((void *)0))?((void *)0):(((((err->u.exception.msg_list)==((void *)0))?-1:((0x000000ff) & ((err->u.exception.msg_list)->tag)))==3)?(err->u.exception.msg_list)->u.list.item:((void *)0)))));
  if (cell_eq_str(err->u.exception.code, "ErrParseClose") == 0) break;
  if (buff[0] == '!') break;
  c = new_cell(buff);
  while (1) {
      fputs("=> ", stderr);
      if (((void *)0) == fgets(buff, (4096), stdin)) goto exit_loop;
      buff[(4096)-1] = 0;
      cell_add_str(c, buff);
      bulk_set_string(b, (c->data));
      any = toy_parse_start(b);
      if (((any==((void *)0))?-1:((0x000000ff) & (any->tag))) == 13) {
   err = any;
   if (cell_eq_str(err->u.exception.code, "ErrParseClose") == 0) {
       fprintf(stderr, "parse error: %s\n",
        to_string((((err->u.exception.msg_list)==((void *)0))?((void *)0):(((((err->u.exception.msg_list)==((void *)0))?-1:((0x000000ff) & ((err->u.exception.msg_list)->tag)))==3)?(err->u.exception.msg_list)->u.list.item:((void *)0)))));
       goto next_loop;
   }
      } else {
   break;
      }
  }
     case 7:
  script = any;
  result = toy_eval_script(interp, script);
  if (((result==((void *)0))?-1:((0x000000ff) & (result->tag))) != 13) {
      char *p;
      fprintf(stdout, "result[%s]=> ", toy_get_type_str(result));
      p = to_print(result);
      if (strlen(p) > 512) {
   fprintf(stdout, "%-.512s ...\n", p);
      } else {
   fprintf(stdout, "%s\n", p);
      }
  } else {
      fprintf(stdout, "EXCEPTION: %s\n", to_string(result));
  }
  break;
     default:
  fprintf(stderr, "parse error: type=%s\n", toy_get_type_str(any));
     }
 }
    next_loop:
 0;
    }
exit_loop:
    return 0;
}

canonical_original_code:
int main(int argc, char **argv, char **envp) {
    char buff[-1];
    struct _toy_type *any; struct _toy_type *result;
    struct _toy_type *script;
    struct _toy_type *err;
    struct _bulk *b;
    struct _cell *c;
    struct _toy_interp *interp;
    struct __jmp_buf_tag jmp_env[1];
error_reset:
    interp = new_interp("main", (1024), ((void *)0), argc, argv, envp);
    b = new_bulk();
    if (0 == _setjmp (jmp_env)) {
 cstack_set_jmpbuff(0, &jmp_env);
    } else {
 fprintf(stderr, "Catch the main co-routine stack overflow, to be restarted.\n");
 goto error_reset;
    }
    if (argv[1] && (strcmp(argv[1], "-") != 0)) {
 if (0 == bulk_load_file(b, argv[1])) {
     fprintf(stderr, "file not open: %s\n", argv[1]);
     exit(1);
 }
 any = toy_parse_start(b);
 if (((void *)0) == any) {
     fprintf(stderr, "no memory\n");
     exit(1);
 }
 switch (((any==((void *)0))?-1:((0x000000ff) & (any->tag)))) {
 case 13:
     err = any;
     fprintf(stderr, "parse error: %s\n",
      to_string((((err->u.exception.msg_list)==((void *)0))?((void *)0):(((((err->u.exception.msg_list)==((void *)0))?-1:((0x000000ff) & ((err->u.exception.msg_list)->tag)))==3)?(err->u.exception.msg_list)->u.list.item:((void *)0)))));
     exit(0);
 case 7:
     script = any;
     result = toy_eval_script(interp, script);
     if (((result==((void *)0))?-1:((0x000000ff) & (result->tag))) != 13) {
  fprintf(stdout, "result[%s]=> ", toy_get_type_str(result));
  fprintf(stdout, "%s\n", to_print(result));
     } else {
  fprintf(stdout, "EXCEPTION: %s\n", to_string(result));
     }
     exit(0);
 default:
     fprintf(stderr, "parse error: type=%s\n", toy_get_type_str(any));
     exit(1);
 }
    }
    while (! feof(stdin)) {
 fputs("> ", stderr);
 if (((void *)0) == fgets(buff, (4096), stdin)) break;
 buff[(4096)-1] = 0;
 if (buff[0] == '!') {
     buff[strlen(buff)-1] = 0;
     if (0 == bulk_load_file(b, &buff[1])) {
  fprintf(stderr, "file not open: %s\n", &buff[1]);
  continue;
     }
 } else {
     bulk_set_string(b, buff);
 }
 any = toy_parse_start(b);
 if (((void *)0) == any) {
     fprintf(stderr, "no memory\n");
 } else {
     switch (((any==((void *)0))?-1:((0x000000ff) & (any->tag)))) {
     case 13:
  err = any;
  fprintf(stderr, "parse error: %s\n",
   to_string((((err->u.exception.msg_list)==((void *)0))?((void *)0):(((((err->u.exception.msg_list)==((void *)0))?-1:((0x000000ff) & ((err->u.exception.msg_list)->tag)))==3)?(err->u.exception.msg_list)->u.list.item:((void *)0)))));
  if (cell_eq_str(err->u.exception.code, "ErrParseClose") == 0) break;
  if (buff[0] == '!') break;
  c = new_cell(buff);
  while (1) {
      fputs("=> ", stderr);
      if (((void *)0) == fgets(buff, (4096), stdin)) goto exit_loop;
      buff[(4096)-1] = 0;
      cell_add_str(c, buff);
      bulk_set_string(b, (c->data));
      any = toy_parse_start(b);
      if (((any==((void *)0))?-1:((0x000000ff) & (any->tag))) == 13) {
   err = any;
   if (cell_eq_str(err->u.exception.code, "ErrParseClose") == 0) {
       fprintf(stderr, "parse error: %s\n",
        to_string((((err->u.exception.msg_list)==((void *)0))?((void *)0):(((((err->u.exception.msg_list)==((void *)0))?-1:((0x000000ff) & ((err->u.exception.msg_list)->tag)))==3)?(err->u.exception.msg_list)->u.list.item:((void *)0)))));
       goto next_loop;
   }
      } else {
   break;
      }
  }
     case 7:
  script = any;
  result = toy_eval_script(interp, script);
  if (((result==((void *)0))?-1:((0x000000ff) & (result->tag))) != 13) {
      char *p;
      fprintf(stdout, "result[%s]=> ", toy_get_type_str(result));
      p = to_print(result);
      if (strlen(p) > 512) {
   fprintf(stdout, "%-.512s ...\n", p);
      } else {
   fprintf(stdout, "%s\n", p);
      }
  } else {
      fprintf(stdout, "EXCEPTION: %s\n", to_string(result));
  }
  break;
     default:
  fprintf(stderr, "parse error: type=%s\n", toy_get_type_str(any));
     }
 }
    next_loop:
 0;
    }
exit_loop:
    return 0;
}

variable_types:
envp
char **

variable_types:
buff
char [-1]

variable_types: struct _bulk { int length; int allocsize; int pos; int line; char *data; } *

variable_types: struct _toy_interp { char *name; int stack_size; int cur_func_stack; struct _toy_func_env { struct _hash { int bucket_size; struct hash_bucket { char *key; unsigned int index; struct _toy_type { unsigned int tag; union _u { struct _symbol { struct _cell { int length; int allocsize; char *data; } *cell; unsigned int hash_index; } symbol; struct _ref { struct _cell *cell; unsigned int hash_index; } ref; struct _list { struct _toy_type *item; struct _toy_type *nextp; } list; struct __mpz_struct { int _mp_alloc; int _mp_size; unsigned long *_mp_d; } biginteger[1]; double real; struct _cell *string; struct _toy_type *statement_list; struct _statement { struct _toy_type *item_list; struct _toy_func_trace_info { int line; struct _toy_type *object_name; struct _toy_type *func_name; struct _toy_type *statement; } *trace_info; } statement; struct _toy_type *block_body; struct _toy_type *eval_body; struct _native { struct _toy_type *(*cfunc)(struct _toy_interp *interp, struct _toy_type *posargs, struct _hash *namedargs, int arglen); struct _toy_type *argspec_list; } native; struct _object { struct _hash *slots; struct _toy_type *delegate_list; } object; struct _exception { struct _cell *code; struct _toy_type *msg_list; } exception; struct _closure { struct _toy_type *block_body; struct _toy_env { struct _toy_func_env *func_env; struct _toy_obj_env { struct _hash *cur_object_slot; struct _toy_type *cur_object; struct _toy_type *self; } *object_env; struct _toy_type *tobe_bind_val; } *env; } closure; struct _func { struct _toy_argspec { struct _toy_type *list; int posarg_len; struct _array { int alloc_size; int cur_size; struct _toy_type *array; } *posarg_array; struct _hash *namedarg; } *argspec; struct _toy_type *closure; } func; struct _control { unsigned int code; struct _toy_type *ret_value; } control; void *container; struct _getmacro { struct _toy_type *obj; struct _toy_type *para; } getmacro; struct _initmacro { struct _toy_type *class; struct _toy_type *param; } initmacro; struct _alias { struct _hash *slot; struct _toy_type *key; } alias; struct _cell *rquote; struct _toy_type *bind_var; struct _hash *dict; struct _array *vector; struct _toy_coroutine { struct _toy_interp *interp; struct _toy_type *script; int state; void *coro_id; } *coroutine; } u; } *item; struct hash_bucket *next; } **bucket; int items; int synonyms; } *localvar; struct _toy_func_env *upstack; struct _toy_type *tobe_bind_val; struct _toy_func_trace_info *trace_info; int script_id; } **func_stack; int cur_obj_stack; struct _toy_obj_env **obj_stack; struct _hash *funcs; struct _hash *classes; struct _hash *globals; struct _hash *scripts; struct _toy_func_trace_info *trace_info; int script_id; struct _hash *gcache; int cache_hit; int cache_missing; int trace; int trace_fd; int cstack_id; void *cstack; int cstack_size; void *coroid; struct _toy_interp *co_parent; struct _toy_type *co_value; int co_calling; } *

variable_types: struct __jmp_buf_tag { long __jmpbuf[8]; int __mask_was_saved; struct __sigset_t { unsigned long __val[-1]; } __saved_mask; } [1]

variable_types:
p
char *

user_defined_types: struct __jmp_buf_tag { long __jmpbuf[8]; int __mask_was_saved; struct __sigset_t __saved_mask; }

user_defined_types: struct _toy_env { struct _toy_func_env *func_env; struct _toy_obj_env *object_env; struct _toy_type *tobe_bind_val; }

user_defined_types: struct hash_bucket { char *key; unsigned int index; struct _toy_type *item; struct hash_bucket *next; }


decompiled_code:
__int64 __fastcall new_list(__int64 a1)
{
__int64 result; // rax

result = GC_malloc(24LL);
if ( !result )
{
puts("alloc failed.");
exit(255);
}
*(_DWORD *)result = 3;
*(_QWORD *)(result + 16) = 0LL;
*(_QWORD *)(result + 8) = a1;
return result;
}

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

result = GC_malloc(24LL);
if ( !result )
{
puts("alloc failed.");
exit(255);
}
*(_DWORD *)result = 3;
*(_QWORD *)(result + 16) = 0LL;
*(_QWORD *)(result + 8) = a1;
return result;
}

original_code:
Toy_Type*
new_list(Toy_Type *item) {
    Toy_Type *list;
    list = GC_malloc(sizeof(Toy_Type));
    if (!list) {printf("alloc failed.\n"); exit(255);};
    list->tag = 3;
    list->u.list.nextp = ((void *)0);
    list->u.list.item = item;
    return list;
}

canonical_original_code:
struct _toy_type *new_list(struct _toy_type *item) {
    struct _toy_type *list;
    list = GC_malloc(sizeof(Toy_Type));
    if (!list) {printf("alloc failed.\n"); exit(255);};
    list->tag = 3;
    list->u.list.nextp = ((void *)0);
    list->u.list.item = item;
    return list;
}

variable_types:
item
struct _toy_type *

return_type: struct _toy_type { unsigned int tag; union _u { struct _symbol { struct _cell { int length; int allocsize; char *data; } *cell; unsigned int hash_index; } symbol; struct _ref { struct _cell *cell; unsigned int hash_index; } ref; struct _list { struct _toy_type *item; struct _toy_type *nextp; } list; struct __mpz_struct { int _mp_alloc; int _mp_size; unsigned long *_mp_d; } biginteger[1]; double real; struct _cell *string; struct _toy_type *statement_list; struct _statement { struct _toy_type *item_list; struct _toy_func_trace_info { int line; struct _toy_type *object_name; struct _toy_type *func_name; struct _toy_type *statement; } *trace_info; } statement; struct _toy_type *block_body; struct _toy_type *eval_body; struct _native { struct _toy_type *(*cfunc)(struct _toy_interp { char *name; int stack_size; int cur_func_stack; struct _toy_func_env { struct _hash { int bucket_size; struct hash_bucket { char *key; unsigned int index; struct _toy_type *item; struct hash_bucket *next; } **bucket; int items; int synonyms; } *localvar; struct _toy_func_env *upstack; struct _toy_type *tobe_bind_val; struct _toy_func_trace_info *trace_info; int script_id; } **func_stack; int cur_obj_stack; struct _toy_obj_env { struct _hash *cur_object_slot; struct _toy_type *cur_object; struct _toy_type *self; } **obj_stack; struct _hash *funcs; struct _hash *classes; struct _hash *globals; struct _hash *scripts; struct _toy_func_trace_info *trace_info; int script_id; struct _hash *gcache; int cache_hit; int cache_missing; int trace; int trace_fd; int cstack_id; void *cstack; int cstack_size; void *coroid; struct _toy_interp *co_parent; struct _toy_type *co_value; int co_calling; } *interp, struct _toy_type *posargs, struct _hash *namedargs, int arglen); struct _toy_type *argspec_list; } native; struct _object { struct _hash *slots; struct _toy_type *delegate_list; } object; struct _exception { struct _cell *code; struct _toy_type *msg_list; } exception; struct _closure { struct _toy_type *block_body; struct _toy_env { struct _toy_func_env *func_env; struct _toy_obj_env *object_env; struct _toy_type *tobe_bind_val; } *env; } closure; struct _func { struct _toy_argspec { struct _toy_type *list; int posarg_len; struct _array { int alloc_size; int cur_size; struct _toy_type *array; } *posarg_array; struct _hash *namedarg; } *argspec; struct _toy_type *closure; } func; struct _control { unsigned int code; struct _toy_type *ret_value; } control; void *container; struct _getmacro { struct _toy_type *obj; struct _toy_type *para; } getmacro; struct _initmacro { struct _toy_type *class; struct _toy_type *param; } initmacro; struct _alias { struct _hash *slot; struct _toy_type *key; } alias; struct _cell *rquote; struct _toy_type *bind_var; struct _hash *dict; struct _array *vector; struct _toy_coroutine { struct _toy_interp *interp; struct _toy_type *script; int state; void *coro_id; } *coroutine; } u; } *


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

result = GC_malloc(24LL);
if ( !result )
{
puts("alloc failed.");
exit(255);
}
*(_DWORD *)result = 3;
*(_QWORD *)(result + 8) = a1;
*(_QWORD *)(result + 16) = a2;
return result;
}

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

result = GC_malloc(24LL);
if ( !result )
{
puts("alloc failed.");
exit(255);
}
*(_DWORD *)result = 3;
*(_QWORD *)(result + 8) = a1;
*(_QWORD *)(result + 16) = a2;
return result;
}

original_code:
Toy_Type*
new_cons(Toy_Type *car, Toy_Type *cdr) {
    Toy_Type *list;
    list = GC_malloc(sizeof(Toy_Type));
    if (!list) {printf("alloc failed.\n"); exit(255);};
    list->tag = 3;
    list->u.list.item = car;
    list->u.list.nextp = cdr;
    return list;
}

canonical_original_code:
struct _toy_type *new_cons(struct _toy_type *car, struct _toy_type *cdr) {
    struct _toy_type *list;
    list = GC_malloc(sizeof(Toy_Type));
    if (!list) {printf("alloc failed.\n"); exit(255);};
    list->tag = 3;
    list->u.list.item = car;
    list->u.list.nextp = cdr;
    return list;
}

variable_types:
car
struct _toy_type *

variable_types:
cdr
struct _toy_type *

user_defined_types: struct _ref { struct _cell *cell; unsigned int hash_index; }

user_defined_types: struct _list { struct _toy_type *item; struct _toy_type *nextp; }

user_defined_types: struct _object { struct _hash *slots; struct _toy_type *delegate_list; }

user_defined_types: struct _exception { struct _cell *code; struct _toy_type *msg_list; }

user_defined_types: struct _control { unsigned int code; struct _toy_type *ret_value; }

user_defined_types: struct _getmacro { struct _toy_type *obj; struct _toy_type *para; }

user_defined_types: struct _initmacro { struct _toy_type *class; struct _toy_type *param; }

user_defined_types: struct _alias { struct _hash *slot; struct _toy_type *key; }

user_defined_types: struct __mpz_struct { int _mp_alloc; int _mp_size; unsigned long *_mp_d; }

user_defined_types: struct _toy_coroutine { struct _toy_interp *interp; struct _toy_type *script; int state; void *coro_id; }

user_defined_types: struct _cell { int length; int allocsize; char *data; }

user_defined_types: struct _toy_func_trace_info { int line; struct _toy_type *object_name; struct _toy_type *func_name; struct _toy_type *statement; }

user_defined_types: struct _array { int alloc_size; int cur_size; struct _toy_type *array; }

user_defined_types: struct _toy_obj_env { struct _hash *cur_object_slot; struct _toy_type *cur_object; struct _toy_type *self; }


decompiled_code:
__int64 __fastcall list_append(__int64 a1, __int64 a2)
{
__int64 v2; // rbp
__int64 v3; // rbx
__int64 result; // rax

v2 = a1;
if ( !a1 )
return 0LL;
v3 = *(_QWORD *)(a1 + 16);
if ( *(_QWORD *)(a1 + 8) )
{
if ( v3 )
goto LABEL_6;
LABEL_9:
result = new_list(a2);
*(_QWORD *)(v2 + 16) = result;
return result;
}
if ( v3 )
{
LABEL_6:
while ( *(_BYTE *)v3 == 3 )
{
v2 = v3;
if ( !*(_QWORD *)(v3 + 16) )
{
result = new_list(a2);
*(_QWORD *)(v3 + 16) = result;
return result;
}
v3 = *(_QWORD *)(v3 + 16);
}
goto LABEL_9;
}
*(_QWORD *)(a1 + 8) = a2;
return a1;
}

canonical_decompiled_code:
__int64 __fastcall func2(__int64 a1, __int64 a2)
{
__int64 v2; // rbp
__int64 v3; // rbx
__int64 result; // rax

v2 = a1;
if ( !a1 )
return 0LL;
v3 = *(_QWORD *)(a1 + 16);
if ( *(_QWORD *)(a1 + 8) )
{
if ( v3 )
goto LABEL_6;
LABEL_9:
result = func0(a2);
*(_QWORD *)(v2 + 16) = result;
return result;
}
if ( v3 )
{
LABEL_6:
while ( *(_BYTE *)v3 == 3 )
{
v2 = v3;
if ( !*(_QWORD *)(v3 + 16) )
{
result = func0(a2);
*(_QWORD *)(v3 + 16) = result;
return result;
}
v3 = *(_QWORD *)(v3 + 16);
}
goto LABEL_9;
}
*(_QWORD *)(a1 + 8) = a2;
return a1;
}

original_code:
Toy_Type*
list_append(Toy_Type *list, Toy_Type *item) {
    if (list == ((void *)0)) return ((void *)0);
    if (((list==((void *)0))?1:((((void *)0)==list->u.list.item)&&(((void *)0)==list->u.list.nextp)))) {
 list->u.list.item = item;
 return list;
    }
    if (((void *)0) == list->u.list.nextp) {
 list->u.list.nextp = new_list(item);
 return list->u.list.nextp;
    }
    while (list->u.list.nextp) {
 if (((list->u.list.nextp==((void *)0))?-1:((0x000000ff) & (list->u.list.nextp->tag))) != 3) {
     list->u.list.nextp = new_list(item);
     return list->u.list.nextp;
 }
 list = list->u.list.nextp;
    }
    list->u.list.nextp = new_list(item);
    return list->u.list.nextp;
}

canonical_original_code:
struct _toy_type *list_append(struct _toy_type *list, struct _toy_type *item) {
    if (list == ((void *)0)) return ((void *)0);
    if (((list==((void *)0))?1:((((void *)0)==list->u.list.item)&&(((void *)0)==list->u.list.nextp)))) {
 list->u.list.item = item;
 return list;
    }
    if (((void *)0) == list->u.list.nextp) {
 list->u.list.nextp = new_list(item);
 return list->u.list.nextp;
    }
    while (list->u.list.nextp) {
 if (((list->u.list.nextp==((void *)0))?-1:((0x000000ff) & (list->u.list.nextp->tag))) != 3) {
     list->u.list.nextp = new_list(item);
     return list->u.list.nextp;
 }
 list = list->u.list.nextp;
    }
    list->u.list.nextp = new_list(item);
    return list->u.list.nextp;
}

variable_types:
list
struct _toy_type *

user_defined_types: struct _toy_type { unsigned int tag; union _u u; }

user_defined_types: union _u { struct _symbol symbol; struct _ref ref; struct _list list; struct __mpz_struct biginteger[1]; double real; struct _cell *string; struct _toy_type *statement_list; struct _statement statement; struct _toy_type *block_body; struct _toy_type *eval_body; struct _native native; struct _object object; struct _exception exception; struct _closure closure; struct _func func; struct _control control; void *container; struct _getmacro getmacro; struct _initmacro initmacro; struct _alias alias; struct _cell *rquote; struct _toy_type *bind_var; struct _hash *dict; struct _array *vector; struct _toy_coroutine *coroutine; }

user_defined_types: struct _symbol { struct _cell *cell; unsigned int hash_index; }

user_defined_types: struct _statement { struct _toy_type *item_list; struct _toy_func_trace_info *trace_info; }

user_defined_types: struct _native { struct _toy_type *(*cfunc)(struct _toy_interp *interp, struct _toy_type *posargs, struct _hash *namedargs, int arglen); struct _toy_type *argspec_list; }

user_defined_types: struct _closure { struct _toy_type *block_body; struct _toy_env *env; }

user_defined_types: struct _func { struct _toy_argspec *argspec; struct _toy_type *closure; }

user_defined_types: struct _toy_argspec { struct _toy_type *list; int posarg_len; struct _array *posarg_array; struct _hash *namedarg; }

user_defined_types: struct _toy_interp { char *name; int stack_size; int cur_func_stack; struct _toy_func_env **func_stack; int cur_obj_stack; struct _toy_obj_env **obj_stack; struct _hash *funcs; struct _hash *classes; struct _hash *globals; struct _hash *scripts; struct _toy_func_trace_info *trace_info; int script_id; struct _hash *gcache; int cache_hit; int cache_missing; int trace; int trace_fd; int cstack_id; void *cstack; int cstack_size; void *coroid; struct _toy_interp *co_parent; struct _toy_type *co_value; int co_calling; }

user_defined_types: struct _toy_func_env { struct _hash *localvar; struct _toy_func_env *upstack; struct _toy_type *tobe_bind_val; struct _toy_func_trace_info *trace_info; int script_id; }

user_defined_types: struct _hash { int bucket_size; struct hash_bucket **bucket; int items; int synonyms; }


decompiled_code:
__int64 __fastcall list_length(__int64 a1)
{
__int64 v1; // rax
unsigned int v2; // er8

if ( !a1 )
return 0LL;
v1 = *(_QWORD *)(a1 + 16);
v2 = 1;
if ( *(_QWORD *)(a1 + 8) )
goto LABEL_6;
if ( !v1 )
return 0LL;
do
{
++v2;
if ( *(_BYTE *)v1 != 3 )
break;
v1 = *(_QWORD *)(v1 + 16);
LABEL_6:
;
}
while ( v1 );
return v2;
}

canonical_decompiled_code:
__int64 __fastcall func3(__int64 a1)
{
__int64 v1; // rax
unsigned int v2; // er8

if ( !a1 )
return 0LL;
v1 = *(_QWORD *)(a1 + 16);
v2 = 1;
if ( *(_QWORD *)(a1 + 8) )
goto LABEL_6;
if ( !v1 )
return 0LL;
do
{
++v2;
if ( *(_BYTE *)v1 != 3 )
break;
v1 = *(_QWORD *)(v1 + 16);
LABEL_6:
;
}
while ( v1 );
return v2;
}

original_code:
int
list_length(Toy_Type *list) {
    int length = 1;
    if (((void *)0) == list) return 0;
    if (((list==((void *)0))?1:((((void *)0)==list->u.list.item)&&(((void *)0)==list->u.list.nextp)))) return 0;
    while (list->u.list.nextp) {
 list = list->u.list.nextp;
 length++;
 if (((list==((void *)0))?-1:((0x000000ff) & (list->tag))) != 3) return length;
    }
    return length;
}

canonical_original_code:
int list_length(struct _toy_type *list) {
    int length = 1;
    if (((void *)0) == list) return 0;
    if (((list==((void *)0))?1:((((void *)0)==list->u.list.item)&&(((void *)0)==list->u.list.nextp)))) return 0;
    while (list->u.list.nextp) {
 list = list->u.list.nextp;
 length++;
 if (((list==((void *)0))?-1:((0x000000ff) & (list->tag))) != 3) return length;
    }
    return length;
}

variable_types: length int

user_defined_types: struct _ref { struct _cell *cell; unsigned int hash_index; }

user_defined_types: struct _list { struct _toy_type *item; struct _toy_type *nextp; }

user_defined_types: struct _object { struct _hash *slots; struct _toy_type *delegate_list; }

user_defined_types: struct _exception { struct _cell *code; struct _toy_type *msg_list; }

user_defined_types: struct _control { unsigned int code; struct _toy_type *ret_value; }

user_defined_types: struct _getmacro { struct _toy_type *obj; struct _toy_type *para; }

user_defined_types: struct _initmacro { struct _toy_type *class; struct _toy_type *param; }

user_defined_types: struct _alias { struct _hash *slot; struct _toy_type *key; }

user_defined_types: struct __mpz_struct { int _mp_alloc; int _mp_size; unsigned long *_mp_d; }

user_defined_types: struct _toy_env { struct _toy_func_env *func_env; struct _toy_obj_env *object_env; struct _toy_type *tobe_bind_val; }

user_defined_types: struct hash_bucket { char *key; unsigned int index; struct _toy_type *item; struct hash_bucket *next; }


decompiled_code:
__int64 __fastcall cell_get_alloc_size(int a1, int a2)
{
__int64 result; // rax

result = (unsigned int)a1;
if ( a1 < a2 )
{
do
result = (unsigned int)(2 * result);
while ( a2 > (int)result );
}
return result;
}

canonical_decompiled_code:
__int64 __fastcall func0(int a1, int a2)
{
__int64 result; // rax

result = (unsigned int)a1;
if ( a1 < a2 )
{
do
result = (unsigned int)(2 * result);
while ( a2 > (int)result );
}
return result;
}

original_code:
static int
cell_get_alloc_size(int init_s, int dest_s) {
    int i = init_s;
    while (i < dest_s) {
 i = i*2;
    }
    return i;
}


decompiled_code:
__int64 __fastcall cell_realloc(__int64 a1, int a2)
{
int v2; // ebx
void *v3; // rax
void *v4; // rax

v2 = cell_get_alloc_size(*(_DWORD *)(a1 + 4), a2);
v3 = (void *)GC_malloc_atomic();
if ( !v3 )
{
puts("alloc failed.");
exit(255);
}
v4 = memcpy(v3, *(const void **)(a1 + 8), *(_DWORD *)a1 + 1);
*(_DWORD *)(a1 + 4) = v2;
*(_QWORD *)(a1 + 8) = v4;
return a1;
}

canonical_decompiled_code:
__int64 __fastcall func1(__int64 a1, int a2)
{
int v2; // ebx
void *v3; // rax
void *v4; // rax

v2 = func0(*(_DWORD *)(a1 + 4), a2);
v3 = (void *)GC_malloc_atomic();
if ( !v3 )
{
puts("alloc failed.");
exit(255);
}
v4 = memcpy(v3, *(const void **)(a1 + 8), *(_DWORD *)a1 + 1);
*(_DWORD *)(a1 + 4) = v2;
*(_QWORD *)(a1 + 8) = v4;
return a1;
}

original_code:
static Cell*
cell_realloc(Cell *p, int dest_s) {
    int i;
    char *data;
    i = cell_get_alloc_size(p->allocsize, dest_s);
    data = GC_malloc_atomic(i);
    if (!data) {printf("alloc failed.\n"); exit(255);};
    memcpy(data, p->data, p->length+1);
    p->data = data;
    p->allocsize = i;
    return p;
}

canonical_original_code:
static struct _cell *cell_realloc(struct _cell *p, int dest_s) {
    int i;
    char *data;
    i = cell_get_alloc_size(p->allocsize, dest_s);
    data = GC_malloc_atomic(i);
    if (!data) {printf("alloc failed.\n"); exit(255);};
    memcpy(data, p->data, p->length+1);
    p->data = data;
    p->allocsize = i;
    return p;
}

variable_types:
p
struct _cell *

variable_types:
data
char *

return_type: struct _cell { int length; int allocsize; char *data; } *


decompiled_code:
__int64 __fastcall new_cell(const char *a1)
{
const char *v1; // rbp
__int64 v2; // r12
int v3; // ebx
int v4; // eax
int v5; // edx
char *v6; // rax

if ( a1 )
v1 = a1;
else
v1 = &src;
v2 = GC_malloc(16LL);
if ( !v2
|| (v3 = strlen(v1) + 1,
v4 = cell_get_alloc_size(8, v3),
*(_DWORD *)v2 = v5,
*(_DWORD *)(v2 + 4) = v4,
v6 = (char *)GC_malloc_atomic(v4),
(*(_QWORD *)(v2 + 8) = v6) == 0LL) )
{
puts("alloc failed.");
exit(255);
}
strncpy(v6, v1, v3);
return v2;
}

canonical_decompiled_code:
__int64 __fastcall func2(const char *a1)
{
const char *v1; // rbp
__int64 v2; // r12
int v3; // ebx
int v4; // eax
int v5; // edx
char *v6; // rax

if ( a1 )
v1 = a1;
else
v1 = &src;
v2 = GC_malloc(16LL);
if ( !v2
|| (v3 = strlen(v1) + 1,
v4 = func0(8, v3),
*(_DWORD *)v2 = v5,
*(_DWORD *)(v2 + 4) = v4,
v6 = (char *)GC_malloc_atomic(v4),
(*(_QWORD *)(v2 + 8) = v6) == 0LL) )
{
puts("alloc failed.");
exit(255);
}
strncpy(v6, v1, v3);
return v2;
}

original_code:
Cell*
new_cell(const char *src) {
    Cell *c;
    int alen, len;
    if (((void *)0) == src) return new_cell("");
    c = (Cell*)GC_malloc(sizeof(Cell));
    if (!c) {printf("alloc failed.\n"); exit(255);};
    len = strlen(src)+1;
    alen = cell_get_alloc_size((8), len);
    c->length = len-1;
    c->allocsize = alen;
    c->data = (char*) GC_malloc_atomic(alen);
    if (!c->data) {printf("alloc failed.\n"); exit(255);};
    strncpy(c->data, src, len);
    return c;
}

canonical_original_code:
struct _cell *new_cell(char *src) {
    struct _cell *c;
    int alen; int len;
    if (((void *)0) == src) return new_cell("");
    c = (struct _cell *)GC_malloc(sizeof(Cell));
    if (!c) {printf("alloc failed.\n"); exit(255);};
    len = strlen(src)+1;
    alen = cell_get_alloc_size((8), len);
    c->length = len-1;
    c->allocsize = alen;
    c->data = (char *) GC_malloc_atomic(alen);
    if (!c->data) {printf("alloc failed.\n"); exit(255);};
    strncpy(c->data, src, len);
    return c;
}

variable_types:
src
char *

variable_types: struct _cell { int length; int allocsize; char *data; } *

variable_types: alen int

variable_types: len int


decompiled_code:
int *__fastcall cell_add_str(int *a1, const char *a2)
{
int v4; // eax
__int64 v5; // rdi
int v6; // ebp
int v7; // esi
int *result; // rax

if ( !a1 )
return 0LL;
v4 = strlen(a2);
v5 = *a1;
v6 = v4 + 1;
v7 = v5 + v4 + 1;
if ( v7 <= a1[1] )
{
LABEL_5:
strncpy((char *)(*((_QWORD *)a1 + 1) + v5), a2, v6);
result = a1;
*a1 = *a1 + v6 - 1;
return result;
}
if ( cell_realloc((__int64)a1, v7) )
{
v5 = *a1;
goto LABEL_5;
}
return 0LL;
}

canonical_decompiled_code:
int *__fastcall func3(int *a1, const char *a2)
{
int v4; // eax
__int64 v5; // rdi
int v6; // ebp
int v7; // esi
int *result; // rax

if ( !a1 )
return 0LL;
v4 = strlen(a2);
v5 = *a1;
v6 = v4 + 1;
v7 = v5 + v4 + 1;
if ( v7 <= a1[1] )
{
LABEL_5:
strncpy((char *)(*((_QWORD *)a1 + 1) + v5), a2, v6);
result = a1;
*a1 = *a1 + v6 - 1;
return result;
}
if ( func1((__int64)a1, v7) )
{
v5 = *a1;
goto LABEL_5;
}
return 0LL;
}

original_code:
Cell*
cell_add_str(Cell *p, const char *src) {
    int len;
    if (((void *)0) == p) return ((void *)0);
    len = strlen(src)+1;
    if ((len + p->length) > p->allocsize) {
 if (((void *)0) == cell_realloc(p, len + p->length))
     return ((void *)0);
    }
    strncpy(&p->data[p->length], src, len);
    p->length = p->length + len-1;
    return p;
}

canonical_original_code:
struct _cell *cell_add_str(struct _cell *p, char *src) {
    int len;
    if (((void *)0) == p) return ((void *)0);
    len = strlen(src)+1;
    if ((len + p->length) > p->allocsize) {
 if (((void *)0) == cell_realloc(p, len + p->length))
     return ((void *)0);
    }
    strncpy(&p->data[p->length], src, len);
    p->length = p->length + len-1;
    return p;
}

user_defined_types: struct _cell { int length; int allocsize; char *data; }


decompiled_code:
int *__fastcall cell_add_char(int *a1, char a2)
{
__int64 v2; // rax
int *result; // rax

if ( !a1 )
return 0LL;
v2 = *a1;
if ( (int)v2 + 2 > a1[1] )
{
if ( !cell_realloc((__int64)a1, (int)v2 + 2) )
return 0LL;
v2 = *a1;
}
*(_BYTE *)(*((_QWORD *)a1 + 1) + v2) = a2;
*(_BYTE *)(*((_QWORD *)a1 + 1) + *a1 + 1LL) = 0;
result = a1;
++*a1;
return result;
}

canonical_decompiled_code:
int *__fastcall func4(int *a1, char a2)
{
__int64 v2; // rax
int *result; // rax

if ( !a1 )
return 0LL;
v2 = *a1;
if ( (int)v2 + 2 > a1[1] )
{
if ( !func1((__int64)a1, (int)v2 + 2) )
return 0LL;
v2 = *a1;
}
*(_BYTE *)(*((_QWORD *)a1 + 1) + v2) = a2;
*(_BYTE *)(*((_QWORD *)a1 + 1) + *a1 + 1LL) = 0;
result = a1;
++*a1;
return result;
}

original_code:
Cell*
cell_add_char(Cell *p, const char src) {
    int len;
    if (((void *)0) == p) return ((void *)0);
    len = 2;
    if ((len + p->length) > p->allocsize) {
 if (((void *)0) == cell_realloc(p, len + p->length))
     return ((void *)0);
    }
    p->data[p->length] = src;
    p->data[p->length+1] = 0;
    p->length = p->length + len-1;
    return p;
}

canonical_original_code:
struct _cell *cell_add_char(struct _cell *p, char src) {
    int len;
    if (((void *)0) == p) return ((void *)0);
    len = 2;
    if ((len + p->length) > p->allocsize) {
 if (((void *)0) == cell_realloc(p, len + p->length))
     return ((void *)0);
    }
    p->data[p->length] = src;
    p->data[p->length+1] = 0;
    p->length = p->length + len-1;
    return p;
}

variable_types: src char


decompiled_code:
int __fastcall cell_eq_str(__int64 a1, const char *a2)
{
return strcmp(*(const char **)(a1 + 8), a2);
}

canonical_decompiled_code:
int __fastcall func5(__int64 a1, const char *a2)
{
return strcmp(*(const char **)(a1 + 8), a2);
}

original_code:
int
cell_eq_str(Cell *s, char *d) {
    return strcmp((s->data), d);
}

canonical_original_code:
int cell_eq_str(struct _cell *s, char *d) {
    return strcmp((s->data), d);
}

variable_types:
d
char *