#include <bits/stdc++.h>
const int N = 150010;
int n, val[N];
int las[N], nxt[N << 1], to[N << 1], cnt;
inline void add(int u, int v) {
  ++cnt;
  to[cnt] = v;
  nxt[cnt] = las[u];
  las[u] = cnt;
}
inline void add() {
  int a, b;
  scanf("%d%d", &a, &b);
  add(a, b);
  add(b, a);
}
long long k[N], b[N];
int id[N << 2];
inline void swap(int &x, int &y) {
  int t = x;
  x = y;
  y = t;
}
inline void swap(long long &x, long long &y) {
  long long t = x;
  x = y;
  y = t;
}
inline long long max(long long a, long long b) { return a > b ? a : b; }
void update(int rt, int l, int r, int i) {
  int m = (l + r) >> 1;
  long long yl1 = k[id[rt]] * l + b[id[rt]], yr1 = k[id[rt]] * r + b[id[rt]],
            yl2 = k[i] * l + b[i], yr2 = k[i] * r + b[i];
  if (yl1 >= yl2 && yr1 >= yr2) return;
  if (yl1 <= yl2 && yr1 <= yr2) return (void)(id[rt] = i);
  if (k[i] * m + b[i] >= k[id[rt]] * m + b[id[rt]])
    swap(id[rt], i), swap(yl1, yl2);
  yl2 >= yl1 ? update(rt << 1, l, m, i) : update(rt << 1 | 1, m + 1, r, i);
}
long long query(int rt, int l, int r, int p) {
  long long now = k[id[rt]] * p + b[id[rt]];
  if (l == r) return now;
  int m = (l + r) >> 1;
  return max(
      now, p <= m ? query(rt << 1, l, m, p) : query(rt << 1 | 1, m + 1, r, p));
}
void clear(int rt, int l, int r) {
  id[rt] = 0;
  if (l == r) return;
  int m = (l + r) >> 1;
  clear(rt << 1, l, m);
  clear(rt << 1 | 1, m + 1, r);
}
int q[N], fa[N], siz[N], son[N], dep[N];
long long sum[N], sum1[N], ans;
bool vis[N];
int bfs(int &x) {
  int i, hd, tl;
  for (fa[q[hd = tl = 1] = x] = 0; hd <= tl; hd++)
    for (i = las[q[hd]]; i; i = nxt[i])
      if (!vis[to[i]] && to[i] != fa[q[hd]]) fa[q[++tl] = to[i]] = q[hd];
  son[x] = 1e9;
  for (hd = tl; hd >= 1; hd--) {
    siz[q[hd]] = 1;
    son[q[hd]] = 0;
    for (i = las[q[hd]]; i; i = nxt[i])
      if (!vis[to[i]] && to[i] != fa[q[hd]]) {
        siz[q[hd]] += siz[to[i]];
        if (son[q[hd]] < siz[to[i]]) son[q[hd]] = siz[to[i]];
      }
    if (son[q[hd]] < tl - siz[q[hd]]) son[q[hd]] = tl - siz[q[hd]];
    if (son[q[hd]] < son[x]) x = q[hd];
  }
  return tl;
}
int _n;
void calc(int rt, int x) {
  int i, hd, tl;
  sum[x] = sum1[x] = val[x];
  dep[x] = 1;
  for (fa[q[hd = tl = 1] = x] = 0; hd <= tl; hd++)
    for (i = las[q[hd]]; i; i = nxt[i])
      if (!vis[to[i]] && to[i] != fa[q[hd]])
        fa[q[++tl] = to[i]] = q[hd], sum[q[tl]] = sum[q[hd]] + val[q[tl]],
                     dep[q[tl]] = dep[q[hd]] + 1,
                     sum1[q[tl]] = sum[q[tl]] + sum1[q[hd]];
  for (hd = 1; hd <= tl; hd++)
    ans = max(ans, query(1, 1, _n, dep[q[hd]]) + sum1[q[hd]]);
  sum[x] = val[rt] + val[x];
  sum1[x] = sum[x] + val[x];
  dep[x] = 2;
  for (hd = 1; hd <= tl; hd++)
    for (i = las[q[hd]]; i; i = nxt[i])
      if (!vis[to[i]] && to[i] != fa[q[hd]])
        sum[to[i]] = sum[q[hd]] + val[to[i]], dep[to[i]] = dep[q[hd]] + 1,
        sum1[to[i]] = sum1[q[hd]] + (long long)val[to[i]] * dep[to[i]];
  for (hd = 1; hd <= tl; hd++)
    ++cnt, k[cnt] = sum[q[hd]], b[cnt] = sum1[q[hd]],
           ans = max(ans, sum1[q[hd]]), update(1, 1, _n, cnt);
}
int stk[N], top;
void dfs(int x) {
  _n = bfs(x);
  vis[x] = true;
  ++cnt;
  k[cnt] = val[x];
  b[cnt] = val[x];
  update(1, 1, _n, cnt);
  for (int i = las[x]; i; i = nxt[i])
    if (!vis[to[i]]) calc(x, to[i]), stk[++top] = to[i];
  clear(1, 1, _n);
  cnt = 0;
  while (top) calc(x, stk[top--]);
  clear(1, 1, _n);
  cnt = 0;
  for (int i = las[x]; i; i = nxt[i])
    if (!vis[to[i]]) dfs(to[i]);
}
int main() {
  int i;
  scanf("%d", &n);
  for (i = 1; i < n; i++) add();
  cnt = 0;
  for (i = 1; i <= n; i++) scanf("%d", &val[i]);
  dfs(1);
  printf("%lld\n", ans);
  return 0;
}
