#include <iostream>
#include <vector>
#include <queue>

using namespace std;

struct State {
    int x, y, orientation;

    State(int x, int y, int orientation) : x(x), y(y), orientation(orientation) {}
};

int main() {
    int n, m;
    cin >> n >> m;
    vector<vector<char>> table(n, vector<char>(m));

    for (int i = 0; i < n; i++) {
        for (int j = 0; j < m; j++) {
            cin >> table[i][j];
        }
    }

    vector<vector<vector<bool>> > visited(n, vector<vector<bool>>(m, vector<bool>(2, false)));
    queue <State> q;

    q.push(State(0, 0, 0)); // Начинаем с верхнего левого угла (горизонтальное положение)
    visited[0][0][0] = true;

    int dx[] = {1, 0, -1, 0};
    int dy[] = {0, 1, 0, -1};

    while (!q.empty()) {
        State cur = q.front();
        q.pop();

        if (cur.x == n - 2 && cur.y == m - 2) {
            cout << 0 << endl; // Слайм уже в целевом положении
            return 0;
        }

        for (int i = 0; i < 4; i++) {
            int new_x = cur.x + dx[i];
            int new_y = cur.y + dy[i];
            int new_orientation = cur.orientation;

            if (new_x < 0 || new_x + 1 >= n || new_y < 0 || new_y + 1 >= m) {
                continue; // Выход за границы стола
            }

            if (table[new_x][new_y] == '#' || table[new_x + 1][new_y] == '#' ||
                table[new_x][new_y + 1] == '#' || table[new_x + 1][new_y + 1] == '#') {
                continue; // Слайм попал на дырку
            }

            if (!visited[new_x][new_y][new_orientation]) {
                visited[new_x][new_y][new_orientation] = true;
                q.push(State(new_x, new_y, new_orientation));
            }
        }
    }

    cout << -1 << endl; // Не удалось достичь цели
    return 0;
}