// #pragma GCC optimize("Ofast")
// #pragma GCC target("avx,avx2,fma")
#include<bits/stdc++.h>
using namespace std;
#define fastIO ios_base::sync_with_stdio(false); cin.tie(NULL); cout.tie(NULL)
typedef long long int lli;
typedef long long int ll;
typedef long double ld;
typedef pair<ll, ll> pll;
typedef vector<pll> vop;
typedef vector<ll> vl;
typedef vector<vl> vvl;
typedef vector<int> vi;
typedef pair<int, int> pii;
#define REP(i,a,b) for( long long i=a;i<b;i++)
#define REPR(i,a,b) for(long long i=a;i>=b;i--)
#define adb(a) for(auto ii:a) cout << ii << " "; cout << endl
#define adp(a) for(auto ii:a) cout << ii.F << " " << ii.S << endl;
#define PB push_back
#define MP make_pair
#define F first
#define S second
#define all(x) (x).begin(),(x).end()
#define endl "\n"
#define mem(a,b) memset(a,b,sizeof(a))
#define mod 1000000007
#define PI 3.14159265358979323846
const ll MAXN = 100007;
const ll p = 1000000007;
#define N 200003
#define INF INTMAX_MAX

struct hash_pair {
    template <class T1, class T2>
    size_t operator()(const pair<T1, T2>& p) const
    {
        auto hash1 = hash<T1> {}(p.first);
        auto hash2 = hash<T2> {}(p.second);
        return hash1 ^ hash2;
    }
};

struct LessSecond
{
    template<typename T, typename U>
    bool operator()(const std::pair<T, U> &x, const std::pair<T, U> &y) const
    {
        return x.second < y.second;
    }
};

ll dx[] = {1, -1, 0, 0};
ll dy[] = {0, 0, 1, -1};
ll n, m;
char a[1007][1007];

ll power(ll a, ll b, ll m) { ll ans = 1; a = a % m; while (b) { if (b & 1) ans = (ans * a) % m; b /= 2; a = (a * a) % m; } return ans; }

ll lcm(ll a, ll b) { return (a * b) / __gcd(a, b); }

ll modInverse(ll a, ll m) { ll g = __gcd(a, m); return power(a, m - 2, m); }

bool cmp(const pll &a, const pll &b)
{
    if (a.F != b.F) {
        return a.F > b.F;
    }
    else
        return a.S < b.S;
}

bool check(ll i, ll j)
{
    if (i >= 0 && i < n && j >= 0 && j < m && a[i][j] != '#')
        return true;
    return false;
}

int main()
{


    fastIO;
    int test = 1;
    //cin >> test;
    while (test--)
    {
        cin >> n >> m;
        ll x, y, s, d;
        cin >> x >> y >> s >> d;
        x--, y--, s--, d--;
        ll dist[n + 1][m + 1];
        REP(i, 0, n)
        {
            REP(j, 0, m) cin >> a[i][j], dist[i][j] = 1e10;
        }
        bool vis[n + 1][m + 1];
        mem(vis, false);
        priority_queue<pair<ll, pll>>q;
        q.push({0, {x, y}});
        dist[x][y] = 0;
        vis[x][y] = true;
        ll ans = 1e10;
        while (!q.empty())
        {
            auto v = q.top();
            q.pop();
            //cout << v.F << " " << v.S << endl;
            REP(i, 0, 4)
            {
                ll a = v.S.F + dx[i], b = v.S.S + dy[i];
                if (check(a, b))
                {
                    if (dist[a][b] > dist[v.S.F][v.S.S])
                    {
                        vis[a][b] = true;
                        dist[a][b] = dist[v.S.F][v.S.S];
                        q.push({ -dist[a][b], {a, b}});
                    }
                }
                for (ll i = max(0ll, v.S.F - 2); i <= min(n - 1, v.S.F + 2); i++)
                {
                    for (ll j = max(0ll, v.S.S - 2); j <= min(m - 1, v.S.S + 2); j++)
                    {
                        if (check(i, j))
                        {
                            if (dist[i][j] > dist[v.S.F][v.S.S] + 1)
                            {
                                vis[i][j] = true;
                                dist[i][j] = dist[v.S.F][v.S.S] + 1;
                                q.push({ -dist[i][j], {i, j}});
                            }
                        }
                    }
                }
            }
        }
        if (dist[s][d] < 1e10) cout << dist[s][d] << endl;
        else
            cout << -1 << endl;
    }
    return 0;
}


Measured memory_bytes: 13580