xuks124Most MT5 "daily loss guard" implementations look like this: double today_pnl = 0.0; //...
Most MT5 "daily loss guard" implementations look like this:
double today_pnl = 0.0; // module-level variable
bool daily_blocked = false;
It works fine — until the terminal restarts, the EA is recompiled, the chart is switched, or the config is reloaded. Every one of those calls OnInit() again and zeroes the variable. Your hard daily cap cheerfully hands you back the full day's risk budget.
If you trade a prop-firm account (5% daily drawdown rule), this is not a small bug: crashes and restarts cluster on bad trading days, exactly when you need that guard most.
| Event | Memory var | Terminal globals | File (common folder) |
|---|---|---|---|
| New tick / new bar | yes | yes | yes |
| EA recompile / re-attach | no | yes | yes |
| Terminal restart | no | yes | yes |
| Reinstall / another machine / several terminals | no | no | yes |
GlobalVariableSet() covers the common cases. The file wins the last row.
struct GuardState
{
long day_stamp; // which trading day this state belongs to
double day_start_balance; // anchor for the daily drawdown
bool blocked; // has the day already tripped
};
day_stamp is the field people forget. Without it the restored state is either ignored forever or applied forever. Both are wrong.
long TradingDayStamp()
{
MqlDateTime t;
TimeToStruct(TimeTradeServer(), t); // NOT TimeLocal()
return((long)t.year * 10000 + t.mon * 100 + t.day);
}
TimeLocal() resets your cap in the middle of the session. TimeCurrent() is the last quote time and lags badly in quiet markets.
if(blocked) return; // cheap, and catches externally triggered blocks
if(!risk_ok) { blocked = true; SaveState(); return; }
SendOrder();
Wrong order + one crash between the two lines = one order that should never have been sent.
MQL5 has no cross-program order hook. Your "guard EA" cannot stop an order another EA (or a Python strategy on the same account) is about to send. Three options: close positions when the cap trips, publish a terminal global your own strategies respect, or move risk control outside the terminal.
If the new process happily sends the order, your state was in memory and the guard was decoration.
Three lines of discipline: state on disk, broker trading day, write before send. That is the difference between a risk limit and a wish.
I packaged this as a free, open MT5 tool (pure MQL5, no DLL, no network calls, percentages only):
https://xuks124.github.io/vigildesk/free.html
No profit promises — it only handles risk control.