#include <cstdio>
#include <cstdint>
#include <algorithm>
#include <vector>
#include <map>
#include <string>
#include <queue>

const size_t di[]={size_t(-1), 0, 1, 0};
const size_t dj[]={0, 1, 0, size_t(-1)};

class Cube {
  std::string s;

public:
  Cube(): s("rmbgyc") {}
  Cube(const Cube& c): s(c.s) {}
  Cube(const std::string& s): s(s) {}

  bool operator <(const Cube& other) const {
    return s < other.s;
  }

  bool operator !=(const Cube& other) const {
    return s != other.s;
  }

  Cube roll(int k) const {
    std::vector<size_t> idx;
    if (k == 0) {
      idx = std::vector<size_t>{1, 5, 2, 0, 4, 3};
    } else if (k == 1) {
      idx = std::vector<size_t>{4, 1, 0, 3, 5, 2};
    } else if (k == 2) {
      idx = std::vector<size_t>{3, 0, 2, 5, 4, 1};
    } else if (k == 3) {
      idx = std::vector<size_t>{2, 1, 5, 3, 0, 4};
    }

    std::string tmp(6, '.');
    for (size_t i=0; i<6; ++i)
      tmp[i] = s[idx[i]];

    // fprintf(stderr, "%s -[%d]-> %s\n", s.c_str(), k, tmp.c_str());
    return Cube(tmp);
  }

  void inspect() const {
    // fprintf(stderr, "%s\n", s.c_str());
  }

  char operator [](size_t i) const {
    return s[i];
  }
};

class State {
  size_t i, j;
  Cube c;
  size_t cct;

public:
  State(size_t i, size_t j, const Cube &c, size_t cct=0):
    i(i), j(j), c(c), cct(cct)
  {}

  size_t h() const { return i; }
  size_t w() const { return j; }
  size_t count() const { return cct; }

  bool operator <(const State& other) const {
    if (i != other.i) return i < other.i;
    if (j != other.j) return j < other.j;
    if (cct != other.cct) return cct < other.cct;
    return c < other.c;
  }

  bool operator !=(const State& other) const {
    if (i != other.i) return true;
    if (j != other.j) return true;
    if (cct != other.cct) return true;
    return c != other.c;
  }

  bool visit(char ch, const std::string& v) {
    if (ch == 'w' || ch == '#') return true;
    if (v[cct] != ch) return false;
    if (c[0] != ch) return false;
    ++cct;
    return true;
  }

  const Cube& cube() const {
    return c;
  }

  void inspect() const {
    // fprintf(stderr, "on %zu %zu\n", i, j);
    // c.inspect();
    // fprintf(stderr, "visited [:%zu]\n", cct);
    // fprintf(stderr, "\n");
  }
};

int testcase_ends() {
  size_t w, h;
  scanf("%zu %zu", &w, &h);

  if (w == 0 && h == 0) return 1;

  std::vector<std::string> c(h);
  for (size_t i=0; i<h; ++i) {
    char buf[32];
    scanf("%s", buf);
    c[i] = buf;
  }
  char buf[8];
  scanf("%s", buf);
  std::string v=buf;

  size_t si=-1, sj=-1, gi=-1, gj=-1;
  for (size_t i=0; i<h; ++i)
    for (size_t j=0; j<w; ++j)
      if (c[i][j] == '#') {
        si = i;
        sj = j;
      } else if (c[i][j] == v[5]) {
        gi = i;
        gj = j;
      }

  std::queue<State> q;
  std::map<State, int> dp;

  State init(si, sj, Cube());
  q.emplace(init);
  dp[init] = 0;
  int INF=1e9, res=INF;
  while (!q.empty()) {
    State st=q.front();
    q.pop();

    for (int k=0; k<4; ++k) {
      size_t ni=st.h()+di[k], nj=st.w()+dj[k];
      if (!(ni < h && nj < w)) continue;
      if (c[ni][nj] == 'k') continue;

      State nst(ni, nj, st.cube().roll(k), st.count());
      if (!nst.visit(c[ni][nj], v)) continue;

      auto it=dp.lower_bound(nst);
      if (it == dp.end() || it->first != nst) {
        it = dp.emplace_hint(it, nst, dp.at(st)+1);
        q.emplace(nst);
      } else if (it->second > dp.at(st) + 1) {
        it->second = dp.at(st) + 1;
        q.emplace(nst);
      } else {
        continue;
      }

      // fprintf(stderr, "cost: %d\n", it->second);
      it->first.inspect();

      if (it->first.count() == 6)
        res = std::min(res, it->second);
    }
  }

  if (res < INF) {
    printf("%d\n", res);
  } else {
    printf("unreachable\n");
  }
  return 0;
}

int main() {
  while (!testcase_ends()) {}
}



Measured memory_bytes: 12424