#include <iostream>
#include <map>
#include <queue>
#include <algorithm>
#include <vector>
#include <cstdio>
#include <cstring>

using namespace std;

#define MAX_H 12
#define MAX_W 12
#define INF (1<<28)
int h, w;
int F[MAX_H][MAX_W];

bool dfs_used[MAX_H][MAX_W];
const int dy[] = {0, 1, 0, -1}, dx[] = {1, 0, -1, 0};
int dfs(int y, int x, int n) {
    F[y][x] = n;
    int cnt = 1;
    for (int i = 0; i < 4; i++) {
        int ny = y + dy[i], nx = x + dx[i];
        if (0 <= ny && ny < h && 0 <= nx && nx < w && !dfs_used[ny][nx] && F[ny][nx] == INF) 
            cnt += dfs(ny, nx, n);
    }
    return cnt;
}

int ice_count[MAX_H*MAX_W];
int ice_lump_count;
int dist_from_goal[MAX_H][MAX_W];
struct S {
    int y, x, t;
    S(int y, int x, int t) : y(y), x(x), t(t) {}
};

int sy, sx, gy, gx;
void init() {
    memset(dfs_used, 0, sizeof(dfs_used));
    memset(ice_count, 0, sizeof(ice_count));
    memset(dist_from_goal, -1, sizeof(dist_from_goal));
    int n = 1;
    for (int i = 0; i < h; i++) {
        for (int j = 0; j < w; j++) {
            if (F[i][j] == INF) {
                ice_count[n] = dfs(i, j, n);
                n++;
            }
        }
    }
    ice_lump_count = n;

    // 各タイルに対しbfsで氷を考慮しない場合のゴールまでの最短距離を求める.
    queue<S> q;
    q.push(S(gy, gx, 0));
    dist_from_goal[gy][gx] = 0;
    while (!q.empty()) {
        S p = q.front(); q.pop();
        for (int i = 0; i < 4; i++) {
            int ny = p.y + dy[i], nx = p.x + dx[i];
            if (0 <= ny && ny < h && 0 <= nx && nx < w &&
                    dist_from_goal[ny][nx] < 0 && F[ny][nx] >= 0) {
                dist_from_goal[ny][nx] = p.t+1;
                q.push(S(ny, nx, p.t+1));
            }
        }
    }
}

bool dls_used[MAX_H][MAX_W];
bool __used[MAX_H][MAX_W];
int count_used_ice(int y, int x) {
    int cnt = (dls_used[y][x] ? 1 : 0);
    //if (cnt == 1) cout << "count_used_ice: " << y << ',' << x << endl;
    for (int i = 0; i < 4; i++) {
        int ny = y + dy[i], nx = x + dx[i];
        if (0 <= ny && ny < h && 0 <= nx && nx < w && !__used[ny][nx] && F[ny][nx] == F[y][x]) {
            __used[ny][nx] = true;
            cnt += count_used_ice(ny, nx);
        }
    }
    return cnt;
}

bool ice_break(int y, int x) {
    memset(__used, 0, sizeof(__used));
    __used[y][x] = true;
    int c = count_used_ice(y, x);
    //cout << "icebreak: " << c << endl;
    return c * 2 > ice_count[F[y][x]];
}

bool dls(int y, int x, int depth) {
    //cout << y << ',' << x << ',' << depth << endl;
    if (depth == 0) 
        return y == gy && x == gx;
    if (dist_from_goal[y][x] > depth) 
        return false;
    for (int i = 0; i < 4; i++) {
        int ny = y + dy[i];
        int nx = x + dx[i];
        if (0 <= ny && ny < h && 0 <= nx && nx < w
                && !dls_used[ny][nx] && F[ny][nx] >= 0) {
            dls_used[ny][nx] = true;
            if (F[ny][nx] > 0) 
                if (ice_break(ny, nx)) {
                    dls_used[ny][nx] = false;
                    continue;
                }
            if (dls(ny, nx, depth-1)) {
                //cout << endl;
                //for (int k = 0; k < h; k++) {
                //    for (int l = 0; l < w; l++)
                //        cout << dls_used[k][l] << ' ';
                //    cout << endl;
                //}
                dls_used[ny][nx] = false;
                return true;
            }
            dls_used[ny][nx] = false;
        }
    }
    return false;
}

int iddfs() {
    int depth = 0;
    int y = sy, x = sx;
    while (true) {
        memset(dls_used, 0, sizeof(dls_used));
        dls_used[y][x] = true;
        if (dls(y, x, depth)) return depth;
        depth++;
    }
}

void debug() {
    printf("Ice lump count: %d\n", ice_lump_count);
    printf("Ice count: %d\n\t", ice_lump_count);
    for (int i = 0; i < ice_lump_count; i++) 
        printf("%3d ", ice_count[i]);
    printf("\n");
    for (int i = 0; i < h; i++) {
        for (int j = 0; j < w; j++) {
            printf("%4d ", F[i][j]);
        }
        printf("\n");
    }
    for (int i = 0; i < h; i++) {
        for (int j = 0; j < w; j++) {
            printf("%4d ", dist_from_goal[i][j]);
        }
        printf("\n");
    }
}

int main() {
    while (cin >> w >> h, w || h) {
        for (int i = 0; i < h; i++) {
            for (int j = 0; j < w; j++) {
                char t; cin >> t;
                switch (t) {
                    case 'S':
                        sy = i, sx = j;
                        F[i][j] = 0;
                        break;
                    case 'G':
                        gy = i, gx = j;
                        F[i][j] = 0;
                        break;
                    case '.': 
                        F[i][j] = 0;
                        break;
                    case '#':
                        F[i][j] = -1;
                        break;
                    case 'X':
                        F[i][j] = INF;
                        break;
                }
            }
        }
        init();
        //debug();
        cout << iddfs() << endl;
    }
    return 0;
}

Measured memory_bytes: 1204