// i must be the reason why
// you have given up your smiles
// and the hope inside your life has been stolen
// i must be the reason why
// you have told me all these lies
// that i will lead a happier life without you by my side
// дальше текст забыл

// t.me/truebaza <---- лучший тг канал
// t.me/truebaza <---- лучший тг канал
// t.me/truebaza <---- лучший тг канал
// t.me/truebaza <---- лучший тг канал
// t.me/truebaza <---- лучший тг канал
// t.me/truebaza <---- лучший тг канал
#pragma GCC optimize("O3")
#include <bits/stdc++.h>
#include <ext/pb_ds/assoc_container.hpp>
using namespace __gnu_pbds;
using namespace std;
typedef tree<int, null_type, less<>, rb_tree_tag, tree_order_statistics_node_update> ordered_set;
#define fastio cin.tie(0), ios_base::sync_with_stdio(false)
#define all(x) (x).begin(), (x).end()
#define INF ((1ll << 60) - 1)

struct ST {
    struct Node {
        int mx = 0, add = 0;
    };

    Node t[4 * 300000];

    inline Node merge(Node a, Node b) {
        return Node(max(a.mx + a.add, b.mx + b.add), 0);
    }

    inline void push(int v) {
        if (t[v].add == 0) return;
        t[v * 2].add += t[v].add;
        t[v * 2 + 1].add += t[v].add;
        t[v].mx += t[v].add;
        t[v].add = 0;
    }

    void upd(int v, int vl, int vr, int l, int r, int x) {
        if (vl >= l && vr <= r) {
            t[v].add += x;
            return;
        }
        push(v);
        int m = (vl + vr) / 2;
        if (l <= m) upd(v * 2, vl, m, l, r, x);
        if (r > m) upd(v * 2 + 1, m + 1, vr, l, r, x);
        t[v] = merge(t[v * 2], t[v * 2 + 1]);
    }

    int get(int v, int vl, int vr, int l, int r) {
        if (vl >= l && vr <= r) {
            return t[v].mx + t[v].add;
        }
        push(v);
        int res = -INF;
        int m = (vl + vr) / 2;
        if (l <= m) res = get(v * 2, vl, m, l, r);
        if (r > m) res = max(res, get(v * 2 + 1, m + 1, vr, l, r));
        return res;
    }

};
vector<vector<int>> g;
struct hld {
    vector<int> pos;
    vector<int> p;
    vector<int> phld;
    vector<int> sz;
    ST t;
    hld(int n) {
        pos.resize(n);
        p.resize(n);
        phld.resize(n);
        sz.resize(n);
        calcsz(0, -1);
        build(0, 0); // DO NOT CHANGE TO -1
    }
    int te = 0;
    void calcsz(int v, int pr) {
        p[v] = pr;
        sz[v] = 1;
        for (auto w : g[v]) {
            calcsz(w, v);
            sz[v] += sz[w];
        }
    }

    void build(int v, int prh) {
        sort(all(g[v]), [&](auto a, auto b){return sz[a] > sz[b];});
        bool he = true;
        phld[v] = prh;
        pos[v] = te++;
        for (auto w : g[v]) {
            if (he) {
                build(w, prh);
                he = false;
            } else {
                build(w, w);
            }
        }
    }

    int get(int v) {
        vector<pair<int, int>> segs;
        while (true) {
            int le = pos[phld[v]], re = pos[v];
            segs.push_back({le, re});
            if (le == 0) break;
            v = p[phld[v]];
        }
        sort(all(segs));
        int br = 0;
        for (int i = 0; i < segs.size(); ++i) {
            if (i == 0 && segs[i].first > 0) {
                br = max(br, t.get(1, 0, te - 1, 0, segs[0].first - 1));
            }
            if (i + 1 == segs.size() && segs[i].second + 1 < te) {
                br = max(br, t.get(1, 0, te - 1, segs[i].second + 1, te - 1));
            }
            if (i + 1 < segs.size() && segs[i].second + 1 <= segs[i + 1].first - 1) {
                br = max(br, t.get(1, 0, te - 1, segs[i].second + 1, segs[i + 1].first - 1));
            }
        }
        return br;
    }

    void upd(int v) {
        while (true) {
            int le = pos[phld[v]], re = pos[v];
            t.upd(1, 0, te - 1, le, re, 1);
            if (le == 0) break;
            v = p[phld[v]];
        }
    }

};

vector<int> s;
vector<int> v;

auto main() -> signed { // t.me/truebaza <---- лучший тг канал
    fastio;
    int n, q;
    cin >> n >> q;
    g.resize(n);
    s.resize(n);
    for (int i = 1; i < n; ++i) {
        int pr;
        cin >> pr;
        pr--;
        g[pr].push_back(i);
    }
    for (auto& i : s) cin >> i;
    set<pair<int, int>> st;
    vector<int> order;
    // sort vertices by greedy algorithm
    st.insert({INF, 0});
    while (!st.empty()) {
        auto [val, v] = *st.rbegin();
        st.erase(*st.rbegin());
        order.push_back(v);
        for (auto w : g[v]) {
            st.insert({s[w], w});
        }
    }
    // add vertex, then find the biggest subtree that is not our ancestor,
    // answer for it is amount of vertices before us - this size???
    vector<int> ans(n, 0);
    hld H(n);
    for (int i = 1; i < n; ++i) {
        int v = order[i];
        int bsz = H.get(v);
        ans[v] = i - bsz;
        H.upd(v);
    }
    while (q--) {
        int v;
        cin >> v;
        v--;
        cout << ans[v] << ' ';
    }
}