// Slower C++ solution:
#include <iostream> // cout, endl, cin

#include <string> // string, to_string, stoi

#include <vector> // vector

#include <algorithm> // min, max, swap, sort, reverse, lower_bound, upper_bound

#include <utility> // pair, make_pair

#include <tuple> // tuple, make_tuple

#include <cstdint> // int64_t, int*_t

#include <cstdio> // printf

#include <map> // map

#include <queue> // queue, priority_queue

#include <set> // set

#include <stack> // stack

#include <deque> // deque

#include <unordered_map> // unordered_map

#include <unordered_set> // unordered_set

#include <bitset> // bitset

#include <cctype> // isupper, islower, isdigit, toupper, tolower

using namespace std;

#define int long long





signed main(){

    cin.tie(nullptr);

    ios::sync_with_stdio(false);



    int h,w; cin >> h >> w;

    vector<vector<char> > s(h+2,vector<char>(w+2));

    for(int i = 1;i < h+1;i ++){

        for(int j = 1;j < w+1;j ++){

            cin >> s.at(i).at(j);

        }

    }



    vector<vector<int> > t(h+2,vector<int>(w+2,10000));

    t.at(0).at(1) = 0;



    for(int i = 0;i < 100;i ++){

        for(int j = 1;j < h+1;j ++){

            for(int k = 1;k < w+1;k ++){

                if(s.at(j).at(k) == '.'){

                    t.at(j).at(k) = min(t.at(j).at(k),t.at(j).at(k-1)+1);

                    t.at(j).at(k) = min(t.at(j).at(k),t.at(j).at(k+1)+1);

                    t.at(j).at(k) = min(t.at(j).at(k),t.at(j-1).at(k)+1);

                    t.at(j).at(k) = min(t.at(j).at(k),t.at(j+1).at(k)+1);

                }

            }

        }



    }



    int count = 0;

    for(int i = 1;i < h+1;i ++){

        for(int j = 1;j < w+1;j ++){

            if(s.at(i).at(j) == '.') count ++;

        }

    }



    if(t.at(h).at(w) == 10000){

        cout << -1 << endl;

    }else{

        cout << count - t.at(h).at(w) << endl;

    }



    

}

// Faster C++ solution for the same problem (measured speedup: 1.1215713110162533x):
#include <iostream> // cout, endl, cin

#include <string> // string, to_string, stoi

#include <vector> // vector

#include <algorithm> // min, max, swap, sort, reverse, lower_bound, upper_bound

#include <utility> // pair, make_pair

#include <tuple> // tuple, make_tuple

#include <cstdint> // int64_t, int*_t

#include <cstdio> // printf

#include <map> // map

#include <queue> // queue, priority_queue

#include <set> // set

#include <stack> // stack

#include <deque> // deque

#include <unordered_map> // unordered_map

#include <unordered_set> // unordered_set

#include <bitset> // bitset

#include <cctype> // isupper, islower, isdigit, toupper, tolower

using namespace std;

#define int long long





signed main(){

    cin.tie(nullptr);

    ios::sync_with_stdio(false);



    int h,w; cin >> h >> w;

    vector<vector<char> > s(h+2,vector<char>(w+2));

    for(int i = 1;i < h+1;i ++){

        for(int j = 1;j < w+1;j ++){

            cin >> s.at(i).at(j);

        }

    }



    vector<vector<int> > t(h+2,vector<int>(w+2,10000));

    t.at(0).at(1) = 0;



    for(int i = 0;i < 50;i ++){

        for(int j = 1;j < h+1;j ++){

            for(int k = 1;k < w+1;k ++){

                if(s.at(j).at(k) == '.'){

                    t.at(j).at(k) = min(t.at(j).at(k),t.at(j).at(k-1)+1);

                    t.at(j).at(k) = min(t.at(j).at(k),t.at(j).at(k+1)+1);

                    t.at(j).at(k) = min(t.at(j).at(k),t.at(j-1).at(k)+1);

                    t.at(j).at(k) = min(t.at(j).at(k),t.at(j+1).at(k)+1);

                }

            }

        }



    }



    int count = 0;

    for(int i = 1;i < h+1;i ++){

        for(int j = 1;j < w+1;j ++){

            if(s.at(i).at(j) == '.') count ++;

        }

    }



    if(t.at(h).at(w) == 10000){

        cout << -1 << endl;

    }else{

        cout << count - t.at(h).at(w) << endl;

    }



    

}