Guide

Convert MQL4 to MQL5: 8 Easy Fixes for Common Errors

When you convert MQL4 to MQL5, most compile errors come from the same eight changes. This guide shows each error, the fix and how to test the result on demo.

Converting MQL4 to MQL5: old MQL4 code with compile errors next to clean MQL5 code using CTrade and an indicator handle
On this page

Workflow to convert MQL4 to MQL5, from source file to demo test

Save an old .mq4 file as .mq5 and open it in MetaEditor for MT5. Then press Compile. The Errors tab fills up at once, often with dozens of lines. It looks bad, but most errors trace back to just eight changes in the language. Fix those, and much of the code compiles as it is.

[SCREENSHOT: MetaEditor 5 Errors tab after compiling an unconverted MQL4 file]

Below, you will convert MQL4 to MQL5 one error at a time. Then you test both versions side by side.

Why you need to convert MQL4 to MQL5

MT5 cannot run .ex4 files at all. On top of that, MQL5 changed two big parts of the language. First, the trade model now splits orders, deals and positions. Second, indicators return a handle instead of a value.

The rest of the syntax looks alike, so loops, math and inputs carry over. The trade and indicator layers, however, need a real rewrite. That is why no simple rename can convert MQL4 to MQL5.

MQL4 calls next to their MQL5 replacements

Before you convert MQL4 to MQL5

Keep the .mq4 source file safe. A compiled .ex4 file holds no readable code, and we do not decompile files. So without the source, the only path is a fresh build from a written list of the rules.

Next, list every input and feature of the EA. Then open the same symbol on an MT5 demo account for the tests later.

Common MetaEditor errors and the MQL5 fix for each

Fix 1: Replace OrderSend() with CTrade

Error: 'OrderSend' - wrong parameters count

Most traders who convert MQL4 to MQL5 start here, since all EAs send orders. In MQL4, OrderSend() takes eleven values in one call. MQL5 expects a request and a result structure instead. The simplest fix is the CTrade class from the standard library:

#include <Trade\Trade.mqh>
CTrade trade;
// MQL4: OrderSend(Symbol(), OP_BUY, 0.10, Ask, 3, sl, tp, "", 123, 0, clrNONE);
trade.SetExpertMagicNumber(123);
trade.Buy(0.10, _Symbol, 0.0, sl, tp);   // price 0.0 = current Ask

CTrade fills the request for you and keeps the last result.

Fix 2: Rewrite order loops for positions

Errors: 'MODE_TRADES' - undeclared identifier and 'OrderSelect' - wrong parameters count

MQL4 keeps market and pending orders in one list, while MQL5 splits them up. Open trades become positions, and OrdersTotal() now counts pending orders only. So a loop over open trades needs new functions:

for(int i = PositionsTotal() - 1; i >= 0; i--)
  {
   ulong ticket = PositionGetTicket(i);           // also selects the position
   if(PositionGetInteger(POSITION_MAGIC) != 123) continue;
   // manage the position here
  }

For closed trades, call HistorySelect() first, then read the deals. Each fill is a deal, so one position can have several deals.

Fix 3: Use indicator handles and CopyBuffer()

Error: 'iMA' - wrong parameters count

In MQL4, iMA() returns the value of the moving average right away. In MQL5, it returns a handle, and you read values with CopyBuffer(). So create the handle once in OnInit(), then read it in OnTick():

int maHandle = INVALID_HANDLE;                                   // global
maHandle = iMA(_Symbol, _Period, 50, 0, MODE_EMA, PRICE_CLOSE);  // OnInit()
double ma[];                                                     // OnTick()
ArraySetAsSeries(ma, true);
if(CopyBuffer(maHandle, 0, 0, 3, ma) < 3) return;                // ma[1] = last closed bar

Finally, free the handle with IndicatorRelease() in OnDeinit(). Never create a new handle on every tick, since that wastes memory.

Fix 4: Replace Bid, Ask and the Close[] series

Errors: 'Bid' - undeclared identifier and 'Close' - undeclared identifier

MQL5 has no built-in Bid, Ask or Close[] variables. Instead, you ask for prices when you need them:

MqlTick tick;
if(!SymbolInfoTick(_Symbol, tick)) return;
double ask = tick.ask, bid = tick.bid;
double lastClose = iClose(_Symbol, _Period, 1);   // last closed bar

For many bars at once, use CopyRates() or CopyClose(). Old MQL4 code counts bars backwards, with 0 as the newest bar. So call ArraySetAsSeries() on your arrays first. Otherwise, index 0 points at the oldest bar.

Fix 5: Rename the event handlers

Old MQL4 code often uses init(), start() and deinit(). MQL5 does not treat these names as events, so MT5 never runs them. Rename them to OnInit(), OnTick() and OnDeinit().

Also, OnInit() now returns a code. Use INIT_SUCCEEDED when all is well, or INIT_FAILED to stop the EA from loading. Indicators move from start() to the new OnCalculate() function.

Fix 6: Swap MarketInfo() and the account functions

Error: 'MarketInfo' - undeclared identifier

MQL5 reads symbol and account data through a few new functions. So each old call has a new match, as the panel below shows. The MQL5 docs list each name, so keep them open while you work.

MQL4 market and account calls next to their MQL5 match

Fix 7: Handle netting and hedging accounts

An MT4 account lets you hold many trades on one symbol. An MT5 account, however, can work in two ways. In netting mode, each symbol has one position, and a new trade adds to it or reduces it. In hedging mode, each trade stays a separate position, as in MT4.

So read the mode at start-up with AccountInfoInteger(ACCOUNT_MARGIN_MODE). Close logic and magic number filters differ between the two modes. If other traders will use your EA, test it on both account types.

Fix 8: Set the filling mode and read return codes

Error: Unsupported filling mode in the Journal tab

Many traders who convert MQL4 to MQL5 miss this step until a live order fails. Each broker accepts only certain filling modes: FOK, IOC or RETURN. If the EA sends the wrong one, the server rejects the order. So let CTrade pick a valid mode, then check the return code after each order:

trade.SetTypeFillingBySymbol(_Symbol);
if(!trade.Buy(lots, _Symbol, 0.0, sl, tp) || trade.ResultRetcode() != TRADE_RETCODE_DONE)
   Print("Order failed: ", trade.ResultRetcode(), " ", trade.ResultRetcodeDescription());

Also round prices to the symbol’s digits, and lots to its volume step. Otherwise, the server rejects values such as 0.033 lots on a 0.01 step.

Test the converted EA side by side

Once the code compiles, test it before you trust it. Run the MT4 and MT5 versions on the same symbol, timeframe and dates. Then compare the two trade lists: entries, exits and lots. Expect small gaps, because each platform uses its own data and spreads. A big gap, however, usually points to a logic bug.

Test checklist for a converted EA

After that, forward test the MT5 version on a demo account for at least a week. Watch the Experts tab for errors, and check each order against your rules. Only then do you know that you managed to convert MQL4 to MQL5 without changing the strategy.

Convert it yourself or ask a developer?

A small EA with one strategy may only need these eight fixes. However, panels, many symbols or custom indicators take longer. Each custom indicator also needs its own conversion first. A clean MQL4 to MQL5 conversion follows the five steps below.

Five steps for an MQL4 to MQL5 conversion

Would you rather not convert MQL4 to MQL5 yourself? Our strategy conversion service handles MQL4 rewrites too. You test a demo build before the final payment. For new features, see MT5 EA development. Need an indicator as well? See custom MT5 indicators. For prices, check our pricing page.

Frequently asked questions

Can an MT4 EA run on MT5 without changes?

No. MT5 cannot load .ex4 files. MQL5 also handles orders and indicators in a new way. So the code needs a rewrite before it can trade on MT5.

Is there an automatic MQL4 to MQL5 converter?

Some include files map old MQL4 calls onto MQL5, and they help with simple code. However, the trade logic still needs a manual review, because MT5 uses positions and deals. A side-by-side test then shows what still differs.

How long does it take to convert MQL4 to MQL5?

It depends on the size of the code. A small EA may only need the eight fixes in this guide. Panels, many symbols or custom indicators take longer. So we read the code before we confirm a date.

Will the MT5 version trade exactly like the MT4 version?

Close, but not identical. Data, spreads and fills differ between the two platforms, and netting accounts merge trades on one symbol. The side-by-side test lists every gap and where it comes from.

Is the .ex4 file enough, or do you need the .mq4 source?

We need the .mq4 source code to convert MQL4 to MQL5. An .ex4 file has no readable code, and we do not decompile files. Without the source, we can rebuild the EA from a written list of its rules.

Can you convert custom indicators as well?

Yes. Each indicator moves to the new OnCalculate() function in MQL5. If your EA reads one through iCustom(), we convert it first. MT5 cannot load an .ex4 file, so the EA needs the new version.

WhatsApp · Email · Telegram

Tell us what you want to automate

Send your rules on WhatsApp. You get a clear quote, then a demo build to test before you pay in full.