#include <bits/stdc++.h>   using namespace std;   mt19937 rng(chrono::steady_clock::now().time_since_epoch().count());   inline long long int rand(long long int x, long long int y) {     ++y;     return (rng() % (y - x)) + x;   }   string to_string(char c) {     string second(1, c);     return second;   }   string to_string(bool b) { return (b ?  true  :  false ); }   template <typename A, typename B>   string to_string(pair<A, B> p) {     return  (  + to_string(p.first) +  ,   + to_string(p.second) +  ) ;   }   template <typename A>   string to_string(A v) {     bool first = true;     string res =  { ;     for (const auto &x : v) {       if (!first) {         res +=  ,  ;       }       first = false;       res += to_string(x);     }     res +=  } ;     return res;   }   void degug_out() { cerr << endl; }   template <typename Head, typename... Tail>   void degug_out(Head H, Tail... T) {     cerr <<     << to_string(H);     degug_out(T...);   }   inline long long int gcd(long long int a, long long int b) {     if (a > b) swap(a, b);     if (a == 0) return b;     return gcd(b % a, a);   }   long long int n, m;   vector<vector<char>> grid;   vector<vector<int>> dist, dist2;   long long int dx[] = {1, 0, -1, 0};   long long int dy[] = {0, 1, 0, -1};   void bfs(long long int x, long long int y, long long int op) {     dist[x][y] = 0;     queue<pair<long long int, long long int>> q;     q.emplace(x, y);     while (q.size()) {       long long int x = q.front().first, y = q.front().second;       q.pop();       if (op == 0) {         for (long long int i = (0); i <= (long long int)(1); ++i) {           long long int nx = x + dx[i];           long long int ny = y + dy[i];           if (nx < 0 || ny < 0 || nx >= n || ny >= m || ~dist[nx][ny] ||               grid[nx][ny] ==  # )             continue;           dist[nx][ny] = dist[x][y] + 1;           q.emplace(nx, ny);         }       } else {         for (long long int i = (2); i <= (long long int)(3); ++i) {           long long int nx = x + dx[i];           long long int ny = y + dy[i];           if (nx < 0 || ny < 0 || nx >= n || ny >= m || ~dist[nx][ny] ||               grid[nx][ny] ==  # )             continue;           dist[nx][ny] = dist[x][y] + 1;           q.emplace(nx, ny);         }       }     }     return;   }   int main() {     ios_base::sync_with_stdio(false);     cin.tie(0);     cin >> n >> m;     grid.resize(n, vector<char>(m,  * ));     dist.resize(n, vector<int>(m, -1));     dist2.resize(n, vector<int>(m, -1));     for (long long int i = (0); i <= (long long int)(n - 1); ++i)       for (long long int j = (0); j <= (long long int)(m - 1); ++j)         cin >> grid[i][j];     bfs(0, 0, 0);     swap(dist, dist2);     bfs(n - 1, m - 1, 1);     if (dist2[n - 1][m - 1] == -1) {       cout << 0;       return 0;     }     map<long long int, long long int> co;     for (long long int i = (0); i <= (long long int)(n - 1); ++i)       for (long long int j = (0); j <= (long long int)(m - 1); ++j)         if (~dist[i][j] && ~dist2[i][j] && dist2[i][j] &&             dist2[i][j] != (n - 1 + m - 1))           co[dist2[i][j]]++;     for (long long int i = (0); i <= (long long int)(n - 1); ++i)       for (long long int j = (0); j <= (long long int)(m - 1); ++j)         if (~dist[i][j] && ~dist2[i][j] && dist2[i][j] &&             dist2[i][j] != (n - 1 + m - 1))           if (co[dist2[i][j]] == 1) {             cout << 1;             return 0;           }     cout << 2;   }