using System;
using System.Linq;
using System.Collections.Generic;

namespace Contest
{
  class Program
  {
    static void Main(string[] args)
    {
      ABC088.D();
    }
    class ABC088
    {
      public static void A()
      {
        var N = Read.Int();
        var A = Read.Int();
        Console.WriteLine(N % 500 <= A ? "Yes" : "No");
      }
      public static void B()
      {
        var N = Read.Int();
        var A = Read.IntN().OrderBy(x => -x).ToArray();
        Console.WriteLine(A.Select((x, i) => i % 2 == 0 ? x : -x).Sum());
      }
      public static void C()
      {
        var C = Read.LongMatrix(3, 3);
        bool ok = true;
        for(int i = 0; i < 2; ++i)
        {
          if (C[i, 0] - C[i + 1, 0] != C[i, 1] - C[i + 1, 1]) { ok = false; }
          if (C[i, 0] - C[i + 1, 0] != C[i, 2] - C[i + 1, 2]) { ok = false; }
          if (C[i, 1] - C[i + 1, 1] != C[i, 2] - C[i + 1, 2]) { ok = false; }
          if (C[0, i] - C[0, i + 1] != C[1, i] - C[1, i + 1]) { ok = false; }
          if (C[0, i] - C[0, i + 1] != C[2, i] - C[2, i + 1]) { ok = false; }
          if (C[1, i] - C[1, i + 1] != C[2, i] - C[2, i + 1]) { ok = false; }
        }
        Console.WriteLine(ok ? "Yes" : "No");
      }
      public static void D()
      {
        var H = Read.Int();
        var W = Read.Int();
        var S = Enumerable.Range(0, H).Select(i => Read.Str()).ToArray();
        var board = new bool[H + 2, W + 2];
        int white = 0;
        for(int i = 0; i < H; ++i)
        {
          for(int j = 0; j < W; ++j)
          {
            board[i + 1, j + 1] = S[i][j] == '.';
            if(S[i][j] == '.') { white++; }
          }
        }
        var dx = new int[] { 1, -1, 0, 0 };
        var dy = new int[] { 0, 0, 1, -1 };
        var dist = Util.Gen(H + 2, W + 2, -1);
        dist[1, 1] = 0;
        var queue = new Queue<Tuple<int, int>>();
        queue.Enqueue(new Tuple<int, int>(1, 1));
        while (queue.Count > 0)
        {
          var t = queue.Dequeue();
          for(int i = 0; i < 4; ++i)
          {
            var x = t.Item1 + dx[i];
            var y = t.Item2 + dy[i];
            if (dist[x, y] < 0 && board[x, y])
            {
              dist[x, y] = dist[t.Item1, t.Item2] + 1;
              queue.Enqueue(new Tuple<int, int>(x, y));
            }
          }
        }
        if (dist[H, W] < 0) { Console.WriteLine(-1);return; }
        Console.WriteLine(white - 1 - dist[H, W]);
      }
    }
    class ABC089
    {
      public static void A()
      {
        var N = Read.Int();
        Console.WriteLine(N / 3);
      }
      public static void B()
      {
        var N = Read.Int();
        var S = Read.StrN();
        Console.WriteLine(S.Contains("Y") ? "Four" : "Three");
      }
      public static void C()
      {
        var N = Read.Int();
        var S = Enumerable.Range(0, N).Select(i => Read.Str()).ToArray();
        var count = new long[5];
        foreach(var s in S)
        {
          switch (s[0])
          {
            case 'M': count[0]++; break;
            case 'A': count[1]++; break;
            case 'R': count[2]++; break;
            case 'C': count[3]++; break;
            case 'H': count[4]++; break;
          }
        }
        long sum = 0;
        for(int i = 0; i < 5; ++i)
        {
          for(int j = i + 1; j < 5; ++j)
          {
            for(int k = j + 1; k < 5; ++k)
            {
              sum += count[i] * count[j] * count[k];
            }
          }
        }
        Console.WriteLine(sum);
      }
      public static void D()
      {
        var H = Read.Int();
        var W = Read.Int();
        var D = Read.Int();
        var A = Read.LongMatrix(H, W);
        var place = new Tuple<int, int>[H * W + 1];
        for(int i = 0; i < H; ++i)
        {
          for(int j = 0; j < W; ++j)
          {
            place[(int)A[i, j]] = new Tuple<int, int>(i, j);
          }
        }
        var Q = Read.Int();
        var LR = Read.TupleInt(Q);
        var distance = new List<int>[D];
        for(int i = 0; i < D; ++i)
        {
          var list = new List<int>();
          distance[i] = list;
          list.Add(0);
          for (int j = 1; ; ++j)
          {
            var prev = i + D * (j - 1);
            var next = i + D * j;
            if (next > H * W) { break; }
            if (prev == 0) { list.Add(0); continue; }
            var d = Math.Abs(place[prev].Item1 - place[next].Item1) + Math.Abs(place[prev].Item2 - place[next].Item2);
            list.Add(list.Last() + d);
          }
        }
        var ans = new List<int>();
        foreach(var lr in LR)
        {
          var c = lr.Item1 % D;
          var s = lr.Item1 / D;
          var t = lr.Item2 / D;
          ans.Add(distance[c][t] - distance[c][s]);
        }
        Console.WriteLine(String.Join(Environment.NewLine, ans));
      }
    }


    class Util
    {
      public static T[,] Gen<T>(int r, int c, T v)
      {
        var matrix = new T[r, c];
        for (int i = 0; i < r; ++i)
        {
          for (int j = 0; j < c; ++j)
          {
            matrix[i, j] = v;
          }
        }
        return matrix;
      }
      public static long[] ASum(long[] array)
      {
        var res = new long[array.Length + 1];
        for (int i = 0; i < array.Length; ++i)
        {
          res[i + 1] = res[i] + array[i];
        }
        return res;
      }
      public static long[,] ASum(long[,] matrix)
      {
        var N = matrix.GetLength(0);
        var M = matrix.GetLength(1);
        var res = new long[N + 1, M + 1];
        for(int i = 0; i < N; ++i)
        {
          for(int j = 0; j < M; ++j)
          {
            res[i + 1, j + 1] = res[i, j + 1] + res[i + 1, j] - res[i, j] + matrix[i, j];
          }
        }
        return res;
      }
      public static Dictionary<T, long> Frequency<T>(T[] array)
      {
        var dict = new Dictionary<T, long>();
        foreach (var a in array)
        {
          if (!dict.ContainsKey(a)) { dict.Add(a, 0); }
          dict[a]++;
        }
        return dict;
      }
      public static bool IsPrime(long x)
      {
        var fact = Factorize(x);
        return fact.Count == 1 && fact.Values.ElementAt(0) == 1;
      }
      public static Dictionary<long, int> Factorize(long x)
      {
        var dict = new Dictionary<long, int>();
        long minp = 2;
        while (x > 1)
        {
          bool ok = false;
          for (long p = minp; p * p <= x; ++p)
          {
            if (x % p == 0)
            {
              if (!dict.ContainsKey(p))
              {
                dict.Add(p, 0);
              }
              dict[p]++;
              minp = p;
              x /= p;
              ok = true;
              break;
            }
          }
          if (!ok)
          {
            if (!dict.ContainsKey(x)) { dict.Add(x, 0); }
            dict[x]++;
            break;
          }
        }
        return dict;
      }
    }

    static class Read
{
static Queue<string> queue = new Queue<string>();
static void Enqueue() { var ss = Console.ReadLine().Split(' '); foreach (var s in ss) { queue.Enqueue(s); } }
public static int Int() { if (queue.Count == 0) { Enqueue(); } return Convert.ToInt32(queue.Dequeue()); }
public static long Long() { if (queue.Count == 0) { Enqueue(); } return Convert.ToInt64(queue.Dequeue()); }
public static string Str() { if (queue.Count == 0) { Enqueue(); } return queue.Dequeue(); }
public static int[] IntN() { return Console.ReadLine().Split(' ').Select(s => Convert.ToInt32(s)).ToArray(); }
public static long[] LongN() { return Console.ReadLine().Split(' ').Select(s => Convert.ToInt64(s)).ToArray(); }
public static ulong[] ULongN() { return Console.ReadLine().Split(' ').Select(s => Convert.ToUInt64(s)).ToArray(); }
public static string[] StrN() { return Console.ReadLine().Split(' '); }
public static Tuple<int, int>[] TupleInt(int n) { List<Tuple<int, int>> list = new List<Tuple<int, int>>(); for (int i = 0; i < n; ++i) { var ab = Read.IntN(); list.Add(new Tuple<int, int>(ab[0], ab[1])); } return list.ToArray(); }
public static Tuple<long, long>[] TupleLong(int n) { List<Tuple<long, long>> list = new List<Tuple<long, long>>(); for (int i = 0; i < n; ++i) { var ab = Read.LongN(); list.Add(new Tuple<long, long>(ab[0], ab[1])); } return list.ToArray(); }
public static Tuple<string, string>[] TupleStr(int n) { List<Tuple<string, string>> list = new List<Tuple<string, string>>(); for (int i = 0; i < n; ++i) { var ab = Read.StrN(); list.Add(new Tuple<string, string>(ab[0], ab[1])); } return list.ToArray(); }
public static Tuple<double, double>[] TupleDouble(int n) { List<Tuple<double, double>> list = new List<Tuple<double, double>>(); for (int i = 0; i < n; ++i) { var ab = Read.LongN(); list.Add(new Tuple<double, double>(ab[0], ab[1])); } return list.ToArray(); }
public static long[,] LongMatrix(int r, int c) { var mat = new long[r, c]; for (int i = 0; i < r; ++i) { var x = Read.LongN(); for (int j = 0; j < c; ++j) { mat[i, j] = x[j]; } } return mat; }
public static Dictionary<int, HashSet<int>> AdjacencyList(int N, int M, bool isDirectional = false)
{
Dictionary<int, HashSet<int>> dict = new Dictionary<int, HashSet<int>>();
for (int i = 0; i <= N; ++i) { dict.Add(i, new HashSet<int>()); }
        for (int i = 0; i < M; ++i) { var ab = Read.IntN(); if (!dict[ab[0]].Contains(ab[1])) { dict[ab[0]].Add(ab[1]); } if (!isDirectional && !dict[ab[1]].Contains(ab[0])) { dict[ab[1]].Add(ab[0]); } }
        return dict;
}
public static Dictionary<int, Dictionary<int, long>> AdjacencyListWithWeight(int N, int M)
{
Dictionary<int, Dictionary<int, long>> dict = new Dictionary<int, Dictionary<int, long>>(); for (int i = 0; i <= N; ++i) { dict.Add(i, new Dictionary<int, long>()); }
for (int i = 0; i < M; ++i) { var ab = Read.IntN(); dict[ab[0]].Add(ab[1], ab[2]); dict[ab[1]].Add(ab[0], ab[2]); }
return dict;
}
}
    }
}


Measured memory_bytes: 13524