#include <bits/stdc++.h>
using namespace std;
template <class T, class... S>
void dbs(string str, T t, S... s) {
  int idx = str.find(',');
  cout << str.substr(0, idx) << " : " << t << ",";
  dbs(str.substr(idx + 1), s...);
}
template <class S, class T>
ostream& operator<<(ostream& os, const pair<S, T>& p) {
  return os << "(" << p.first << ", " << p.second << ")";
}
template <class T>
ostream& operator<<(ostream& os, const vector<T>& p) {
  os << "[ ";
  for (auto& it : p) os << it << " ";
  return os << "]";
}
template <class T>
ostream& operator<<(ostream& os, const set<T>& p) {
  os << "[ ";
  for (auto& it : p) os << it << " ";
  return os << "]";
}
template <class S, class T>
ostream& operator<<(ostream& os, const map<S, T>& p) {
  os << "[ ";
  for (auto& it : p) os << it << " ";
  return os << "]";
}
using namespace std;
int N, M;
int mp(int i, int j) { return M * i + j; }
pair<int, int> dir[100];
vector<char> xc = {'U', 'R', 'L', 'D'};
struct eph {
  bool val = 1;
  char c;
  int U, L, R, D;
  int get(char c) {
    if (c == 'U') return U;
    if (c == 'L') return L;
    if (c == 'R') return R;
    if (c == 'D') return D;
    assert(false);
  }
  void fil(char c, int x) {
    if (c == 'U') U = x;
    if (c == 'L') L = x;
    if (c == 'R') R = x;
    if (c == 'D') D = x;
  }
  int nx() { return get(c); }
};
bool valid(pair<int, int> cur) {
  return cur.first >= 0 && cur.first < N && cur.second >= 0 && cur.second < M;
}
vector<eph> cur;
void del(int x) {
  if (cur[x].U >= 0) {
    cur[cur[x].U].D = cur[x].D;
  }
  if (cur[x].D >= 0) {
    cur[cur[x].D].U = cur[x].U;
  }
  if (cur[x].L >= 0) {
    cur[cur[x].L].R = cur[x].R;
  }
  if (cur[x].R >= 0) {
    cur[cur[x].R].L = cur[x].L;
  }
}
int cnt = 0;
void tryItFor(int x) {
  del(x);
  int y = cur[x].nx();
  if (y < 0) return;
  cnt++;
  tryItFor(y);
}
int main() {
  ios_base::sync_with_stdio(0);
  cin.tie(0);
  cout.tie(0);
  cin >> N >> M;
  dir['U'] = {-1, 0};
  dir['D'] = {1, 0};
  dir['R'] = {0, 1};
  dir['L'] = {0, -1};
  vector<string> A(N);
  for (int i = 0; i < N; i++) {
    cin >> A[i];
  }
  vector<eph> nexx(N * M);
  for (int i = 0; i < N; i++) {
    for (int j = 0; j < M; j++) {
      nexx[mp(i, j)].c = A[i][j];
      for (auto u : xc) {
        pair<int, int> cur = {i + dir[u].first, j + dir[u].second};
        while (valid(cur) && A[cur.first][cur.second] == '.') {
          cur = {cur.first + dir[u].first, cur.second + dir[u].second};
        }
        if (!valid(cur)) {
          nexx[mp(i, j)].fil(u, -1);
        } else {
          nexx[mp(i, j)].fil(u, mp(cur.first, cur.second));
        }
      }
    }
  }
  int cx = 0, best = -1;
  for (int i = 0; i < N * M; i++) {
    if (A[i / M][i % M] == '.') {
      continue;
    }
    cnt = 1;
    cur = nexx;
    tryItFor(i);
    if (cnt == best) {
      cx++;
    } else if (cnt > best) {
      cx = 1;
      best = cnt;
    }
  }
  cout << best << ' ' << cx << endl;
  return 0;
}
