Skip to content

Instructions Substitution

Pascal Junod edited this page Nov 22, 2013 · 6 revisions

Description

The goal of this obfuscating technique consists in substituting standard binary operators (like addition, subtraction, boolean operators) by functionally equivalent, but more complicated sequences of instructions. When several equivalent instructions sequence are available, one is chosen at random.

This kind of obfuscation is rather straightforward and does not add a lot of security, as it can easily be removed by re-optimizing the generated code. However, provided the pseudo-random generator is seeded with different values, instructions substitutions bring diversity in the produced binary.

Currently, only operators on integers are available, as substituting operators on floating-point values bring rounding errors and unnecessary numerical inaccuracy.

Available Compiler Options

  • -mllvm -sub: activate instructions substitution
  • -mllvm -funcSUB="func1,func2,func3": if instructions substitution is activated, apply it only on functions func1, func2 and func3
  • -mllvm -perSUB=20: if instructions substitution is activated, apply it with a probability of 20% on each function

Implemented Techniques

For the moment, the following substitutions are available :

  • Addition
    • a = b - (-c)
%0 = load i32* %a, align 4
%1 = load i32* %b, align 4
%2 = sub i32 0, %1
%3 = sub nsw i32 %0, %2
  • a = -(-b + (-c))
%0 = load i32* %a, align 4
%1 = load i32* %b, align 4
%2 = sub i32 0, %0
%3 = sub i32 0, %1
%4 = add i32 %2, %3
%5 = sub nsw i32 0, %4
  • r = rand (); a = b + r; a = a + c; a = a - r
%0 = load i32* %a, align 4
%1 = load i32* %b, align 4
%2 = add i32 %0, 1107414009
%3 = add i32 %2, %1
%4 = sub nsw i32 %3, 1107414009
  • r = rand (); a = b - r; a = a + b; a = a + r
%0 = load i32* %a, align 4
%1 = load i32* %b, align 4
%2 = sub i32 %0, 1108523271
%3 = add i32 %2, %1
%4 = add nsw i32 %3, 1108523271
  • Subtraction
    • a = b + (-c)
%0 = load i32* %a, align 4
%1 = load i32* %b, align 4
%2 = sub i32 0, %1
%3 = add nsw i32 %0, %2
  • r = rand (); a = b + r; a = a - c; a = a - r
%0 = load i32* %a, align 4
%1 = load i32* %b, align 4
%2 = add i32 %0, 1571022666
%3 = sub i32 %2, %1
%4 = sub nsw i32 %3, 1571022666
  • r = rand (); a = b - r; a = a - c; a = a + r
%0 = load i32* %a, align 4
%1 = load i32* %b, align 4
%2 = sub i32 %0, 1057193181
%3 = sub i32 %2, %1
%4 = add nsw i32 %3, 1057193181
  • AND
    • a = b & c => a = (b ^ ~c) & b
%0 = load i32* %a, align 4
%1 = load i32* %b, align 4
%2 = xor i32 %1, -1
%3 = xor i32 %0, %2
%4 = and i32 %3, %0
  • OR
    • a = b | c => a = (b & c) | (b ^ c)
%0 = load i32* %a, align 4
%1 = load i32* %b, align 4
%2 = and i32 %0, %1
%3 = xor i32 %0, %1
%4 = or i32 %2, %3
  • XOR
    • a = a ^ b => a = (~a & b) | (a & ~b)
%0 = load i32* %a, align 4
%1 = load i32* %b, align 4
%2 = xor i32 %0, -1
%3 = and i32 %1, %2
%4 = xor i32 %1, -1
%5 = and i32 %0, %4
%6 = or i32 %3, %5
Clone this wiki locally