#include <bits/stdc++.h>
using namespace std;
const int N = 2020 * 2020;
int v[N], nxt[N], h[N], in[N], hl;
int dp[N][2];
bool flag;
void edgeInit() {
  memset(h, -1, sizeof(h));
  hl = 0;
  memset(in, 0, sizeof(in));
}
void addEdge(int x, int y) {
  v[hl] = y;
  ++in[y];
  nxt[hl] = h[x];
  h[x] = hl++;
}
char mm[2200][2200];
void dfs(int x) {
  int sec = 0;
  for (int i = h[x]; ~i; i = nxt[i]) {
    int& y = v[i];
    dfs(y);
    if (dp[y][0] + 1 > dp[x][0]) {
      sec = dp[x][0];
      dp[x][0] = dp[y][0] + 1;
    } else if (dp[y][0] + 1 > sec) {
      sec = dp[y][0] + 1;
    }
    dp[x][1] = max(dp[x][1], dp[y][1] + 1);
  }
  dp[x][1] = max(dp[x][1], dp[x][0] + sec);
}
int main() {
  ios::sync_with_stdio(false);
  int n, m;
  while (cin >> n >> m) {
    for (int i = 0; i < n; i++) {
      cin >> mm[i];
    }
    edgeInit();
    flag = false;
    for (int i = 0; i < n; i++) {
      for (int j = 0; j < m; j++) {
        if (mm[i][j] == '#') continue;
        if (mm[i][j] == '>') {
          if (mm[i][j + 1] == '<') flag = true;
          addEdge(i * m + j + 1, i * m + j);
        } else if (mm[i][j] == '<') {
          if (mm[i][j - 1] == '>') flag = true;
          addEdge(i * m + j - 1, i * m + j);
        } else if (mm[i][j] == '^') {
          if (mm[i - 1][j] == 'v') flag = true;
          addEdge((i - 1) * m + j, i * m + j);
        } else if (mm[i][j] == 'v') {
          if (mm[i + 1][j] == '^') flag = true;
          addEdge((i + 1) * m + j, i * m + j);
        }
      }
    }
    if (flag) {
      cout << "-1" << endl;
      continue;
    }
    memset(dp, 0, sizeof(dp));
    int ma1(0), ma2(0);
    int ans = 0;
    for (int i = 0; i < n * m; i++) {
      if (!in[i]) {
        dfs(i);
        if (ma1 < dp[i][0]) {
          ma2 = ma1;
          ma1 = dp[i][0];
        } else if (ma2 < dp[i][0]) {
          ma2 = dp[i][0];
        }
        ans = max(ans, dp[i][1]);
        ans = max(ans, dp[i][0] + dp[i][0] - 1);
      }
    }
    ans = max(ans, ma1 + ma2);
    cout << ans << endl;
  }
  return 0;
}
