import std.stdio, std.algorithm, std.range, std.array, std.conv, std.string, std.math;

void main() {
    auto S = readln.split.to!(int[]);
    auto H = S[0], W = S[1];
    char[][] cell;
    foreach (y; 0..H) {
        cell ~= readln.split.to!(char[]);
    }
    auto white = cell.map!(c => c.count('.')).sum;
    auto score = new long[][](H,W);
    auto cost(int x, int y, char[][] cell) {
        if (x == W-1 && y == H-1) return 1;
        if (x < 0) return long.max;
        if (y < 0) return long.max;
        if (x >= W) return long.max;
        if (y >= H) return long.max;
        if (cell[y][x] == '#') return long.max;
        if (score[y][x] > 0) return score[y][x];
        cell[y][x] = '#';
        scope(exit) cell[y][x] = '.';
        score[y][x] = min(cost(x-1,y,cell), cost(x+1,y,cell), cost(x,y-1,cell), cost(x,y+1,cell));
        if (score[y][x] < long.max) score[y][x]++;
        return score[y][x];
    }
    auto minCost = cost(0,0,cell);
    if (minCost == long.max) {
        writeln(-1);
        return;
    }
    writeln(cast(long)(white - minCost));
}
