#include <bits/stdc++.h>
using namespace std;
const int MD = (int)1e9 + 7;
void dbg() { cerr << "\n"; }
template <class T, class... T2>
void dbg(const T& fst, const T2&... rst) {
  cerr << fst << ": ";
  dbg(rst...);
}
template <class T>
void amax(T& a, T b) {
  a = max(a, b);
}
vector<vector<int>> rd;
class LCA {
 private:
  vector<vector<int>> to;
  vector<int> depth;
  void dfs(const vector<vector<int>>& edges, int curr, int prev, int cnt) {
    depth[curr] = cnt;
    if (prev != -1) {
      to[curr].push_back(prev);
      int j = prev;
      for (int(k) = 0; (k) < ((int)(to[j]).size()); (k)++) {
        j = to[j][k];
        to[curr].push_back(j);
      }
    }
    for (int(i) = 0; (i) < ((int)(edges[curr]).size()); (i)++) {
      int next = edges[curr][i];
      if (next != prev) dfs(edges, next, curr, cnt + 1);
    }
  }
  int climb(int curr, int dist) {
    for (int i = 0; dist > 0; ++i) {
      if (dist % 2 == 1) curr = to[curr][i];
      dist /= 2;
    }
    return curr;
  }

 public:
  LCA(const vector<vector<int>>& edges, int root) {
    int n = (int)(edges).size();
    to.assign(n, vector<int>());
    depth.assign(n, 0);
    dfs(edges, root, -1, 0);
  }
  int query(int a, int b) {
    pair<int, int> dist(0, 0);
    int diff = depth[a] - depth[b];
    if (diff < 0) {
      b = climb(b, -diff);
      dist.second += -diff;
    } else {
      a = climb(a, diff);
      dist.first += diff;
    }
    if (a == b) return dist.first + dist.second;
    for (int x = (int)(to[a]).size() - 1; x >= 0; --x) {
      if (x < (int)(to[a]).size() && to[a][x] != to[b][x]) {
        a = to[a][x];
        b = to[b][x];
        dist.first += 1 << x;
        dist.second += 1 << x;
      }
    }
    return dist.first + dist.second + 2;
  }
};
int main() {
  int n, u, v;
  cin >> n >> u >> v;
  u--;
  v--;
  rd.resize(n);
  for (int(i) = 0; (i) < (n - 1); (i)++) {
    int a, b;
    cin >> a >> b;
    rd[a - 1].push_back(b - 1);
    rd[b - 1].push_back(a - 1);
  }
  LCA mlca(rd, 0);
  int ans = 0;
  map<pair<int, int>, int> mp;
  queue<tuple<int, int, int>> que;
  que.emplace(u, v, 0);
  while (!que.empty()) {
    int cu, cv, ky;
    tie(cu, cv, ky) = que.front();
    que.pop();
    int wd = mlca.query(cu, cv);
    for (auto x : rd[cu]) {
      if (x != cv && !mp.count(pair<int, int>(x, cv))) {
        que.emplace(x, cv, ky + 1);
        mp[pair<int, int>(x, cv)]++;
        ans = max(ans, ky + 1);
      }
    }
    for (auto y : rd[cv]) {
      if (y != cu && !mp.count(pair<int, int>(cu, y))) {
        if (mlca.query(cu, y) <= wd) {
          que.emplace(cu, y, ky + 1);
          mp[pair<int, int>(cu, y)]++;
          ans = max(ans, ky + 1);
        }
      }
    }
  }
  cout << ans / 2 << "\n";
  return 0;
}
