#include <bits/stdc++.h>
using namespace std;
void search(int x, int y, int t, vector<vector<char>>& c,
            vector<vector<long long>>& memo, int H, int W) {
  if (y >= H || x >= W || x < 0 || y < 0 || c.at(y).at(x) == '#') {
    return;
  }
  if (memo.at(y).at(x) <= t && memo.at(y).at(x) > 0) {
    return;
  }
  memo.at(y).at(x) = t;
  search(x + 1, y, t + 1, c, memo, H, W);
  search(x - 1, y, t + 1, c, memo, H, W);
  search(x, y + 1, t + 1, c, memo, H, W);
  search(x, y - 1, t + 1, c, memo, H, W);
}
void filling(int H, int W, vector<vector<long long>>& memo) {
  for (int i = 0; i < H; i++) {
    for (int j = 0; j < W; j++) {
      memo.at(i).at(j) = -1;
    }
  }
}
int main() {
  int H, W;
  cin >> H >> W;
  vector<vector<char>> c(H, vector<char>(W));
  for (int i = 0; i < H; i++)
    for (int j = 0; j < W; j++) {
      cin >> c.at(i).at(j);
    }
  long long ans = 0;
  vector<vector<long long>> memo(H, vector<long long>(W));
  for (int i = 0; i < H; i++) {
    for (int j = 0; j < W; j++) {
      filling(H, W, memo);
      if (c.at(i).at(j) != '#') search(j, i, 0, c, memo, H, W);
      for (int k = 0; k < H; k++) {
        for (int l = 0; l < W; l++) {
          ans = max(ans, memo.at(k).at(l));
        }
      }
    }
  }
  cout << ans << endl;
  return 0;
}
