#include <bits/stdc++.h>
#define err(args...) {}
#ifdef DEBUG
#include "_debug.cpp"
#endif
using namespace std;
using ll = long long;
template <bool Directed> struct graph {
    int n;
    vector<vector<int>> adj;
    graph(int n) : n(n), adj(n + 1) {}
    void add_edge(int u, int v) {
        adj[u].push_back(v);
        if(not Directed) adj[v].push_back(u);
    }
};
template <bool Directed> vector<int> bfs(graph<Directed>& g, int s) {
    vector<int> d(g.n + 1, -1);
    d[s] = 0;
    queue<int> q({s});
    while(not q.empty()) {
        int u = q.front(); q.pop();
        for(int v : g.adj[u]) {
            if(d[v] == -1) {
                d[v] = d[u] + 1;
                q.push(v);
            }
        }
    }
    return d;
}
vector<int> diameter_nodes(graph<0>& g) {
    auto d1 = bfs(g, 1);
    int n1 = max_element(d1.begin(), d1.end()) - d1.begin();
    auto d2 = bfs(g, n1);
    int n2 = max_element(d2.begin(), d2.end()) - d2.begin();
    return {n1, n2};
}
int main() {
    ios_base::sync_with_stdio(false);
    cin.tie(0);
    int n, m;
    cin >> n >> m;
    graph<0> g(n);
    for(int i = 1; i < n; i++) {
        int u, v;
        cin >> u >> v;
        g.add_edge(u, v);
    }
    vector<int> c(n + 1);
    for(int i = 1; i <= n; i++) {
        cin >> c[i];
    }
    vector<int> ans(n + 1);
    for(int s : diameter_nodes(g)) {
        vector<int> h(n + 1), max_subtree(n + 1), depth(n + 1), unique_cities;
        vector<int> unique_goods(m + 1);
        int n_unique = 0;
        function<void(int, int)> dfs1 = [&](int u, int from) {
            for(int v : g.adj[u]) {
                if(v != from) {
                    dfs1(v, u);
                    if(h[v] > h[max_subtree[u]]) max_subtree[u] = v;
                }
            }
            h[u] = h[max_subtree[u]] + 1;
        };
        dfs1(s, 0);
        function<void(int, int)> dfs2 = [&](int u, int from) {
            depth[u] = depth[from] + 1;
            auto add = [&](int v) {
                unique_cities.push_back(v);
                n_unique += ++unique_goods[c[v]] == 1;
            };
            auto remove = [&](int v) {
                if(not unique_cities.empty() and unique_cities.back() == v) {
                    unique_cities.pop_back();
                    n_unique -= unique_goods[c[v]]-- == 1;
                }
            };
            auto filter = [&](int max_allowed_depth) {
                while(not unique_cities.empty() and depth[unique_cities.back()] >= max_allowed_depth) {
                    remove(unique_cities.back());
                }
            };
            int n_children = g.adj[u].size() - bool(from);
            if(n_children >= 1) {
                if(n_children > 1) {
                    int second_max_subtree = 0;
                    for(int v : g.adj[u]) {
                        if(v != from and v != max_subtree[u] and h[v] > h[second_max_subtree]) {
                            second_max_subtree = v;
                        }
                    }
                    filter(depth[u] - h[second_max_subtree]);
                }
                add(u);
                dfs2(max_subtree[u], u);
                remove(u);
            }
            filter(depth[u] - (h[u] - 1));
            ans[u] = max(ans[u], n_unique);
            for(int v : g.adj[u]) {
                if(v != from and v != max_subtree[u]) {
                    add(u);
                    dfs2(v, u);
                    remove(u);
                }
            }
        };
        dfs2(s, 0);
    }
    for(int i = 1; i <= n; i++) {
        cout << ans[i] << endl;
    }
    return 0;
}



Measured memory_bytes: 54620