Bibliothèque: Bibliothèque de fonctions de hachage et de conversions vers d'autres systèmes numériques

 

Bibliothèque de fonctions de hachage et de conversions vers d'autres systèmes numériques:

La bibliothèque contient des algorithmes de fonctions de hachage à usage général : adler32, CRC-32, MaHash8v64. Elle contient également des fonctions permettant de convertir une représentation décimale en chaîne de caractères dans le système de base et vice versa.

Author: Aleksandr Chugunov

 

Bonjour !

La tâche consiste à suivre les moments de changement d'un ensemble de collections d'objets complexes. Je peux convertir un objet et une collection en une chaîne de caractères, ce qui représente environ 2000 caractères par collection. Pouvez-vous me dire quelle fonction de la bibliothèque sera la plus correcte pour obtenir une représentation courte d'une chaîne aussi longue?

Документация по MQL5: Основы языка / Типы данных / Тип string
Документация по MQL5: Основы языка / Типы данных / Тип string
  • www.mql5.com
Тип string предназначен для хранения текстовых строк. Текстовая строка представляет собой последовательность символов в формате Unicode с завершающим нулем на конце. string-переменной может быть назначена строковая константа. Строковая константа представляет собой последовательность символов Unicode, заключенную в двойные кавычки: "Это...
 
Nikolai Karetnikov:

Bonjour !

La tâche consiste à suivre les moments de changement d'un ensemble de collections d'objets complexes. Je peux convertir un objet et une collection en une chaîne de caractères, ce qui représente environ 2000 caractères par collection. Pouvez-vous me dire quelle fonction de la bibliothèque sera la plus correcte pour obtenir une représentation courte d'une chaîne aussi longue?

CryptEncode/Decode et choisissez les méthodes HASH_xxx.

vous pouvez même ZIP :-) un texte normal de 2000 caractères imprimés ne représente qu'un maigre 200-300 octets, il peut tenir dans 4 long`es.

 

ErreurCryptDecode(CRYPT_BASE64

int OnInit()
{
   string text="";
   string res="";
   string key="fuyTkH3cd63K9Htrl2xdFgjerPjmla8h";

   text="indicator_chart_window";
   if(!CryptEncodeA(text,key,res))
      Print("Error: Encode:",GetLastError());

   Print(res);

   text="vj9jDk+GxxB4W1zQc4/rC4OPvttMcgcF5ZFVC7m7l50=";
   if(!CryptDecodeA(text,key,res))
      Print("Error: Decode:",GetLastError());

   Print(res);
   return(INIT_SUCCEEDED);
}

//------------------------------------------------------------------
bool CryptEncodeA(string InputText,string key,string &Output) {
   uchar scr[];
   uchar dst[];
   uchar res[];
   uchar key_aes256[];
   uchar key_base64[];
   StringToCharArray(InputText,scr);
   StringToCharArray(key,key_aes256);
   if(CryptEncode(CRYPT_AES256,scr,key_aes256,dst)==0) return(false);
   if(CryptEncode(CRYPT_BASE64,dst,key_base64,res)==0) return(false);
   Output = CharArrayToString(res);
   return(true);
}
//--
bool CryptDecodeA(string InputText,string key,string &Output) {
   uchar scr[];
   uchar dst[];
   uchar res[];
   uchar key_base64[];
   uchar key_aes256[];
   StringToCharArray(InputText,scr);
   StringToCharArray(key,key_aes256);
   if(CryptDecode(CRYPT_BASE64,scr,key_base64,dst)==0) return(false);
   if(CryptDecode(CRYPT_AES256,dst,key_aes256,res)==0) return(false);
   Output = CharArrayToString(res);
   return(true);
}

---

La fonction CryptEncodeA crée une chaîne de caractères queCryptDecodeA ne peut pas décrypter et donne une erreur dans mt4 : "4029", dans mt5 : "4006". Le terminal a chiffré ce qu'il ne peut pas déchiffrer lui-même.

Ligne du journal : vj9jDk+GxxB4W1zQc4/rC4OPvttMcgcF5ZFVC7m7l50=

Si vous supprimez le dernier "="-, le décryptage s'effectue et il n'y a pas d'erreur.

En même temps, php décode normalement et correctement :

$secret_key = 'fuyTkH3cd63K9Htrl2xdFgjerPjmla8h';

$s = "indicator_chart_window";
$res = base64_encode(openssl_encrypt($s,"AES-256-ECB",$secret_key,OPENSSL_RAW_DATA));
echo $res.'<br>';

$s= "vj9jDk+GxxB4W1zQc4/rC54fEtkLAsAONkyeprqmMlw=";
$res = openssl_decrypt(base64_decode($s),"AES-256-ECB",$secret_key,OPENSSL_ZERO_PADDING|OPENSSL_RAW_DATA);
echo $res;

---

Encryptez la même chaîne sur le serveur : "indicator_chart_window".

Obtenez le résultat :"vj9jDk+GxxB4W1zQc4/rC54fEtkLAsAONkyeprqmMlw=""

Nous insérons cette ligne dans le code mql et nous obtenons à nouveau une erreur - supprimez le dernier "=" et tout fonctionne correctement.

---

J'ai mis une clé de cryptage aléatoire, sur le serveur la chaîne est : "8CpXr3OlVhGs41syHA0+HqZKnatswQjRWn2fKYN4qN4=="

J'ai inséré la chaîne dans le code mql - erreur, j'aienlevé un "=" en n'en laissant qu'un - cela a bien fonctionné (quelle était la clé qui créait une chaîne avec deux égalités - je n'ai pas pu la reproduire).

J'aimerais avoir une réponse, peut-être que je fais quelque chose de mal !

P.S. J'ai joint tous les codes, quel pourrait être le problème ?
 

La fonction StringToArray capture la terminaison zéro si vous ne spécifiez pas la longueur de la chaîne (historiquement)

Par conséquent, dans la fonction CryptDecodeA, vous devez utiliser

StringToCharArray(InputText,scr,0,StringLen(InputText));

au lieu de

StringToCharArray(InputText,scr);
Документация по MQL5: Общие функции / CryptDecode
Документация по MQL5: Общие функции / CryptDecode
  • www.mql5.com
CryptDecode - Общие функции - Справочник MQL5 - Справочник по языку алгоритмического/автоматического трейдинга для MetaTrader 5
 
Ilyas:

La fonction StringToArray capture la terminaison zéro si vous ne spécifiez pas la longueur de la chaîne (historiquement)

Par conséquent, dans la fonction CryptDecodeA, il est nécessaire d'utiliser la fonction

au lieu de

@Ilyas

J'ai vérifié dans différentes variantes - tout fonctionne.

Un problèmesubsiste:

StringReplace(res,"\x00..\x1F",""); // Не помогает

Comment supprimer les caractères non imprimables ?

Merci de votre compréhension.

 
Vitaly Muzichenko:

@Ilyas

J'ai vérifié dans différentes variantes - tout fonctionne.

Un problèmesubsiste:

Comment supprimer les caractères non imprimables ?

Je vous remercie de votre attention.

Il n'y a pas de fonction dans MQL avec la fonctionnalité dont vous avez besoin

Il est plus facile de le faire avant de convertir le tableau en chaîne de caractères :

//+------------------------------------------------------------------+
//|ArrayToString.mq5 |
//| Copyright 2021, MetaQuotes Software Corp.
//|https ://www.mql5.com
//+------------------------------------------------------------------+
#property copyright "Copyright 2021, MetaQuotes Software Corp."
#property link      "https://www.mql5.com"
#property version   "1.00"
//+------------------------------------------------------------------+
//||
//+------------------------------------------------------------------+
template<typename TChar>
string ArrayToString(const TChar &input_array[],bool remove_non_printable=false,int start=0,int count=-1,int codepage=CP_ACP)
  {
   struct cvt
     {
      static string convert(const uchar &input_array[],int start=0,int count=-1,int codepage=CP_ACP) { return(CharArrayToString(input_array,start,count,codepage)); }
      static string convert(const short &input_array[],int start=0,int count=-1,int codepage=CP_ACP) { return(ShortArrayToString(input_array,start,count)); }      
     };
  
   int input_size =ArraySize(input_array);
//--- pas de données à convertir
   if(start>=input_size || count==0)
      return(NULL);
//--- fixer le paramètre de départ
   if(start<0)
      start=0;
//--- fixer le paramètre de comptage
   if(count<0 || count==WHOLE_ARRAY || (start+count)>input_size)
      count=input_size-start;
//--- convertir le tableau d'entrée tel quel
   if(!remove_non_printable)
      return(cvt::convert(input_array,start,count,codepage));
//--- supprimer les symboles non imprimables du tableau d'entrée
   TChar cvt_array[];
   int   cvt_size=0;

   if(!ArrayResize(cvt_array,input_size))
      return(NULL);

   for(int i=0,n=start; i<input_size; i++)
     {
      const TChar input_sym = input_array[n++];
      //--- vérifier si le résultat est négatif, le tableau d'entrée peut être signé
      if(input_sym>0 && input_sym<' ')
         continue;
      //--- le zéro est un terminateur
      if(input_sym==0)
         break;
      //--- copie du symbole d'entrée
      cvt_array[cvt_size++]=input_sym;
     }
//--- convertir un tableau nettoyé en chaîne de caractères
   return(cvt::convert(cvt_array,0,cvt_size));
  }
//+------------------------------------------------------------------+
//| Fonction de démarrage du programme de script|
//+------------------------------------------------------------------+
void OnStart()
  {
   uchar input_array_uc[]= { 1, 'T', 2, 'h', 3, 'e', 4, ' ', 5, 'q', 6, 'u', 7, 'i', 8, 'c', 9, 'k', 10, ' ', 11, 'b', 12, 'r', 13, 'o', 14, 'w', 15, 'n', 16, ' ', 15, 'f', 16, 'o', 17, 'x', 18, ' ', 19, 'j', 20, 'u',
                            21, 'm', 22, 'p', 23, 's', 24, ' ', 25, 'o', 26, 'v', 27, 'e', 28, 'r', 29, ' ', 30, 't', 31, 'h','e',' ','l','a','z','y',' ','d','o','g','.', 0, 'X', 'X', 'X', 'X', 'X', 'X' };
   short input_array_s []= { 1, 'T', 2, 'h', 3, 'e', 4, ' ', 5, 'q', 6, 'u', 7, 'i', 8, 'c', 9, 'k', 10, ' ', 11, 'b', 12, 'r', 13, 'o', 14, 'w', 15, 'n', 16, ' ', 15, 'f', 16, 'o', 17, 'x', 18, ' ', 19, 'j', 20, 'u',
                            21, 'm', 22, 'p', 23, 's', 24, ' ', 25, 'o', 26, 'v', 27, 'e', 28, 'r', 29, ' ', 30, 't', 31, 'h','e',' ','l','a','z','y',' ','d','o','g','.', 0, 'X', 'X', 'X', 'X', 'X', 'X' };

   Print("without removing non-printables");
   Print(ArrayToString(input_array_uc));
   Print(ArrayToString(input_array_s));

   Print("with removing non-printables");
   Print(ArrayToString(input_array_uc,true));
   Print(ArrayToString(input_array_s,true));
  }
//+------------------------------------------------------------------+