• delphi key解密转c# 解决string 不可变长度问题


    遇见问题:

    delphi的解密需要在c#里面实现

    方法一:delphi编写delphi dll组件,c#里面调用
    方法二:c#重写delphi的代码进行解析


    方法一:

    delphi部分代码:

    library Project2;
    
    { Important note about DLL memory management: ShareMem must be the
      first unit in your library's USES clause AND your project's (select
      Project-View Source) USES clause if your DLL exports any procedures or
      functions that pass strings as parameters or function results. This
      applies to all strings passed to and from your DLL--even those that
      are nested in records and classes. ShareMem is the interface unit to
      the BORLNDMM.DLL shared memory manager, which must be deployed along
      with your DLL. To avoid using BORLNDMM.DLL, pass string information
      using PChar or ShortString parameters. }
    
    uses
      SysUtils,
      Classes;
    
    
    
    function UncrypStr(Src, Key: String): string;//字符串解密函数
    //对字符串解密(Src:源 Key:密匙)
    var KeyLen :Integer;
        KeyPos :Integer;
        offset :Integer;
        dest :string;
        SrcPos :Integer;
        SrcAsc :Integer;
        TmpSrcAsc :Integer;
    begin
       KeyLen:=Length(Key);
       if KeyLen = 0 then key:='delphi';
       KeyPos:=0;
       offset:=StrToInt('$'+ copy(src,1,2));
       SrcPos:=3;
       repeat
          SrcAsc:=StrToInt('$'+ copy(src,SrcPos,2));
          if KeyPos < KeyLen
          Then KeyPos := KeyPos + 1
          else KeyPos := 1;
          TmpSrcAsc := SrcAsc xor Ord(Key[KeyPos]);
          if TmpSrcAsc <= offset
          then TmpSrcAsc := 255 + TmpSrcAsc - offset
          else TmpSrcAsc := TmpSrcAsc - offset;
          dest:=dest + chr(TmpSrcAsc);
          offset:=srcAsc;
          SrcPos:=SrcPos + 2;
       until SrcPos >= Length(Src);
       Result:=Dest;
    end;
      
    function filesinfo(files:string): string;stdcall;
    //var
      //t:TStringlist;
      //strs:string;
      //strsss:string;
    begin
        //strs:=StrPas(files);
         //t := TStringlist.Create;
          //t.LoadFromFile(strs);
          //strsss := StringReplace(UncrypStr(t.Strings[0], 'Cernet@4206'), ' ', '', [rfReplaceAll]);
           Result:=files;
    end;
    function Check23(AA:string):Pchar;stdcall;
    var
       t:TStringlist;
       strs:string;
       begin
         t := TStringlist.Create;
         t.LoadFromFile(pchar(AA));
         strs := StringReplace(UncrypStr(t.Strings[0], 'Cernet@4206'), ' ', '', [rfReplaceAll]);
       result:=pchar(strs);
       end ;
    
    exports
        Check23;
    begin
    end.
    
    
    

    c# 调用 (如果数据量小还可以读出) 这里 的dll组建是x86的 需要把debug改成x86运行

     [DllImport(@"D:
    wasdllsProject2.dll", EntryPoint = "Check23")]
    
            static extern IntPtr Check23(string sx);
    
        string ss = Marshal.PtrToStringAnsi(Check23("C:\Users\忧郁的小学生\Desktop\997.azjx"));
                if (string.IsNullOrEmpty(ss)) {
                    Console.WriteLine("xss");
                }
    

    方法二:c# 重写 (刚开始用string是不可变长度,每次追加相当于开辟新的空间了,cpu占用过大,最后使用stringbuffer里面可变的)

     public string UncrypStr(string src="",string key="") {
                int KeyLen = key.Length;
                 src = src.Replace("
    ", "");
                src = src.Replace("
    ", "");
                if (KeyLen==0) {
                    key = "delphi";
                }
                int KeyPos= 0;
                int SrcAsc = 0;
                StringBuilder ps = new StringBuilder();
                string dest = "";
                int ks = 0;
                //16进制转换位10进制 delph 从起始位开始 c# 字节数组 从0开始
                string xs = src.Substring(0, 2);
                int offset = Convert.ToInt32(xs, 16);
                int SrcPos= 2;
                int TmpSrcAsc = 0;
                char[] chars = key.ToCharArray();
                while (SrcPos < (int)src.Length) {
                    //截取字符串
                    string tx = src.Substring(SrcPos, 2);
                    //转换为16进制 将10进制转换为16进制
                  SrcAsc = Convert.ToInt32(tx, 16);
                    //判断解密密钥的起始
                    if (KeyPos < KeyLen)
                    {
                        KeyPos++;
                    }
                    else {
                        KeyPos = 1;
                    }
                    //分割成单个字符
                   
                    char s = chars[KeyPos-1];
                    //byte[] array = System.Text.Encoding.ASCII.GetBytes(chars);
    
                    TmpSrcAsc = SrcAsc ^ (int)s; 
                    if (TmpSrcAsc <= offset)
                    {
                        TmpSrcAsc = 255 + TmpSrcAsc - offset;
                    }
                    else
                    {
                        TmpSrcAsc= TmpSrcAsc - offset;
                    }
                    //这里十进制直接转换ascii表不行,待转换为16进制
                    //char chs = (char)TmpSrcAsc;
                    string chs = TmpSrcAsc.ToString("X");
    
                    ps.Append(chs);
    
                    offset = SrcAsc;
                    SrcPos= SrcPos + 2;
                }
    
                return ps.ToString();
    
            }
            /// <summary>
            /// ascii码转换为中文
            /// </summary>
            /// <param name="textAscii"></param>
            /// <returns></returns>
            public string getstring(string textAscii="")
            {
    
                string textStr = string.Empty;
    
                int k = 0;//字节移动偏移量
    
                byte[] buffer = new byte[textAscii.Length / 2];//存储变量的字节
    
                for (int i = 0; i < textAscii.Length / 2; i++)
    
                {
    
                    //每两位合并成为一个字节
    
                    buffer[i] = byte.Parse(textAscii.Substring(k, 2),System.Globalization.NumberStyles.HexNumber);
    
                    k = k + 2;
    
                }
    
                //将字节转化成汉字
    
                textStr = Encoding.Default.GetString(buffer);
    
                return textStr;
    
            }
    
  • 相关阅读:
    LeetCode 81 Search in Rotated Sorted Array II(循环有序数组中的查找问题)
    LeetCode 80 Remove Duplicates from Sorted Array II(移除数组中出现两次以上的元素)
    LeetCode 79 Word Search(单词查找)
    LeetCode 78 Subsets (所有子集)
    LeetCode 77 Combinations(排列组合)
    LeetCode 50 Pow(x, n) (实现幂运算)
    LeetCode 49 Group Anagrams(字符串分组)
    LeetCode 48 Rotate Image(2D图像旋转问题)
    LeetCode 47 Permutations II(全排列)
    LeetCode 46 Permutations(全排列问题)
  • 原文地址:https://www.cnblogs.com/mengluo/p/11927553.html
Copyright © 2020-2023  润新知