Errors, bugs, questions - page 2540

 
Сергей Таболин:

What do you want?

So that incompetent people like you, Fedoseyev, etc. do not get into the discussion of bugs and designs with their comments.

That constructions and mechanisms taken in MQL from C++ in their entirety and looking the same as in C++ work the same as in C++.

Sergei Tabolin:

For MQL to be a full analogue of C++?

it's bullshit and you know it, but you have to throw it in there.
Sergey Tabolin:

And stop whining and blowing snot bubbles about it. I opened a separate thread for such "discussions".

You're the one whining about how annoying it is, about a separate language and about a separate thread.

Open a separate thread for yourself and your sympathizers and whine there.

 
How to make the terminal release the mqd file? Or even better, if there was an in-house way to delete it from the interface?
 
Stanislav Korotky:
How to make the terminal release the mqd file? Or even better, if there was an in-house way to remove it from the interface?

I can roughly guess what the question is about. Better to restate it.

 
I think there is a problem with dll deinitialisation in Services, help me to understand.
The problem is this. After pressing "Stop" command in Service menu, terminal doesn't wait for Fn() function to finish for some reason.
It prematurely tries to break the connection with the dll, hanging up the terminal or completely crashes (closes).
Although at the DllMain entry point, the Detach flag in DLL_PROCESS_DETACH explicitly sets a flag to terminate the while loop.

But while doesn't have time to exit the loop in time to execute the functions below, after all the other processes have completed additionally.
And terminate the Fn() function itself.
The DestroyFunction(); function acts as a check in this example.

The dll contents

#define  EXP extern "C" __declspec(dllexport)

void DestroyFunction(void);
EXP void __stdcall Fn(int num);

bool Detach;

//---------------------------------------------------------------------
BOOL APIENTRY DllMain(HMODULE hModule, DWORD  ul_reason_for_call, LPVOID lpReserved)
{
        switch (ul_reason_for_call)
        {
                case DLL_PROCESS_ATTACH:
                        Detach = false;
                        break;
                case DLL_THREAD_ATTACH:
                        break;
                case DLL_THREAD_DETACH:
                        break;
                case DLL_PROCESS_DETACH:
                        Detach = true;
                        break;
        }
        return TRUE;
}

//---------------------------------------------------------------------
void DestroyFunction()
{
        MessageBoxW(NULL, L"Start DestroyFunction", L"OK", MB_OK);

        return;
}

//---------------------------------------------------------------------
EXP void __stdcall Fn(int num)
{
        int count = num;

        while (Detach == false)
        {
            //Имитация работы цикла
            count++;    

            if (count > 0)
                MessageBoxW(NULL, L"Start While iteration", L"OK", MB_OK);

            Sleep(10000);
        }       

 
        //После нажатия команды "Остановить" в меню Сервис, сюда уже не доходим, так как уже висим, или вылетел терминал.
        DestroyFunction();

        
        return;
}


The contents of the program Service.
Additional delay by _StopFlag does not help.

//+------------------------------------------------------------------+
//|                                                      BugDll.mq5 |
//|                        Copyright 2019, MetaQuotes Software Corp. |
//|                                             https://www.mql5.com |
//+------------------------------------------------------------------+
#property service
#property copyright "Copyright 2019, MetaQuotes Software Corp."
#property link      "https://www.mql5.com"
#property version   "1.00"
#property strict
#property script_show_inputs


#import "BugDll.dll"
   void Fn(int num);
#import


//+------------------------------------------------------------------+
//| Service program start function                                   |
//+------------------------------------------------------------------+
int OnStart()
{      
   
   Fn(0);

   if(_StopFlag)
      Sleep(10000);
   
   return(0);
}
//+------------------------------------------------------------------+
Files:
MQL5.zip  54 kb
 
Roman:
I think there's a problem with deinitialisation of the dll in Services, help me out.

the dll is not (necessarily) unloaded immediately after the service ends (I could be wrong)

In any case, what you do with DLL_PROCESS_DETACH is too late. Make an explicit deinit function in dll which will set this flag and explicitly call it when the service ends.

 
Roman:

The terminal will start unloading the lib after the thread returns from start(), I think. Otherwise, how does it work? The program is running and start to break its environment? This is nonsense. Start a separate thread in the lib, not chasing a script thread in a loop, and it will be able to terminate normally.

 
Vict:

The terminal will start unloading the lib after the thread returns from start(), I think. Otherwise how does it work? The program is running and start to break its environment? This is nonsense. Start a separate thread in the lib, and it will be able to terminate normally.

The thing is, I have the same problem with threads, and because of this I cannot correctly terminate other processes (threads), which have a bunch of objects that need to be destroyed.
I can't terminate other processes correctly (i.e. I can't kill other processes).
The Terminal works incorrectly with the output pointDLL_PROCESS_DETACH.

I'll try what TheXpert suggested, but the fact that the terminal unloads dll immediately, regardless of DLL_PROCESS_DETACH, it must be an error in the terminal.

TheXpert:

The dll is not (necessarily) unloaded immediately after the service ends (I could be wrong)

Anyway, what you are doing with DLL_PROCESS_DETACH is too late. Make an explicit function deinit in dll, which will set this flag and explicitly call at service shutdown.

Thanks for the hint, I'll try it that way.

 
Roman:

The thing is, I have the same problem with threads and because of it, I can't properly terminate other processes (threads) which have a bunch of objects that need to be destroyed.
I can't terminate other processes correctly (i.e. I can't do anything about them).
The Terminal works incorrectly with the output point DLL_PROCESS_DETACH.

I'll try what TheXpert suggested, but terminal unloads dll at once, regardless of DLL_PROCESS_DETACH, it must be a terminal bug.

Thanks for the tip, I'll try it that way.

What makes you think the dll lives in a separate thread? You have a trivial program crash that is not handled in loop conditions.

And DllMain is run when connecting/disconnecting dll to DLL_PROCESS process and when creating/terminating thread created in this process DLL_THREAD. So your bool Detach, it's not necessarily exists inside dll, because the compiler may have removed it within the framework of optimization, because during the execution of all functions during the lifetime of dll it does not change and equal to false.

 
Vladimir Simakov:

What makes you think the dll lives in a separate thread? You have a trivial program crash that is not handled in loop conditions.

And DllMain is started when you connect/disconnect dll to process DLL_PROCESS and when you create/disconnect a thread, created in this process DLL_THREAD. So your bool Detach, it's not necessarily exists inside dll, because the compiler may have removed it within the framework of optimization, because during the execution of all functions during the lifetime of dll it does not change and equal to false.

It hasn't been said anywhere that the dll lives in a separate thread.
We communicate with Vict and we understand each other )).
I understand that it's a crash, I don't understand why the flag in DLL_PROCESS_DETACH doesn't work to exit the while loop.
As for DLL_THREAD, they are not available for mql at all, it's written in this article, I checked it and they really don't work.
But with VS compiler as an option, could be a trick too.
I would like to hear explanations from competent representatives rather than guessing ))

 
Roman:
I think there is a problem with deinitialisation of dll in Services, help me understand.
The problem is this. After pressing "Stop" command in Service menu, terminal doesn't wait for Fn() function to finish for some reason.
It prematurely tries to break the connection with the dll, hanging up the terminal or completely crashes (closes).
Although at the DllMain entry point, the Detach flag in DLL_PROCESS_DETACH clearly sets a flag to terminate the while loop.

But while doesn't have time to exit the loop in time to execute the functions below, after all the other processes have completed additionally.
And terminate the Fn() function itself.
The DestroyFunction(); function acts as a check in this example.

The dll contents


The contents of the program Service.
Additional delay by _StopFlag does not help.


So you didn't get control back to the terminal, you "hung up" in an "infinite" loop inside the Fn in the DLL.
What kind of normal termination are we talking about!

If you need such behavior, then inside Fn in DLL you should run a separate thread with loop, which should be stopped by flag, which is set in separate function FnStop and at DLL_PROCESS_DETACH