#include <bits/stdc++.h>
using namespace std;
const int maxn = 1e5 + 5;
vector<int> G[maxn];
int L[maxn], R[maxn], label;
int fa[maxn][20], dep[maxn];
void dfs(int u, int father) {
  L[u] = ++label;
  fa[u][0] = father;
  for (int i = 1; i < 20; ++i) fa[u][i] = fa[fa[u][i - 1]][i - 1];
  for (int i = 0; i < (int)G[u].size(); ++i) {
    int v = G[u][i];
    dep[v] = dep[u] + 1;
    dfs(v, u);
  }
  R[u] = label;
}
inline int lca(int u, int v) {
  if (dep[u] != dep[v]) {
    if (dep[u] < dep[v]) swap(u, v);
    for (int i = 19; i >= 0; --i)
      if (dep[fa[u][i]] >= dep[v]) {
        u = fa[u][i];
        if (dep[u] == dep[v]) break;
      }
  }
  if (u == v) return u;
  for (int i = 19; i >= 0; --i)
    if (fa[u][i] != fa[v][i]) {
      u = fa[u][i];
      v = fa[v][i];
    }
  return fa[u][0];
}
struct Segtree {
  Segtree *l, *r;
  int cnt;
} tr[maxn * 20], *root[maxn];
int tot = 0;
inline Segtree *newnode() {
  Segtree *t = (tr + tot++);
  t->l = t->r = 0;
  t->cnt = 0;
  return t;
}
inline int get_cnt(Segtree *p) { return p ? p->cnt : 0; }
inline Segtree *get_l(Segtree *p) { return p ? p->l : 0; }
inline Segtree *get_r(Segtree *p) { return p ? p->r : 0; }
Segtree *updata(Segtree *p, int l, int r, int x, int y) {
  Segtree *t = newnode();
  if (l == x && r == y) {
    t->cnt = get_cnt(p) + 1;
    t->l = get_l(p);
    t->r = get_r(p);
    return t;
  }
  int mid = (x + y) >> 1;
  if (r <= mid) {
    t->r = get_r(p);
    t->l = updata(get_l(p), l, r, x, mid);
  } else if (l > mid) {
    t->l = get_l(p);
    t->r = updata(get_r(p), l, r, mid + 1, y);
  } else {
    t->l = updata(get_l(p), l, mid, x, mid);
    t->r = updata(get_r(p), mid + 1, r, mid + 1, y);
  }
  t->cnt = get_cnt(p);
  return t;
}
int ask(Segtree *p, int x, int l, int r) {
  if (!p) return 0;
  if (l == r) return p->cnt;
  int mid = (l + r) >> 1;
  if (x <= mid)
    return p->cnt + ask(p->l, x, l, mid);
  else
    return p->cnt + ask(p->r, x, mid + 1, r);
}
inline int cal(int u, int year) {
  if (!u) return 0;
  return ask(root[year], L[u], 1, label);
}
inline int query(int a, int b, int k, int y, int now) {
  int lc = lca(a, b);
  int u = a;
  for (int i = 19; i >= 0; --i) {
    int t = fa[u][i];
    if (dep[t] < dep[lc]) continue;
    int v = cal(fa[a][0], now) - cal(fa[t][0], now) -
            (cal(fa[a][0], y) - cal(fa[t][0], y));
    v = dep[fa[a][0]] - dep[fa[t][0]] - v;
    if (v < k) u = t;
  }
  if (u != lc) u = fa[u][0];
  if (u == lc && b == lc) return -1;
  int cnt = cal(fa[a][0], now) - cal(fa[u][0], now) -
            (cal(fa[a][0], y) - cal(fa[u][0], y));
  cnt = dep[fa[a][0]] - dep[fa[u][0]] - cnt;
  if (cnt == k) return u;
  k -= cnt;
  u = b;
  for (int i = 19; i >= 0; --i) {
    int t = fa[u][i];
    if (dep[t] < dep[lc] + 1) continue;
    int v = cal(t, now) - cal(lc, now) - (cal(t, y) - cal(lc, y));
    v = dep[t] - dep[lc] - v;
    if (v >= k) u = t;
  }
  if (u == b) return -1;
  return u;
}
int main() {
  int n, rt;
  scanf("%d", &n);
  for (int i = 1; i <= n; ++i) {
    int f;
    scanf("%d", &f);
    if (!f)
      rt = i;
    else
      G[f].push_back(i);
  }
  label = 0;
  dep[rt] = 1;
  dfs(rt, 0);
  int m;
  scanf("%d", &m);
  root[0] = newnode();
  for (int i = 1; i <= m; ++i) {
    int t;
    scanf("%d", &t);
    if (t == 1) {
      int u;
      scanf("%d", &u);
      root[i] = updata(root[i - 1], L[u], R[u], 1, label);
    } else {
      root[i] = root[i - 1];
      int a, b, k, y;
      scanf("%d%d%d%d", &a, &b, &k, &y);
      printf("%d\n", query(a, b, k, y, i));
    }
  }
  return 0;
}
