如何在Delphi EXE中隐藏或隐藏字符串?

Ben*_*eny 14 delphi string obfuscation

我目前正在Delphi中开发一个应用程序,我必须在源代码中隐藏(混淆)一个字符串str := 'Example String'.
为什么?因为如果我在文本编辑器中打开EXE并搜索Example String我会在第二个中找到该字符串...

我尝试使用基本的HEX转录,#$65#$78#$61#$6d#$70#$6c#$65但它在编译时被清楚地重新转录.
我找了包装工,但这不是最好的解决方案(PECompact可以被检测为误报恶意软件,UPX太容易de-UPX,......).我希望在我的内部代码中有一个想法......

有人会让我走上正确的道路.

And*_*and 20

一种非常简单的方法是存储由ROT13方法模糊的字符串.

procedure ROT13(var Str: string);
const
  OrdBigA = Ord('A');
  OrdBigZ = Ord('Z');
  OrdSmlA = Ord('a');
  OrdSmlZ = Ord('z');
var
  i, o: integer;
begin
  for i := 1 to length(Str) do
  begin
    o := Ord(Str[i]);
    if InRange(o, OrdBigA, OrdBigZ) then
      Str[i] := Chr(OrdBigA + (o - OrdBigA + 13) mod 26)
    else if InRange(o, OrdSmlA, OrdSmlZ) then
      Str[i] := Chr(OrdSmlA + (o - OrdSmlA + 13) mod 26);
  end;
end;

function ROT13fun(const Str: string): string;
begin
  result := Str;
  ROT13(result);
end;

const
  ObfuscatedString = 'Guvf vf n frperg zrffntr.';

procedure TForm4.FormCreate(Sender: TObject);
begin
  ShowMessage(ROT13fun(ObfuscatedString));
end;
Run Code Online (Sandbox Code Playgroud)

采用Caesar切片机或Vigenère切片机稍微复杂一点.

要获取要在源代码中使用的模糊字符串,您可以使用像我自己的Rejbrand Text EditorWolfram | Alpha这样的体面文本编辑.

更新

ROT13很容易破译,但它可能对你的情况来说已经足够了,这取决于它的外观!至少在二进制文件中识别字符串会变得非常困难.获取字符串需要花费一些精力.(毕竟,日常用户甚至不会在十六进制编辑器/文本编辑器中查看二进制文件!)Caesar密码是ROT13密码的一个非常简单的概括,并且也很容易被破译.实际上,只有25种不同的"密码".在V @ genere加密是远远棘手,并采取了一些非常认真努力破解(特别是因为你不知道准确哪里二进制字符串是).

作为一个例子,下面我给出了一个使用Vigenèrecihper进行混淆的字符串:

Xlc tsrgcdk sj'vrivem'ww cei sd kli acirivqhfriw cw qsbsir tfmjmgw,rrh biimrk hyi pygk gilhlvc mf ws,wk leq rpws pvgsqc fj agrvwtvcou mrrsiiwx we izcfp-hew cmji,rpxlmixl ml r piqg xigfbzgep zrrkyyuv.Mlrvih,hyi qmrvvr qctmixw vbtpmwkw ilsikc qclvgiq ks wsqy er soxirr klex hyi ilhzvi cbmmvslavrx mt xli Srvxl wj irboekivcr.先生hymw qstxmsl,ai uwcp mljvwxmeoki xfs tlcqwtep zojmw mt xli seivkw tsrgcdk.

当然可以扩展密码以处理数字和特殊字符,包括空格.它也可以混合大写字母和小写字母.那么解密会非常困难(虽然可能).如果密码是已知单词,则可能更容易解密,这可以在字典中找到.如果它不是一个词,它会更安全.

上面的文本使用您可以在足够大的字典中找到的单词进行模糊处理.使用无意义的字符串作为密码对下面的文本进行模糊处理:

Miwzvjfy m vjsy-tombox zguol ap ahqovz d uwk sbze w conz pe biusvth pagh h njsx.Io puvyeq,fl cjsx xic vmovdq zappzjvz,vnjnatl frcb vy dtmd vhxkt fto babtf davf.Uuxlhqb,khk aa dbn eumsuzq,auk saed vlpnbuuo ywlemz ue pnyl ttmxv.Pa ghof,fl cjsx kmbbzk atmd wv sfjtmxcl rtfysk cb yuta md jsy.Sqf nql njsx ly vs ilusrn o gok uxwupagupaz u.

最后,下面的文本以相同的方式进行模糊处理,但是 - 此外 - 所有空格和特殊字符都已从字符串中删除:

cishkclruervutzgnyarkgzjsaqgsrzvmmrzweolpcnvbkxrvdnqrlurhpmhfaxsuoqncxgzqegnqmngaryfbgozpcgrkgzrrybybmouyzbbkoucbnrnsxkmcbywpllxhkoobmzoydrfvrkhpvsavmzocwjflouboymlotjcnqrirgucdrftllladcwtmnkqehjpmnafoobyvkvdaancbzeokdnsotkkawvanjkryculluyaoklpnojfnqrlatypznpalzocjunuxzdbnzntpqulplekxhrshpttjqyculkkjyxhxgxdozruwlbtkyrsuumkgslbyunabbkryfupvnafobhuoyyvqjlzgzpomc

我挑战你破译这三个文本.如果有人成功破译最后一个,我保证给这个人100瑞典克朗(100瑞典克朗)!

但是,Warren P仍然是对的:如果你真的需要高安全性,即使是专家也无法破译,那么你应该去进行一些真正的加密.

更新

根据Warren P的要求,我使用以下代码加密/解密Vigenère:

const
  OrdBigA = Ord('A');
  OrdBigZ = Ord('Z');
  OrdSmlA = Ord('a');
  OrdSmlZ = Ord('z');

function imod(const x: integer; const y: integer): integer;
begin
  if x >= 0 then
    imod := x - floor(x/y) * y
  else
    imod := x + ceil(-x/y) * y;
end;

procedure Vigenère(var Str: string; const Key: string);
var
  n, i, o: integer;
  KeyChrs: TBytes;
begin

  n := length(Key);
  SetLength(KeyChrs, n);
  for i := 1 to n do
    if InRange(ord(Key[i]), OrdBigA, OrdBigZ) then
      KeyChrs[i - 1] := Ord(Key[i]) - OrdBigA
    else
      raise Exception.Create('Invalid character in Vigenère key.');

  for i := 1 to length(Str) do
  begin
    o := Ord(Str[i]);
    if InRange(o, OrdBigA, OrdBigZ) then
      Str[i] := Chr(OrdBigA + imod((o - OrdBigA + KeyChrs[(i-1) mod n]), 26))
    else if InRange(o, OrdSmlA, OrdSmlZ) then
      Str[i] := Chr(OrdSmlA + imod((o - OrdSmlA + KeyChrs[(i-1) mod n]), 26));
  end;

end;

function Vigenèref(const Str: string; const Key: string): string;
begin
  result := Str;
  Vigenère(result, Key);
end;

procedure VigenèreD(var Str: string; const Key: string);
var
  n, i, o: integer;
  KeyChrs: TBytes;
begin

  n := length(Key);
  SetLength(KeyChrs, n);
  for i := 1 to n do
    if InRange(ord(Key[i]), OrdBigA, OrdBigZ) then
      KeyChrs[i - 1] := Ord(Key[i]) - OrdBigA
    else
      raise Exception.Create('Invalid character in Vigenère key.');

  for i := 1 to length(Str) do
  begin
    o := Ord(Str[i]);
    if InRange(o, OrdBigA, OrdBigZ) then
      Str[i] := Chr(OrdBigA + imod((o - OrdBigA - KeyChrs[(i-1) mod n]), 26))
    else if InRange(o, OrdSmlA, OrdSmlZ) then
      Str[i] := Chr(OrdSmlA + imod((o - OrdSmlA - KeyChrs[(i-1) mod n]), 26));
  end;

end;

function VigenèreDf(const Str: string; const Key: string): string;
begin
  result := Str;
  VigenèreD(result, Key);
end;
Run Code Online (Sandbox Code Playgroud)

  • +1将法语è重音符号放入Delphi函数名称.请在Delphi 7中尝试一下.:-) (4认同)
  • @Warren P:然后你还没有看过我的'Möbius`功能! (2认同)