Fixture 31
edit distance
C · 2 functions · 4 lanes · 8 of 8 function-lanes behave identically
All 4 lanes recompile and return the same results as the original.
Levenshtein distance over a flat (ED_MAX+1)^2 table. The classic three-way minimum makes the inner body a small dependence lattice: every cell reads two previous rows/columns, so a decompiler must keep the row stride and the -1 offsets exact to reproduce the result.
#include <stdint.h>
/* Levenshtein distance over a flat (ED_MAX+1)^2 table. The classic
* three-way minimum makes the inner body a small dependence lattice: every
* cell reads two previous rows/columns, so a decompiler must keep the row
* stride and the -1 offsets exact to reproduce the result. */
#define ED_MAX 8
#define ED_STRIDE (ED_MAX + 1)
__attribute__((noinline)) int32_t
edit_distance(const uint8_t *left, int32_t left_length, const uint8_t *right,
int32_t right_length) {
int32_t table[ED_STRIDE * ED_STRIDE];
int32_t i;
int32_t j;
if (left == 0 || right == 0 || left_length < 0 || right_length < 0 ||
left_length > ED_MAX || right_length > ED_MAX) {
return -1;
}
for (i = 0; i <= left_length; ++i) {
table[i * ED_STRIDE] = i;
}
for (j = 0; j <= right_length; ++j) {
table[j] = j;
}
for (i = 1; i <= left_length; ++i) {
for (j = 1; j <= right_length; ++j) {
int32_t cost = (left[i - 1] == right[j - 1]) ? 0 : 1;
int32_t best = table[(i - 1) * ED_STRIDE + j] + 1;
int32_t insertion = table[i * ED_STRIDE + (j - 1)] + 1;
int32_t substitution = table[(i - 1) * ED_STRIDE + (j - 1)] + cost;
if (insertion < best) {
best = insertion;
}
if (substitution < best) {
best = substitution;
}
table[i * ED_STRIDE + j] = best;
}
}
return table[left_length * ED_STRIDE + right_length];
}
__attribute__((noinline)) int32_t
hamming_distance(const uint8_t *left, const uint8_t *right, int32_t length) {
int32_t distance = 0;
int32_t i;
if (left == 0 || right == 0 || length < 0 || length > ED_MAX) {
return -1;
}
for (i = 0; i < length; ++i) {
if (left[i] != right[i]) {
distance += 1;
}
}
return distance;
} Recovered C
Generated by glaurung decompile --style decbench at b47f6b43.
baseline.json records the result after recompiling the C and calling it beside the
original with seeded inputs.
clang -O0
2/2edit_distance pass 68 lines
// glaurung: edit_distance @ 0x1100
__attribute__((no_stack_protector)) int32_t edit_distance(const uint8_t * arg0, int32_t arg1, const uint8_t * arg2, int32_t arg3) {
int i;
int j;
int cost;
int best;
int insertion;
int substitution;
unsigned char local_170[324];
int local_4;
// x86-64 prologue: save rbp, frame 272 bytes
if ((arg0 == 0)) {
local_4 = -1;
// x86-64 epilogue: restore rbp
return (unsigned int)(local_4);
}
if ((arg2 == 0)) {
local_4 = -1;
// x86-64 epilogue: restore rbp
return (unsigned int)(local_4);
}
if (((long)(arg1) < 0)) {
local_4 = -1;
// x86-64 epilogue: restore rbp
return (unsigned int)(local_4);
}
if (((long)(arg3) < 0)) {
local_4 = -1;
// x86-64 epilogue: restore rbp
return (unsigned int)(local_4);
}
if (((((unsigned long)((unsigned int)(arg1)) == 8) | ((long)(arg1) < 8)) == 0)) {
local_4 = -1;
// x86-64 epilogue: restore rbp
return (unsigned int)(local_4);
}
if (((((unsigned long)((unsigned int)(arg3)) == 8) | ((long)(arg3) < 8)) == 0)) {
local_4 = -1;
// x86-64 epilogue: restore rbp
return (unsigned int)(local_4);
}
for (i = 0; ((((unsigned int)(i) == (unsigned int)(arg1)) | (i < arg1)) != 0); i++) {
*(int *)((&local_170[0] + ((long)((int)((i * 9))) * 4))) = i;
}
for (j = 0; ((((unsigned int)(j) == (unsigned int)(arg3)) | (j < arg3)) != 0); j++) {
*(int *)((&local_170[0] + ((long)(j) * 4))) = j;
}
i = 1;
while (((((unsigned int)(i) == (unsigned int)(arg1)) | (i < arg1)) != 0)) {
for (j = 1; ((((unsigned int)(j) == (unsigned int)(arg3)) | (j < arg3)) != 0); j++) {
cost = (((unsigned int)((unsigned char)(arg0[(long)((int)(((unsigned long)((unsigned int)(i)) - 1)))])) == (unsigned int)((unsigned char)(arg2[(long)((int)(((unsigned long)((unsigned int)(j)) - 1)))]))) ? 0 : 1);
best = ((unsigned int)(*(int *)((&local_170[0] + ((long)((int)((((unsigned long)((unsigned int)(((unsigned long)((unsigned int)(i)) - 1))) * 9) + j))) * 4)))) + 1);
insertion = ((unsigned int)(*(int *)((&local_170[0] + ((long)((int)(((i * 9) + (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(j)) - 1)))))) * 4)))) + 1);
substitution = ((unsigned int)(*(int *)((&local_170[0] + ((long)((int)((((unsigned long)((unsigned int)(((unsigned long)((unsigned int)(i)) - 1))) * 9) + (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(j)) - 1)))))) * 4)))) + cost);
if ((insertion < best)) {
best = insertion;
}
if ((substitution < best)) {
best = substitution;
}
*(int *)((&local_170[0] + ((long)((int)(((i * 9) + j))) * 4))) = best;
}
i = ((unsigned int)(i) + 1);
}
local_4 = *(int *)((&local_170[0] + ((long)((int)(((arg1 * 9) + arg3))) * 4)));
// x86-64 epilogue: restore rbp
return (unsigned int)(local_4);
} hamming_distance pass 36 lines
// glaurung: hamming_distance @ 0x1370
int32_t hamming_distance(const uint8_t * arg0, const uint8_t * arg1, int32_t arg2) {
int distance;
int i;
int local_4;
// x86-64 prologue: save rbp
distance = 0;
if ((arg0 == 0)) {
local_4 = -1;
// x86-64 epilogue: restore rbp
return (unsigned int)(local_4);
}
if ((arg1 == 0)) {
local_4 = -1;
// x86-64 epilogue: restore rbp
return (unsigned int)(local_4);
}
if (((long)(arg2) < 0)) {
local_4 = -1;
// x86-64 epilogue: restore rbp
return (unsigned int)(local_4);
}
if (((((unsigned long)((unsigned int)(arg2)) == 8) | ((long)(arg2) < 8)) == 0)) {
local_4 = -1;
// x86-64 epilogue: restore rbp
return (unsigned int)(local_4);
}
for (i = 0; (i < arg2); i++) {
if (((unsigned int)((unsigned char)(arg0[i])) != (unsigned int)((unsigned char)(arg1[i])))) {
distance = ((unsigned int)(distance) + 1);
}
}
local_4 = distance;
// x86-64 epilogue: restore rbp
return (unsigned int)(local_4);
} clang -O2
2/2edit_distance pass 529 lines
// glaurung: edit_distance @ 0x1100
__attribute__((no_stack_protector)) int32_t edit_distance(const uint8_t * arg0, int32_t arg1, const uint8_t * arg2, int32_t arg3) {
extern long __unknown(long, ...);
int i;
int best;
int j;
int substitution;
unsigned char local_17c[380];
long local_180;
long local_188;
long local_190;
long local_198;
long local_1a0;
long local_1a8;
long local_1b8;
long local_1c0;
long local_1c8;
long local_1d0;
long local_1d8;
long local_1e0;
long ret;
long var0;
long var11;
long var14;
long var153;
long var154;
long var156;
int var157;
int var158;
int var159;
long var16;
int var160;
int var161;
int var162;
int var163;
int var164;
long var174;
long var176;
long var177;
long var179;
long var181;
long var184;
long var185;
long var187;
long var188;
long var189;
long var191;
int var192;
int var193;
int var194;
int var195;
int var196;
int var197;
int var198;
int var199;
long var200;
long var203;
long var204;
int var207;
long var208;
long var210;
long var211;
long var217;
long var218;
long var22;
long var220;
long var222;
long var225;
long var229;
long var23;
long var231;
long var233;
long var235;
long var25;
long var255;
long var256;
long var26;
int var269;
int var27;
int var270;
long var28;
int var285;
int var286;
int var287;
int var288;
long var29;
int var290;
int var291;
int var292;
int var293;
int var295;
int var296;
int var297;
int var298;
long var3;
int var304;
int var305;
int var306;
int var307;
int var316;
int var317;
int var318;
int var319;
long var32;
int var325;
int var326;
int var327;
int var328;
char * var33;
long var350;
int var351;
long var353;
int var354;
long var357;
long var358;
long var36;
long var39;
long var4;
long var42;
int var43;
int var44;
int var45;
int var46;
long var49;
long var50;
int var51;
int var52;
int var53;
int var54;
long var57;
int var58;
int var59;
int var60;
int var61;
int var62;
int var63;
int var64;
int var65;
int var66;
int var67;
int var68;
int var69;
int var70;
int var71;
int var72;
int var73;
int var74;
int var75;
int var76;
int var77;
int var78;
int var79;
long var8;
int var80;
int var81;
int var82;
int var83;
int var84;
int var85;
int var86;
int var87;
int var88;
int var89;
// x86-64 prologue: save callee registers, frame 48 bytes
ret = 0xffffffff;
if (((((unsigned long)((unsigned int)(arg3)) == 8) | ((long)(arg3) < 8)) == 0)) {
// x86-64 epilogue: restore callee registers
return ret;
}
if (((((unsigned long)((unsigned int)(arg1)) == 8) | ((long)(arg1) < 8)) == 0)) {
// x86-64 epilogue: restore callee registers
return ret;
}
if ((arg0 == 0)) {
// x86-64 epilogue: restore callee registers
return ret;
}
if ((arg2 == 0)) {
// x86-64 epilogue: restore callee registers
return ret;
}
var0 = (unsigned long)((unsigned int)(arg3));
if (((long)((int)((arg3 | arg1))) < 0)) {
// x86-64 epilogue: restore callee registers
return ret;
}
var3 = var4;
if (((long)(arg1) < 0)) {
goto L_11bf;
}
var3 = ((unsigned long)((unsigned int)(arg1)) + 1);
var8 = (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(var3)) & 3)));
if (((unsigned long)((unsigned long)((unsigned int)(arg1))) < (unsigned long)(3))) {
var11 = 0;
goto L_1195;
}
var3 = (unsigned long)((unsigned int)((var3 & -4)));
var14 = (long)((&local_17c[0] + 4));
var16 = 0;
do {
*(int *)((var14)) = var16;
*(int *)((var14 + 0x24)) = (var16 + 1);
*(int *)((var14 + 0x48)) = (var16 + 2);
*(int *)((var14 + 0x6c)) = (var16 + 3);
var16 = (var16 + 4);
var14 = (var14 + 144);
var11 = var16;
} while ((var16 != var3));
L_1195: ;
ret = var11;
if ((var8 == 0)) {
goto L_11bf;
}
var3 = (long)((((&local_17c[0] + 20) + ((var11 + (var11 * 8)) * 4)) - 16));
var22 = (var8 << 2);
var23 = (var22 + (var22 * 8));
var25 = 0;
var26 = var11;
do {
*(int *)((var3 + var25)) = var26;
var27 = (var26 + 1);
var26 = (unsigned long)((unsigned int)(var27));
var25 = (var25 + 36);
ret = (unsigned long)((unsigned int)(var27));
} while ((var23 != var25));
L_11bf: ;
var28 = (long)arg0;
if (((long)((int)(var0)) < 0)) {
goto L_133d;
}
var29 = (unsigned long)((unsigned int)((var0 + 1)));
if (((unsigned long)((unsigned long)((unsigned int)(var0))) < (unsigned long)(7))) {
var32 = 0;
var28 = (long)arg0;
goto L_1330;
}
var33 = (char *)arg0;
var32 = (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(var29)) & -8)));
var36 = (var32 - 8);
var39 = (((unsigned long)(var36) >> 3) + 1);
var42 = (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(var39)) & 3)));
if (((unsigned long)(var36) < (unsigned long)(24))) {
var43 = 0;
var44 = 1;
var45 = 2;
var46 = 3;
var49 = 0;
goto L_12d8;
}
var50 = (var39 & -4);
var51 = 0;
var52 = 1;
var53 = 2;
var54 = 3;
var57 = 0;
var58 = 4;
var59 = 4;
var60 = 4;
var61 = 4;
var62 = 8;
var63 = 8;
var64 = 8;
var65 = 8;
var66 = 12;
var67 = 12;
var68 = 12;
var69 = 12;
var70 = 16;
var71 = 16;
var72 = 16;
var73 = 16;
var74 = 20;
var75 = 20;
var76 = 20;
var77 = 20;
var78 = 24;
var79 = 24;
var80 = 24;
var81 = 24;
var82 = 28;
var83 = 28;
var84 = 28;
var85 = 28;
var86 = 32;
var87 = 32;
var88 = 32;
var89 = 32;
do {
*(int *)((&local_17c[0] + ((var57 * 4) + 4))) = var51;
*(int *)((&local_17c[0] + ((var57 * 4) + 8))) = var52;
*(int *)((&local_17c[0] + ((var57 * 4) + 12))) = var53;
*(int *)((&local_17c[0] + ((var57 * 4) + 16))) = var54;
*(int *)((&local_17c[0] + ((var57 * 4) + 20))) = (var51 + var58);
*(int *)((&local_17c[0] + ((var57 * 4) + 24))) = (var52 + var59);
*(int *)((&local_17c[0] + ((var57 * 4) + 28))) = (var53 + var60);
*(int *)((&local_17c[0] + ((var57 * 4) + 32))) = (var54 + var61);
*(int *)((&local_17c[0] + ((var57 * 4) + 36))) = (var51 + var62);
*(int *)((&local_17c[0] + ((var57 * 4) + 40))) = (var52 + var63);
*(int *)((&local_17c[0] + ((var57 * 4) + 44))) = (var53 + var64);
*(int *)((&local_17c[0] + ((var57 * 4) + 48))) = (var54 + var65);
*(int *)((&local_17c[0] + ((var57 * 4) + 52))) = (var51 + var66);
*(int *)((&local_17c[0] + ((var57 * 4) + 56))) = (var52 + var67);
*(int *)((&local_17c[0] + ((var57 * 4) + 60))) = (var53 + var68);
*(int *)((&local_17c[0] + ((var57 * 4) + 64))) = (var54 + var69);
*(int *)((&local_17c[0] + ((var57 * 4) + 68))) = (var51 + var70);
*(int *)((&local_17c[0] + ((var57 * 4) + 72))) = (var52 + var71);
*(int *)((&local_17c[0] + ((var57 * 4) + 76))) = (var53 + var72);
*(int *)((&local_17c[0] + ((var57 * 4) + 80))) = (var54 + var73);
*(int *)((&local_17c[0] + ((var57 * 4) + 84))) = (var51 + var74);
*(int *)((&local_17c[0] + ((var57 * 4) + 88))) = (var52 + var75);
*(int *)((&local_17c[0] + ((var57 * 4) + 92))) = (var53 + var76);
*(int *)((&local_17c[0] + ((var57 * 4) + 96))) = (var54 + var77);
*(int *)((&local_17c[0] + ((var57 * 4) + 100))) = (var51 + var78);
*(int *)((&local_17c[0] + ((var57 * 4) + 104))) = (var52 + var79);
*(int *)((&local_17c[0] + ((var57 * 4) + 108))) = (var53 + var80);
*(int *)((&local_17c[0] + ((var57 * 4) + 112))) = (var54 + var81);
*(int *)((&local_17c[0] + ((var57 * 4) + 116))) = (var51 + var82);
*(int *)((&local_17c[0] + ((var57 * 4) + 120))) = (var52 + var83);
*(int *)((&local_17c[0] + ((var57 * 4) + 124))) = (var53 + var84);
*(int *)((&local_17c[0] + ((var57 * 4) + 128))) = (var54 + var85);
var57 = (var57 + 32);
var51 = (var51 + var86);
var52 = (var52 + var87);
var53 = (var53 + var88);
var54 = (var54 + var89);
var50 = (var50 - 4);
var49 = var57;
var39 = var50;
var43 = var51;
var44 = var52;
var45 = var53;
var46 = var54;
} while ((var50 != 0));
L_12d8: ;
if ((var42 != 0)) {
var153 = (long)(((&local_17c[0] + 20) + (var49 * 4)));
var154 = (var42 << 5);
var156 = 0;
var157 = 4;
var158 = 4;
var159 = 4;
var160 = 4;
var161 = 8;
var162 = 8;
var163 = 8;
var164 = 8;
do {
*(int *)((var153 + var156 - 0x10)) = var43;
*(int *)((var153 + var156 - 0xc)) = var44;
*(int *)((var153 + var156 - 0x8)) = var45;
*(int *)((var153 + var156 - 0x4)) = var46;
*(int *)((var153 + var156)) = (var43 + var157);
*(int *)((var153 + var156 + 0x4)) = (var44 + var158);
*(int *)((var153 + var156 + 0x8)) = (var45 + var159);
*(int *)((var153 + var156 + 0xc)) = (var46 + var160);
var43 = (var43 + var161);
var44 = (var44 + var162);
var45 = (var45 + var163);
var46 = (var46 + var164);
var156 = (var156 + 32);
} while ((var154 != var156));
}
var28 = (long)var33;
if ((var32 == var29)) {
goto L_133d;
}
L_1330: ;
*(int *)((&local_17c[0] + ((var32 * 4) + 4))) = var32;
var174 = (var32 + 1);
var32 = var174;
if ((var29 != var174)) {
goto L_1330;
}
L_133d: ;
var176 = var0;
if ((((unsigned long)((unsigned int)(arg1)) == 0) | ((long)(arg1) < 0))) {
// x86-64 epilogue: restore callee registers
return (unsigned int)(*(int *)((&local_17c[0] + (((long)((int)(((unsigned long)((unsigned int)((arg1 + (arg1 * 8)))) + var176))) * 4) + 4))));
}
var177 = (unsigned long)((unsigned int)((var0 + 1)));
var179 = (unsigned long)((unsigned int)((arg1 + 1)));
local_180 = (var177 - 2);
var181 = (var177 - 1);
local_188 = (long)((((&local_17c[0] + 20) + (var177 * 4)) - 20));
local_190 = (var177 + 8);
local_1b8 = var181;
var184 = (var181 & -4);
local_198 = var184;
var185 = (var184 + 1);
local_1a0 = var185;
var187 = (long)((&local_17c[0] + 4));
var188 = 10;
var189 = 9;
var191 = 0;
var192 = -1;
var193 = -1;
var194 = -1;
var195 = -1;
var196 = 1;
var197 = 1;
var198 = 1;
var199 = 1;
local_1a8 = var0;
local_1e0 = var28;
var200 = 1;
goto L_13ed;
L_13d0: ;
i = (var200 + 1);
var191 = (var191 + 1);
var187 = (var187 + 36);
var188 = (var188 + 9);
var189 = (var189 + 9);
var200 = (unsigned long)((unsigned int)(i));
var176 = var0;
if ((i == var179)) {
// x86-64 epilogue: restore callee registers
return (unsigned int)(*(int *)((&local_17c[0] + (((long)((int)(((unsigned long)((unsigned int)((arg1 + (arg1 * 8)))) + var176))) * 4) + 4))));
}
L_13ed: ;
if ((((unsigned long)((unsigned int)(var0)) == 0) | ((long)((int)(var0)) < 0))) {
goto L_13d0;
}
var203 = (*(char *)((var200 + var28 - 0x1)) & 255);
var204 = 1;
if (((unsigned long)(local_1b8) < (unsigned long)(4))) {
goto L_15b0;
}
var207 = ((-(unsigned long)((unsigned int)((var191 + (var191 * 8))))) - 11);
var185 = (unsigned long)((unsigned int)(var207));
var208 = local_180;
if (((unsigned long)((unsigned long)((unsigned int)(var207))) < (unsigned long)((unsigned long)((unsigned int)(local_180))))) {
goto L_15b0;
}
var185 = ((unsigned long)(var208) >> 32);
if ((var185 != 0)) {
goto L_15b0;
}
var210 = var179;
var211 = (var191 + (var191 * 8));
local_1c0 = (local_190 + var211);
local_1c8 = (local_1b8 + var211);
var217 = (unsigned long)((unsigned int)(((var191 + (var191 * 8)) + 10)));
var218 = (long)((((&local_17c[0] + 20) + (var217 * 4)) - 16));
var220 = (local_188 + (var217 * 4));
local_1d8 = (long)((((&local_17c[0] + 20) + (var211 * 4)) - 12));
var222 = (long)((((&local_17c[0] + 20) + ((var211 + var177) * 4)) - 16));
local_1d0 = (long)((((&local_17c[0] + 20) + (var211 * 4)) + 20));
var225 = (long)((((&local_17c[0] + 20) + (local_1c0 * 4)) - 16));
local_1c0 = (long)((((&local_17c[0] + 20) + (var211 * 4)) - 16));
var229 = (long)((((&local_17c[0] + 20) + (local_1c8 * 4)) - 16));
local_1c8 = ((unsigned long)(var218) < (unsigned long)(var222));
local_1d8 = ((unsigned long)(local_1d8) < (unsigned long)(var220));
var231 = ((var222 & -256) | ((unsigned long)(var218) < (unsigned long)(var225)));
local_1d0 = ((unsigned long)(local_1d0) < (unsigned long)(var220));
var233 = ((unsigned long)(var218) < (unsigned long)(var229));
var235 = ((unsigned long)(local_1c0) < (unsigned long)(var220));
var185 = ((var229 & -256) | ((unsigned char)(local_1d8) & 255));
if (((unsigned long)((unsigned char)(((unsigned char)(local_1c8) & (var185 & 255)))) == 0)) {
var0 = local_1a8;
if (((unsigned long)((unsigned char)(((var231 & 255) & (unsigned char)(local_1d0)))) != 0)) {
goto L_15a3;
}
var28 = local_1e0;
var179 = var210;
if (((unsigned long)((unsigned char)(((var233 & 255) & (var235 & 255)))) != 0)) {
goto L_15b0;
}
var255 = 0;
var256 = local_198;
do {
var269 = __unknown(0);
var270 = __unknown(0);
var285 = (*(int *)((var187 + var255 * 4)) + (((unsigned int)((unsigned short)(var269)) | ((unsigned int)((unsigned short)(var269)) << 16)) & var196));
var286 = (*(int *)((var187 + var255 * 4 + 0x4)) + (((unsigned int)((unsigned short)((((unsigned int)(var269) >> 16) & 0xffff))) | ((unsigned int)((unsigned short)((((unsigned int)(var269) >> 16) & 0xffff))) << 16)) & var197));
var287 = (*(int *)((var187 + var255 * 4 + 0x8)) + (((unsigned int)((unsigned short)(var270)) | ((unsigned int)((unsigned short)(var270)) << 16)) & var198));
var288 = (*(int *)((var187 + var255 * 4 + 0xc)) + (((unsigned int)((unsigned short)((((unsigned int)(var270) >> 16) & 0xffff))) | ((unsigned int)((unsigned short)((((unsigned int)(var270) >> 16) & 0xffff))) << 16)) & var199));
var290 = *(int *)((var187 + var255 * 4 + 0x4));
var291 = *(int *)((var187 + var255 * 4 + 0x8));
var292 = *(int *)((var187 + var255 * 4 + 0xc));
var293 = *(int *)((var187 + var255 * 4 + 0x10));
var295 = *(int *)((var187 + var255 * 4 + 0x24));
var296 = *(int *)((var187 + var255 * 4 + 0x28));
var297 = *(int *)((var187 + var255 * 4 + 0x2c));
var298 = *(int *)((var187 + var255 * 4 + 0x30));
var304 = (-(var295 < var290));
var305 = (-(var296 < var291));
var306 = (-(var297 < var292));
var307 = (-(var298 < var293));
var316 = (((~var304) & var290) | (var295 & var304));
var317 = (((~var305) & var291) | (var296 & var305));
var318 = (((~var306) & var292) | (var297 & var306));
var319 = (((~var307) & var293) | (var298 & var307));
var325 = (-(var316 < var285));
var326 = (-(var317 < var286));
var327 = (-(var318 < var287));
var328 = (-(var319 < var288));
var185 = (unsigned long)((unsigned int)((var188 + var255)));
*(int *)((&local_17c[0] + ((var185 * 4) + 4))) = (((~var325) & var285) | ((var316 - var192) & var325));
*(int *)((&local_17c[0] + ((var185 * 4) + 8))) = (((~var326) & var286) | ((var317 - var193) & var326));
*(int *)((&local_17c[0] + ((var185 * 4) + 12))) = (((~var327) & var287) | ((var318 - var194) & var327));
*(int *)((&local_17c[0] + ((var185 * 4) + 16))) = (((~var328) & var288) | ((var319 - var195) & var328));
var255 = (var255 + 4);
} while ((var256 != var255));
var204 = local_1a0;
if ((local_1b8 != var256)) {
goto L_15b0;
}
goto L_13d0;
}
var0 = local_1a8;
L_15a3: ;
var28 = local_1e0;
var179 = var210;
L_15b0: ;
var350 = (unsigned long)((unsigned int)(*(int *)((var187 + var204 * 4))));
var351 = (((unsigned char)((var203 & 255)) != (unsigned char)(*(char *)(((long)arg2 + var204 - 0x1)))) + *(int *)((var187 + var204 * 4 - 0x4)));
var353 = (unsigned long)((unsigned int)(*(int *)((var187 + var204 * 4 + 0x20))));
var354 = (((long)((int)(var353)) < (long)((int)(var350))) ? var353 : var350);
var357 = (unsigned long)((unsigned int)((var189 + var204)));
*(int *)((&local_17c[0] + ((var357 * 4) + 4))) = ((((unsigned int)(var351) == (unsigned int)(var354)) | (var351 < var354)) ? (unsigned long)((unsigned int)(var351)) : (unsigned long)((unsigned int)((var354 + 1))));
var358 = (var204 + 1);
var204 = var358;
var185 = var357;
if ((var177 != var358)) {
goto L_15b0;
}
var185 = var357;
goto L_13d0;
} hamming_distance pass 65 lines
// glaurung: hamming_distance @ 0x1610
int32_t hamming_distance(const uint8_t * arg0, const uint8_t * arg1, int32_t arg2) {
int distance;
int i;
long ret;
int var15;
int var22;
int var30;
int var38;
int var46;
int var54;
long var55;
long var8;
ret = 0xffffffff;
if (((unsigned long)((unsigned long)((unsigned int)(arg2))) <= (unsigned long)(8))) {
ret = 0xffffffff;
if ((arg0 == 0)) {
return ret;
}
ret = 0xffffffff;
if ((arg1 == 0)) {
return ret;
}
if (((unsigned long)((unsigned int)(arg2)) == 0)) {
return 0;
}
var8 = ((unsigned char)((*(char *)(((long)arg0)) & 255)) != (unsigned char)(*(char *)(((long)arg1))));
ret = var8;
if (((unsigned long)((unsigned int)(arg2)) == 1)) {
return ret;
}
var15 = (var8 + ((unsigned char)((*(char *)(((long)arg0 + 0x1)) & 255)) != (unsigned char)(*(char *)(((long)arg1 + 0x1)))));
ret = (unsigned long)((unsigned int)(var15));
if (((unsigned long)((unsigned int)(arg2)) == 2)) {
return ret;
}
var22 = ((unsigned int)(var15) + ((unsigned char)((*(char *)(((long)arg0 + 0x2)) & 255)) != (unsigned char)(*(char *)(((long)arg1 + 0x2)))));
ret = (unsigned long)((unsigned int)(var22));
if (((unsigned long)((unsigned int)(arg2)) == 3)) {
return ret;
}
var30 = ((unsigned int)(var22) + ((unsigned char)((*(char *)(((long)arg0 + 0x3)) & 255)) != (unsigned char)(*(char *)(((long)arg1 + 0x3)))));
ret = (unsigned long)((unsigned int)(var30));
if (((unsigned long)((unsigned int)(arg2)) == 4)) {
return ret;
}
var38 = ((unsigned int)(var30) + ((unsigned char)((*(char *)(((long)arg0 + 0x4)) & 255)) != (unsigned char)(*(char *)(((long)arg1 + 0x4)))));
ret = (unsigned long)((unsigned int)(var38));
if (((unsigned long)((unsigned int)(arg2)) == 5)) {
return ret;
}
var46 = ((unsigned int)(var38) + ((unsigned char)((*(char *)(((long)arg0 + 0x5)) & 255)) != (unsigned char)(*(char *)(((long)arg1 + 0x5)))));
ret = (unsigned long)((unsigned int)(var46));
if (((unsigned long)((unsigned int)(arg2)) == 6)) {
return ret;
}
var54 = ((unsigned int)(var46) + ((unsigned char)((*(char *)(((long)arg0 + 0x6)) & 255)) != (unsigned char)(*(char *)(((long)arg1 + 0x6)))));
var55 = (unsigned long)((unsigned int)(var54));
ret = (unsigned long)((unsigned int)(var54));
if (((unsigned long)((unsigned int)(arg2)) != 7)) {
ret = (unsigned long)((unsigned int)((var55 + ((unsigned char)((*(char *)(((long)arg0 + 0x7)) & 255)) != (unsigned char)(*(char *)(((long)arg1 + 0x7)))))));
}
}
return ret;
} gcc -O0
2/2edit_distance pass 52 lines
// glaurung: edit_distance @ 0x1119
int32_t edit_distance(const uint8_t * arg0, int32_t arg1, const uint8_t * arg2, int32_t arg3) {
extern __attribute__((noreturn)) void __stack_chk_fail(void);
int i;
int j;
int cost;
int best;
int insertion;
int substitution;
unsigned char local_150[324];
long local_8;
long ret;
long var34;
long var63;
// x86-64 prologue: save rbp, frame 400 bytes
local_8 = (long)(0x28);
if (((((((arg0 == 0) || (arg2 == 0)) || ((long)(arg1) < 0)) || ((long)(arg3) < 0)) || ((((unsigned long)((unsigned int)(arg1)) == 8) | ((long)(arg1) < 8)) == 0)) || (((unsigned long)((unsigned int)(arg3)) != 8) && (8 <= (long)(arg3))))) {
ret = 0xffffffff;
} else {
for (i = 0; ((((unsigned int)(i) == (unsigned int)(arg1)) | (i < arg1)) != 0); i++) {
*(int *)((&local_150[0] + ((long)((int)(((unsigned long)((unsigned int)(((unsigned long)((unsigned int)(i)) << 3))) + (unsigned long)((unsigned int)(i))))) * 4))) = i;
}
for (j = 0; ((((unsigned int)(j) == (unsigned int)(arg3)) | (j < arg3)) != 0); j++) {
*(int *)((&local_150[0] + ((long)(j) * 4))) = j;
}
i = 1;
while (((((unsigned int)(i) == (unsigned int)(arg1)) | (i < arg1)) != 0)) {
for (j = 1; ((((unsigned int)(j) == (unsigned int)(arg3)) | (j < arg3)) != 0); j++) {
cost = ((unsigned char)(((unsigned int)((unsigned char)(arg0[((long)(i) - 1)])) & 255)) != (unsigned char)(((unsigned int)((unsigned char)(arg2[((long)(j) - 1)])) & 255)));
var34 = (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(i)) - 1)));
best = ((unsigned int)(*(int *)((&local_150[0] + ((long)((int)(((unsigned long)((unsigned int)(j)) + (unsigned long)((unsigned int)((var34 + (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(var34)) << 3))))))))) * 4)))) + 1);
insertion = ((unsigned int)(*(int *)((&local_150[0] + ((long)((int)(((unsigned long)((unsigned int)(((unsigned long)((unsigned int)(j)) - 1))) + (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(i)) + (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(i)) << 3))))))))) * 4)))) + 1);
var63 = (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(i)) - 1)));
substitution = ((unsigned int)(cost) + (unsigned int)(*(int *)((&local_150[0] + ((long)((int)(((unsigned long)((unsigned int)(((unsigned long)((unsigned int)(j)) - 1))) + (unsigned long)((unsigned int)((var63 + (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(var63)) << 3))))))))) * 4)))));
if ((insertion < best)) {
best = insertion;
}
if ((substitution < best)) {
best = substitution;
}
*(int *)((&local_150[0] + ((long)((int)(((unsigned long)((unsigned int)(j)) + (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(i)) + (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(i)) << 3))))))))) * 4))) = best;
}
i = (i + 1);
}
ret = (unsigned long)((unsigned int)(*(int *)((&local_150[0] + ((long)((int)(((unsigned long)((unsigned int)(arg3)) + (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(arg1)) + (unsigned long)((unsigned int)(((unsigned long)((unsigned int)(arg1)) << 3))))))))) * 4)))));
}
if ((local_8 != 0x28)) {
__stack_chk_fail();
}
// x86-64 epilogue: restore rbp
return ret;
} hamming_distance pass 30 lines
// glaurung: hamming_distance @ 0x13a8
int32_t hamming_distance(const uint8_t * arg0, const uint8_t * arg1, int32_t arg2) {
int distance;
int i;
// x86-64 prologue: save rbp
distance = 0;
if ((arg0 == 0)) {
// x86-64 epilogue: restore rbp
return 0xffffffff;
}
if ((arg1 == 0)) {
// x86-64 epilogue: restore rbp
return 0xffffffff;
}
if (((long)(arg2) < 0)) {
// x86-64 epilogue: restore rbp
return 0xffffffff;
}
if (((((unsigned long)((unsigned int)(arg2)) == 8) | ((long)(arg2) < 8)) == 0)) {
// x86-64 epilogue: restore rbp
return 0xffffffff;
}
for (i = 0; (i < arg2); i++) {
if (((unsigned char)(((unsigned int)((unsigned char)(arg0[i])) & 255)) != (unsigned char)(((unsigned int)((unsigned char)(arg1[i])) & 255)))) {
distance = (distance + 1);
}
}
// x86-64 epilogue: restore rbp
return (unsigned int)(distance);
} gcc -O2
2/2edit_distance pass 108 lines
// glaurung: edit_distance @ 0x1120
int32_t edit_distance(const uint8_t * arg0, int32_t arg1, const uint8_t * arg2, int32_t arg3) {
extern __attribute__((noreturn)) void __stack_chk_fail(void);
int j;
int best;
int i;
int insertion;
int substitution;
unsigned char local_188[324];
long local_40;
long ret;
long var10;
int var11;
long var15;
long var16;
long var17;
long var18;
long var2;
long var20;
long var21;
int var22;
long var25;
long var26;
long var3;
int var33;
int var34;
long var36;
int var37;
long var4;
long var5;
long var6;
long var7;
long var8;
long var9;
local_40 = (long)(0x28);
var2 = 0;
if ((arg0 == 0)) {
L_123d: ;
ret = 0xffffffff;
} else {
var3 = (long)arg2;
if ((arg2 == 0)) {
goto L_123d;
} else {
var4 = (unsigned long)((unsigned int)(arg3));
if (((unsigned long)(8) < (unsigned long)((unsigned long)((unsigned int)(arg3))))) {
goto L_123d;
} else {
var5 = (unsigned long)((unsigned int)(arg1));
if (((unsigned long)(8) < (unsigned long)((unsigned long)((unsigned int)(arg1))))) {
goto L_123d;
} else {
var6 = (long)(&local_188[0]);
var7 = (long)arg0;
var8 = var6;
var9 = var6;
var10 = var2;
do {
*(int *)((var8)) = var10;
var11 = (var10 + 1);
var8 = (var8 + 36);
var10 = (unsigned long)((unsigned int)(var11));
} while (((long)((int)(var11)) <= (long)((int)(var5))));
var15 = 0;
do {
*(int *)((var6 + var15 * 4)) = var15;
var16 = (var15 + 1);
var15 = var16;
} while (((long)((int)(var16)) <= (long)((int)(var4))));
if (((unsigned long)((unsigned int)(var5)) != 0)) {
var17 = (long)((&local_188[0] + 36));
var18 = (unsigned long)((unsigned int)((var5 + (var5 * 8))));
var20 = 0;
do {
var21 = var6;
if (((unsigned long)((unsigned int)(var4)) != 0)) {
var22 = (unsigned int)((unsigned char)(*(char *)((var7))));
j = 1;
do {
var25 = (unsigned long)((unsigned int)(*(int *)((var9 + j * 4))));
var26 = (unsigned long)((unsigned int)(*(int *)((var17 + j * 4 - 0x4))));
var33 = (((unsigned char)(*(char *)((var3 + j - 0x1))) != (unsigned char)((var22 & 255))) + *(int *)((var9 + j * 4 - 0x4)));
var34 = ((((unsigned int)(var25) == (unsigned int)(var26)) | ((long)((int)(var25)) < (long)((int)(var26)))) ? (unsigned long)((unsigned int)((var25 + 1))) : (unsigned long)((unsigned int)((var26 + 1))));
*(int *)((var17 + j * 4)) = (((((unsigned int)(var34) == (unsigned int)(var33)) | (var34 < var33)) == 0) ? (unsigned long)((unsigned int)(var33)) : var34);
var36 = ((unsigned long)((unsigned int)(j)) + 1);
j = var36;
var21 = (unsigned long)((unsigned int)(var33));
} while (((long)((int)(var36)) <= (long)((int)(var4))));
}
var37 = (var20 + 9);
var20 = (unsigned long)((unsigned int)(var37));
var17 = (var17 + 36);
var9 = (var9 + 36);
var7 = (var7 + 1);
var6 = var21;
} while (((unsigned int)(var37) != (unsigned int)(var18)));
}
ret = (unsigned long)((unsigned int)(*(int *)((&local_188[0] + ((long)((int)(((unsigned long)((unsigned int)((var5 + (var5 * 8)))) + var4))) * 4)))));
}
}
}
}
if ((local_40 != 0x28)) {
__stack_chk_fail();
}
// x86-64 epilogue: tear down frame
return ret;
} hamming_distance pass 35 lines
// glaurung: hamming_distance @ 0x1250
int32_t hamming_distance(const uint8_t * arg0, const uint8_t * arg1, int32_t arg2) {
int i;
int distance;
long t10;
long t11;
long var1;
long var8;
if ((arg0 == 0)) {
var1 = 0xffffffff;
return 0xffffffff;
}
if ((arg1 == 0)) {
var1 = 0xffffffff;
return 0xffffffff;
}
if (((unsigned long)(8) < (unsigned long)((unsigned long)((unsigned int)(arg2))))) {
var1 = 0xffffffff;
return 0xffffffff;
}
if (((unsigned long)((unsigned int)(arg2)) == 0)) {
return 0;
}
i = 0;
var8 = 0;
do {
t10 = *(char *)(((long)arg0 + i));
t11 = ((unsigned int)((unsigned char)(*(char *)(((long)arg1 + i)))) & 255);
i = (i + 1);
distance = (var8 + ((unsigned char)(t10) != (unsigned char)(t11)));
var8 = (unsigned long)((unsigned int)(distance));
var1 = (unsigned long)((unsigned int)(distance));
} while (((((unsigned int)(arg2) == (unsigned int)(i)) | (arg2 < i)) == 0));
return (unsigned int)(var1);
}