[FIXED] Build 604 - major issue with a string containing a single space " " and wininet.dll unicode W import - page 2

 

thanks so much gchrmt4. it works fine and the string/space/"F" memory issue has disappeared, here his a sample call:


   ...../....

   if(!IsDllsAllowed())
   {
      toolAlert("[ERROR] DLL call is not allowed. Experts cannot run!");
   }

   string url = "http://xxxx?stage=ctrlLoad&sym="+Symbol()+"&an="+san;
   page = urlRead(url, false);
   if(StringSubstr(page, 0, 3) != "OK_") // first time, the session failed as explained in comments, try again...
   {
      page = urlRead(url, false);
      if(StringSubstr(page, 0, 3) != "OK_") // failed again ? 
      {
         iFailed = true;
      }
   }
   ..../..... process below

Usually it works with second call. If not this is a server error out of of MT4 scope problem.

THANKS AGAIN buddy.

 
DavidS777:

THANKS AGAIN buddy.

BTW, you don't actually need to do a dummy web request to work round the MT4 bug.

Any long string concatenation seems to "seed" MT4's memory handling and make the problem then go away. For example, you can call a dummy string concatenation such as https://www.mql5.com/en/forum/149360, and after that you should be able to read web data without needing to ignore the first result.

 
gchrmt4:

BTW, you don't actually need to do a dummy web request to work round the MT4 bug.

Any long string concatenation seems to "seed" MT4's memory handling and make the problem then go away. For example, you can call a dummy string concatenation such as https://www.mql5.com/en/forum/149360, and after that you should be able to read web data without needing to ignore the first result.


Oh great, it works with this hotfix on start. thanks again. Here is the fix:

//------------------------------------------------------------------------------------------------------------------------------
string hotfixTestConcatenation()
//------------------------------------------------------------------------------------------------------------------------------
{
   string strTemplate;
   StringInit(strTemplate, 1000, 65);
   string strData = "";
   for (int i = 0; i < 10; i++) {
      strData = StringConcatenate(strData, strTemplate);
   }
   return strData;
}

//------------------------------------------------------------------------------------------------------------------------------
int start()
//------------------------------------------------------------------------------------------------------------------------------
{
   // avoid some bugs
   string strData = hotfixTestConcatenation();

   if(!IsDllsAllowed())
   {
      Alert("[ERROR] DLL call is not allowed. Experts cannot run!");
   }

   string url = "http://xxxx?stage=ctrlLoad&sym="+Symbol()+"&an="+san;
   page = urlRead(url, false);
   if(StringSubstr(page, 0, 3) != "OK_") // your custom header check
   {
      iFailed = true;
   }

  
 ..../..... some processing
}


#import  "Wininet.dll"
   int InternetAttemptConnect(int x);
   int InternetOpenW(string, int, string, string, int);
   int InternetConnectW(int, string, int, string, string, int, int, int); 
   int HttpOpenRequestW(int, string, string, int, string, int, string, int); 
   int InternetOpenUrlW(int, string, string, int, int, int);
   //int InternetReadFile(int, string, int, int& OneInt[]);
   int InternetReadFile(int, uchar & arr[], int, int & arr[]);
   int InternetCloseHandle(int); 
#import


//-----------------------------------------------------------------------------------------------------
// Reads the specified URL and returns the server's response. Return value is 
// a blank string if an error occurs                
//-----------------------------------------------------------------------------------------------------
string urlRead(string Url, bool PrintDebuggingMessages = false)
{
   string strData = "";
   bool bSuccess = false;
   
   // Get an internet handle
   int hInternet = InternetOpenW("mt4", 0 /* 0 = INTERNET_OPEN_TYPE_PRECONFIG */, NULL, NULL, 0);
   if (hInternet == 0) {
      if (PrintDebuggingMessages) Print("InternetOpenW() failed");

   } else {
      // Get a URL handle
      int hInternetUrl = InternetOpenUrlW(hInternet, Url, NULL, 0, 0, 0);
      if (hInternetUrl == 0) {
         if (PrintDebuggingMessages) Print("InternetOpenUrlW() failed");

      } else {
         if (PrintDebuggingMessages) Print("Okay: url handle: ", hInternetUrl);

         // We potentially (in fact, usually) get the response in multiple chunks
         // Keep calling InternetReadFile() until it fails, or until
         // it says that the read is complete
         bool bKeepReading = true;
         while (bKeepReading) {                    
            int szRead[1];
            uchar arrReceive[];
            ArrayResize(arrReceive, READURL_BUFFER_SIZE + 1);
            int success = InternetReadFile(hInternetUrl, arrReceive, READURL_BUFFER_SIZE, szRead);

            if (success == 0) {
               if (PrintDebuggingMessages) Print("InternetReadFile() failed");
               bKeepReading = false;

            } else {
               // InternetReadFile() has succeeded, but we may be at the end of the data 
               if (szRead[0] == 0) {
                  if (PrintDebuggingMessages) Print("Reached end of data");
                  bKeepReading = false;
                  bSuccess = true;
                  
               } else {
                  // Convert the data from Ansi to Unicode using the built-in MT4 function
                  string strThisRead = CharArrayToString(arrReceive, 0, szRead[0], CP_UTF8);
                  strData = StringConcatenate(strData, strThisRead);  // <-- PROBLEM HERE ON FIRST USE ONLY IN EACH MT4 SESSION
               }
            }
         }
         InternetCloseHandle(hInternetUrl);
      }
      InternetCloseHandle(hInternet);
   }
   return (strData);
}