升级到Delphi 2007之后,为什么我的加密工作不起作用?

时间:2011-12-14 16:15:25

标签: delphi unicode delphi-2009 encryption

我最近从Delphi 2007中获取了一些代码并将其升级到Delphi 2009.这可能与也可能不相关。

但是当我在计算机上运行代码时,密码的解密不能正确解密。这是代码。

Seed := GenerateIntFromString('usercode');

// Check if a password already exists
if TableUser.FieldByName('PASSWORD').AsString <> '' then
begin
    EncodedPassword := TableUser.FieldByName('PASSWORD').AsString;
    DecodedPassword := EncryptDecrypt(EncodedPassword, Seed);
//etc.. And the function

function TLogonForm.EncryptDecrypt(Input: string; Seed: integer) : string;
var
i : integer;
Output : string;
begin
    RANDSEED := Seed;
    Output := '';
    for i := 1 to Length(Input) do
        Output := Output + Chr(Ord(Input[i]) XOR (RANDOM(254) + 1));
    Result := Output;
end;

所以如果我的用户代码是TD 我的密码是'JOEJOE'

加密密码为:Â?Âp?

解密的passowrd是:JìEJùE

它应该明显解密为JOEJOE。踢球者,如果我构建代码并将exe发送给另一个用户,它就会解密。这让我相信代码并没有什么问题,而是我的电脑有些异常。它可能是什么?


你可以对此表示不满,因为它可能与此无关。我只提到它,因为这是另一种情况,一台计算机上的工作正常,但另一台计算机却没有。

但是也有一种情况是在尝试设置过滤器时

TableUser2.Filter := FilterString;

它适用于我,但其他用户收到错误。

TableUser2:错误3106:在记录过滤器表达式中找到不支持的运算符。

即使我们使用相同的名称过滤相同的代码。也许是数据库问题?

3 个答案:

答案 0 :(得分:7)

尝试从Ansi到Unicode的端口,如下所示:

function TLogonForm.EncryptDecrypt(Input: AnsiString; Seed: integer) : AnsiString;
var
i : integer;
Output : AnsiString;
begin
    RANDSEED := Seed;
    Output := '';
    for i := 1 to Length(Input) do
        Output := Output + AnsiChar(Ord(Input[i]) XOR (RANDOM(254) + 1));
    Result := Output;
end;

我最好的猜测是,由于AnsiChar和UnicodeChar之间的区别,预期结果会有所不同。如果您设法生成一些无法存储在数据库的非unicode数据字段中的无效代码点,则可能会出现一些有趣的错误。

答案 1 :(得分:1)

您的问题是Delphi 2009的文本使用Unicode而不是ANSI。这是一个重大的突破性变化,需要大量的移植工作。您不仅需要处理代码中的编码问题,还需要升级您使用的任何第三方组件。

您可以恢复此特定功能的先前行为,如下所示:

function TLogonForm.EncryptDecrypt(Input: AnsiString; Seed: integer): AnsiString;
var
i : integer;
Output : AnsiString;
begin
    RANDSEED := Seed;
    Output := '';
    for i := 1 to Length(Input) do
        Output := Output + AnsiChar(Ord(Input[i]) XOR (RANDOM(254) + 1));
    Result := Output;
end;

在Delphi 2009中,string数据类型是UTF-16编码的字符串。以前版本的Delphi命名为AnsiString的ANSI编码字符串。同样地,Chr()生成一个16但WideChar的字符,但您想要一个AnsiChar,即8位ANSI字符类型。


但是,肯定会有许多其他问题需要解决。我建议你在Delphi and Unicode上阅读MarcoCantù的白皮书。在进一步使用端口之前,你真的应该掌握本文详述的问题。

答案 2 :(得分:0)

我要做的第一件事就是在函数的输入/输出周围进行一些记录。

听起来,TableUser.FieldByName(“Password”)中的值可能无法传递您在两种情况下的预期。

我要注意的另一件事是与两台机器一起使用的数据库排序规则。我假设你的两个测试用例之间的底层数据库是不同的;或者,至少,连接字符串信息具有不同的整理值。这肯定会摒弃解密。