#include <stdio.h>
#define DIM 1005
int A[DIM][DIM], C[2][DIM*DIM*2], dist[DIM][DIM], ruta[DIM][DIM];
int di[] = {0, 0, -1, 1}, dj[] = {-1, 1, 0, 0};
char x;
int n, m, i, j, k, X1, X2, Y1, Y2, p, u, iv, jv, ip, jp, ok, poz, rutaC, sol;
FILE *f = fopen("barbar.in","r");
FILE *g = fopen("barbar.out","w");
int min(int a, int b) {
return a<b?a:b;
}
int max(int a, int b) {
return a>b?a:b;
}
void citire() {
fscanf(f,"%d%d\n",&n,&m);
for (i = 1; i <= n; i++) {
for (j = 1; j <= m; j++) {
fscanf(f,"%c",&x);
if (x == 'I')
X1 = i, Y1 = j, A[i][j] = -2;
if (x == 'D')
A[i][j] = -1;
if (x == '*')
A[i][j] = -2;
if (x == 'O')
X2 = i, Y2 = j; //A[i][j] = -2;
}
fscanf(f,"\n");
}
}
void distante() {
for (i = 1; i <= n; i++)
for (j = 1; j <= m; j++)
if (A[i][j] == -1)
u++, C[0][u] = i, C[1][u] = j;
for (p = 1; p <= u; p++) {
ip = C[0][p], jp = C[1][p];
for (k = 0; k <= 3; k++) {
iv = ip + di[k];
jv = jp + dj[k];
if (!A[iv][jv] && iv > 0 && iv <= n && jv > 0 && jv <= m)
u++;
C[0][u] = iv;
C[1][u] = jv;
dist[iv][jv] = dist[ip][jp] + 1;
}
}
}
void drum() {
C[0][1] = X1, C[1][1] = Y1, ruta[X1][Y1] = DIM*DIM; //ruta[X2][Y2] = -1;
for (p = u = 1; p <= u; p++) {
ip = C[0][p], jp = C[1][p];
for (k = 0; k <= 3; k++) {
iv = ip + di[k];
jv = jp + dj[k];
if (!A[iv][jv] && iv > 0 && iv <= n && jv > 0 && jv <=m)
if (!ruta[iv][jv]) {
ruta[iv][jv] = min(ruta[ip][jp], dist[iv][jv]);
u++;
C[0][u] = iv;
C[1][u] = jv;
}
else
if (min(ruta[ip][jp], dist[iv][jv]) > ruta[iv][jv])
ruta[iv][jv] = min(ruta[ip][jp], dist[iv][jv]);
}
}
}
void fill(int i, int j) {
int k;
A[i][j] = -2;
for (k = 0; k <= 3; k++) {
iv = i + di[k];
jv = j + dj[k];
if (A[iv][jv] != -2 && iv > 0 && iv <= n && jv > 0 && jv <=m) {
if (iv == X2 && jv == Y2) {
ok = 1;
return ;
}
fill(iv, jv);
}
}
}
void verif() {
ok = 0;
fill(X1, Y1);
}
int main() {
citire();
distante();
drum();
verif();
if (ok) {
sol = min(max(max(ruta[X2-1][Y2], ruta[X2+1][Y2]), max(ruta[X2][Y2-1], ruta[X2][Y2+1])), ruta[X2][Y2]);
fprintf(g,"%d",sol);
}
else
fprintf(g,"-1");
fclose(f);
fclose(g);
return 0;
}