#include <bits/stdc++.h>
using namespace std;
long long int ind(long long int y, long long int x, long long int w) {
  return y * w + x;
}
void Main() {
  long long int H, W;
  cin >> H >> W;
  vector<string> S(H);
  for (long long int i = 0; i < (long long int)(H); i++) cin >> S[i];
  long long int INF = 1e18;
  vector<vector<long long int> > d(H * W, vector<long long int>(W * H, INF));
  for (long long int y = 0; y < (long long int)(H); y++) {
    for (long long int x = 0; x < (long long int)(W); x++) {
      if (S[y][x] == '#') continue;
      if (0 <= y - 1 && S[y - 1][x] == '.') {
        d[ind(y - 1, x, W)][ind(y, x, W)] = 1;
        d[ind(y, x, W)][ind(y - 1, x, W)] = 1;
      }
      if (0 <= x - 1 && S[y][x - 1] == '.') {
        d[ind(y, x - 1, W)][ind(y, x, W)] = 1;
        d[ind(y, x, W)][ind(y, x - 1, W)] = 1;
      }
      if (y + 1 < H && S[y + 1][x] == '.') {
        d[ind(y + 1, x, W)][ind(y, x, W)] = 1;
        d[ind(y, x, W)][ind(y + 1, x, W)] = 1;
      }
      if (x + 1 < W && S[y][x + 1] == '.') {
        d[ind(y, x + 1, W)][ind(y, x, W)] = 1;
        d[ind(y, x, W)][ind(y, x + 1, W)] = 1;
      }
    }
  }
  long long int n = H * W;
  for (long long int k = 0; k < (long long int)(n); k++) {
    for (long long int i = 0; i < (long long int)(n); i++) {
      for (long long int j = 0; j < (long long int)(n); j++) {
        if (d[i][k] < INF && d[k][j] < INF) {
          d[i][j] = min(d[i][j], d[i][k] + d[k][j]);
        }
      }
    }
  }
  long long int res = 0;
  for (long long int i = 0; i < (long long int)(n); i++) {
    for (long long int j = 0; j < (long long int)(n); j++) {
      if (d[i][j] < INF) {
        res = max(res, d[i][j]);
      }
    }
  }
  cout << res << endl;
  ;
}
signed main() {
  Main();
  return 0;
}
