Dans MQL5, il y a toujours de la place pour un exploit ! ;) - page 8

 
tu mélanges de l'eau dans un seau.
Les pointeurs vers les variables, vers les fonctions, la prise d'adresse par référence sont tous des restrictions MQL.
Ce n'est même pas quelque chose qui n'est pas prévu par la syntaxe, c'est une interdiction de gérer la mémoire.
Même le pointeur void* n'est pas un pointeur au sens habituel du C.
Il s'agit d'un objet permettant de travailler avec les objets de classe pour éviter qu'ils ne soient copiés.
La même référence & n'est pas une prise d'adresse, mais un spécificateur permettant au compilateur de passer un objet sans le copier dans la pile.
Vous voulez écrire en syakh, écrire en syakh et importer des dll, c'est bien.

Si cela vous démange vraiment de vous y mettre et que vous n'avez pas de dll foregn, alors l'importation à partir d'une dll native n'est pas un gros péché, et votre produit MQL n'en perdra pas de sa valeur.

Pour ne pas faire d'histoires, vous pouvez, par exemple, utiliser un simple pointeur de 4 octets et importer memcpy pour travailler avec la mémoire à l'intérieur d'un processus terminal.

#import "msvcrt.dll"
int memcpy(short&,short&,int) ;
int memcpy(int&,int&,int) ;
int memcpy(double&,double&,int) ;
int memcpy(string& s,string& int) ;
#import

une sorte de classe d'enveloppe :

struct TPtr
{
int addr ;
TPtr():addr(0){}
TPtr(const TPtr& r):addr(r.addr){}
template<typename _T> TPtr operator =(_T& r) {
addr = memcpy(r,r,0) ;
renvoyer ceci ;
}
} ;


et d'un exemple d'utilisation :

chaîne de caractères sval = "123" ;
court bval = 123 ;
int ival = 123 ;
double dval = 123 ;

TPtr p = sval ;
int ptrs = p.addr ;
p = bval ;
int ptrb = p.addr ;
p = ival ;
int ptri = p.addr ;
p = dval ;
int ptrd = p.addr ;

De cette façon, vous pouvez manipuler la mémoire comme vous le souhaitez... Pas les habituels pointeurs C, mais quand même

En quoi cela peut-il être utile ?
Par exemple, vous pouvez utiliser la fonction d'importation GlobalAlloc, de sorte que vous ne devez pas utiliser de variables globales pour transférer des données entre les modules.
GlobalAlloc alloue au processus de la mémoire qui n'est pas associée à un tas ou à une statique interne virtuelle pour le travail d'un hibou ou d'un induit.
Vous pouvez y placer des tableaux de n'importe quelle taille et utiliser memcpy pour l'indexation.

Exemple d'importation :

#define HANDLE int
#define LPVOID int

#import "kernel32.dll"
HANDLE GlobalAlloc(uint flags, uint cnt) ;
LPVOID GlobalLock(HANDLE hmem) ;
int GlobalUnlock(HANDLE hmem) ;
HANDLE GlobalFree(HANDLE hmem) ;
#import "ntdll.dll".
// GetLastError existe déjà dans MT, donc à utiliser depuis WinAPI :
int RtlGetLastWin32Error() ;
#import


Un exemple d'utilisation :

// hibou N1, préparez votre tableau de taux

Taux MqlRates [123] ;
// on remplit ici
HANDLE memid = GlobalAlloc(GMEM_MOVEABLE, 123*sizeof(MqlRates)) ;
LPVOID ptr=GlobalLock(memid) ;
memcpy(ptr,rates[0].time, 123*sizeof(MqlRates)) ; // ici, pour compiler, on doit prototyper int memcpy(int&,const datetime&,int)
GlobalUnlock(memid) ;
// envoyer un descripteur de mémoire
EventChartCustom(CID, MY_SEND_DATA, memid, 0, "") ;

// hibou N2
void OnChartEvent(const int id, const long &lparam, const double &dparam, const string &sparam)
{
si( id == CHARTEVENT_CUSTOM+MY_SEND_DATA )
{
LPVOID ptr = GlobalLock((HANDLE)lparam) ;
Taux MqlRates [123] ;
// a obtenu des taux
memcpy(rates[0].time,ptr,123*sizeof(MqlRates)) ; // voici le prototype int memcpy(datetime&,const int&,int)
GlobalUnlock(memid) ;
GlobalFree(memid) ;
}
}

C'est tout... pas de tuyaux, de fichiers externes, d'importation de dlls restantes.
J'ai juste précipité un petit échantillon avec de grandes possibilités, mais mon esprit ne connaît pas de limites.
Oui, en ce qui concerne GlobalAlloc, je suggère toujours d'utiliser GMEM_MOVEABLE, avec un verrou et un accès à la mémoire pour obtenir un pointeur pour une opération spécifique, et le rendre.
Si vous utilisez une mémoire globale fixe, au nombre N de descripteurs ouverts, une fragmentation peut se produire...
c'est ce que le noyau de l'OS veut en fonction de la charge.
Bonne chance, hackers !))
 
alexsis78:

Pour ne pas être vague, vous pouvez, par exemple, utiliser un simple pointeur de 4 octets et importer memcpy pour travailler avec la mémoire à l'intérieur du processus du terminal.
vous vous êtes un peu trompé de branche.
 

Il existe un vieux livre de Henry Warren, "Algorithmic tricks for programmers", qui regorge d'astuces de ce type. Cependant, la plupart des exemples ne fonctionneront pas dans MQL en raison du manque de pointeurs C++.

Je vais essayer de trouver quelque chose d'amusant.

 
Vous ne trouverez pas la similitude de mon exemple en C ;))) Premièrement, c'est MQL, deuxièmement, c'est une solution de contournement pour la syntaxe des pointeurs C.

Un peu plus de clarification pour ceux qui connaissent plus.

En C :
int var = 0 ; // déclarer la variable var
int* ptr = &var ; // obtenir le pointeur sur la variable var
int var2 = *ptr ; // copier la valeur du pointeur sur var dans var2

En MQL :
#import "msvcrt.dll"
uint memcpy(int& destination, const int& source, int cnt) ; // prototype de memcpy pour obtenir l'adresse de la variable destination
uint memcpy(int& destination, uint ptr, int cnt) ; // le prototype memcpy pour copier à partir de l'adresse ptr
// le compilateur substituera l'un des deux prototypes par la différence de type du second argument
// prenons un type de pointeur, par exemple uint
#import

int var = 0 ;
uint ptr = memcpy(var,var,0) ; // obtenons un pointeur ptr vers la variable var (ici memcpy ne copie rien mais retourne l'adresse var)
int var2
memcpy(var2, ptr, 4) ; // copier 4 octets ou sizeof(int) du pointeur ptr à la variable var2 (le deuxième prototype de memcpy fonctionne)

J'espère que vous trouverez la méthode utile ;)))
 
alexsis78:
Vous ne trouverez pas la similitude de mon exemple dans C))). Premièrement, il s'agit de MQL, deuxièmement, le contournement de la syntaxe des pointeurs en C.
J'espère que vous le trouverez utile )))).

les gens, n'écrivez pas juste pour le plaisir d'écrire quelque chose.

Toutes ces variantes avec memcpy ont été mâchées il y a plusieurs années et ne sont pas adaptées à ce sujet.

 
o_O:

Les gens, n'écrivez pas pour le plaisir d'écrire quelque chose.

Toutes ces options memcpy ont été mâchées il y a des années et ne sont pas adaptées à ce sujet.

Je suis d'accord, de plus la variante sans arithmétique de pointeur a été décrite, c'est à dire défectueuse. Ils ne sont pas vraiment nécessaires en C#, il n'y a pas de pointeurs. Il n'est pas sûr mais c'est seulement pour un usage personnel et il y aura beaucoup de restrictions comme l'interdiction d'installer par le réseau et ainsi de suite.
 

Je voulais le mettre dans la base de code, mais j'ai changé d'avis :

Utilisation de MQL5 sur Kaggle, tâche de reconnaissance de chiffres

Digit Recognizer | Kaggle
  • www.kaggle.com
Kaggle is your home for data science. Learn new skills, build your career, collaborate with other data scientists, and compete in world-class machine learning challenges.
Dossiers :
sampleMNIST.mq5  25 kb
 
o_O:

Les gens, n'écrivez pas juste pour le plaisir d'écrire quelque chose.

Toutes ces options memcpy ont été étudiées pendant des années et ne sont pas adaptées à ce sujet.

Pourquoi est-ce "inapproprié" ?

J'ai oublié où c'était et je n'ai pas pu le trouver...

A propos, je considère que sauvegarder un pointeur sur un tableau sans appeler de DLL externe relève de l'exploit. Je ne veux pas avoir à confirmer à chaque fois que je lance des indicateurs que j'accepte d 'importer des fonctions de la DLL.

 
George Merts:

Pourquoi n'est-il pas "adapté" ?

J'ai déjà oublié où il était et je n'ai pas pu le retrouver...

À propos, je considère comme un exploit de sauvegarder un pointeur sur un tableau sans faire appel à des DLL externes. Je ne veux pas avoir à confirmer à chaque fois que je lance des indicateurs que je suis d'accord pour importer des fonctions d'une DLL.

Enveloppez le tableau dans une classe, vous pouvez créer des pseudo-pointeurs MQL vers celui-ci avec new
 
Alexey Volchanskiy:
Enveloppez le tableau dans une classe et vous pouvez créer des pseudo-pointeurs MQL vers celui-ci avec new

Alexey, tu devrais aussi me dire comment envelopper des tableaux, émis par la fonction OnCalculate(), dans une classe - dans ce cas, on ne peut pas se passer de copier des pointeurs.

Pour le moment, je ne fais que copier des données dans mon tableau de classe, puis je tire un pointeur vers cet objet. Mais cela nécessiterait des copies supplémentaires, ce qui, à mon avis, ajoute beaucoup de "poids" aux ticks fréquents et au grand nombre de graphiques. Je veux me débarrasser de cette copie. Mais, à part une béquille via DLL (standard ou auto-écrite), il n'y a rien que je puisse suggérer.

Dans le Service Desk, on me renvoie sans cesse en disant "l'objet peut être supprimé". Mais ce sont leurs propres tableaux ! Lorsque je dis que je peux créer un objet puis le supprimer et que le pointeur deviendra invalide, ils répondent que "c'est moi qui en serai responsable". C'est une "double moralité" qui est à l'œuvre ici.

Je ne me soucie pas de la DLL - mais de tels indicateurs nécessitent une confirmation constante lors de l'exécution - quel ennui....