#include<bits/stdc++.h>
#define ll long long
using namespace std;
const int N=2e5+3;
inline int read(){
int x=0,f=1;
char ch=getchar();
while(ch>'9'||ch<'0')
{
if(ch=='-')
{
f=-f;
}
ch=getchar();
}
while(ch>='0'&&ch<='9')
{
x=x*10+ch-'0';
ch=getchar();
}
return x*f;
}
int n,h[N],e[N*2],ne[N*2],tot,m;
ll s[N],col[N];
void add(int a,int b)
{
e[++tot]=b,ne[tot]=h[a],h[a]=tot;
}
int dep[N],fa[N],size[N],id[N],top[N],son[N],rk[N],cnt;
ll ans1;
void dfs1(int u,int ba)
{
size[u]=1;
s[u]=col[u];
for(int i=h[u];i;i=ne[i])
{
int v=e[i];
if(v!=ba)
{
dep[v]=dep[u]+1;
fa[v]=u;
dfs1(v,u);
size[u]+=size[v];
if(size[son[u]]<size[v])
{
son[u]=v;
}
s[u]+=s[v];
}
}
ans1+=s[u]*s[u];
}
void dfs2(int u)
{
id[u]=++cnt;
rk[cnt]=u;
if(son[u])
{
top[son[u]]=top[u];
dfs2(son[u]);
}
for(int i=h[u];i;i=ne[i])
{
int v=e[i];
if(v!=fa[u]&&v!=son[u])
{
top[v]=v;
dfs2(v);
}
}
}
struct Tree
{
ll sum,lazy;
}tr[N<<2];
void pushup(int rt)
{
tr[rt].sum=tr[rt<<1].sum+tr[rt<<1|1].sum;
}
void build(int rt,int l,int r)
{
tr[rt].lazy=0;
if(l==r)
{
tr[rt].sum=s[rk[l]];
return;
}
int mid=(l+r)>>1;
build(rt<<1,l,mid);
build(rt<<1|1,mid+1,r);
pushup(rt);
}
void pushdown(int rt,int l,int r)
{
if(tr[rt].lazy==0)
{
return;
}
int mid=(l+r)>>1;
tr[rt<<1].sum+=tr[rt].lazy*(ll)(mid-l+1),tr[rt<<1|1].sum+=tr[rt].lazy*(ll)(r-mid);
tr[rt<<1].lazy+=tr[rt].lazy,tr[rt<<1|1].lazy+=tr[rt].lazy;
tr[rt].lazy=0;
return;
}
void modify(int rt,int l,int r,int x,int y,ll v)
{
if(l>=x&&r<=y)
{
tr[rt].sum+=(ll)(r-l+1)*v;
tr[rt].lazy+=v;
return;
}
int mid=(l+r)>>1;
pushdown(rt,l,r);
if(x<=mid)
{
modify(rt<<1,l,mid,x,y,v);
}
if(y>mid)
{
modify(rt<<1|1,mid+1,r,x,y,v);
}
pushup(rt);
}
void update(int x,int y,ll v)
{
while(top[x]!=top[y])
{
if(dep[top[x]]<dep[top[y]])
{
swap(x,y);
}
modify(1,1,n,id[top[x]],id[x],v);
x=fa[top[x]];
}
if(dep[x]<dep[y])
{
swap(x,y);
}
modify(1,1,n,id[y],id[x],v);
}
ll query(int rt,int l,int r,int x,int y)
{
if(l>=x&&r<=y)
{
return tr[rt].sum;
}
int mid=(l+r)>>1;
pushdown(rt,l,r);
ll ret=0;
if(x<=mid)
{
ret+=query(rt<<1,l,mid,x,y);
}
if(y>mid)
{
ret+=query(rt<<1|1,mid+1,r,x,y);
}
pushup(rt);
return ret;
}
ll ask1(int x,int y)
{
ll ret=0;
while(top[x]!=top[y])
{
if(dep[top[x]]<dep[top[y]])
{
swap(x,y);
}
ret+=query(1,1,n,id[top[x]],id[x]);
x=fa[top[x]];
}
if(dep[x]<dep[y])
{
swap(x,y);
}
ret+=query(1,1,n,id[y],id[x]);
return ret;
}
int main()
{
n=read(),m=read();
for(int i=1;i<n;++i)
{
int u=read(),v=read();
add(u,v);
add(v,u);
}
for(int i=1;i<=n;++i)
{
cin>>col[i];
}
dfs1(1,0);
top[1]=1,dfs2(1);
build(1,1,n);
while(m--)
{
int opt=read(),x=read();
if(opt==1)
{
ll y;
cin>>y;
y-=col[x];
s[1]+=y;
ans1+=(ll)y*y*(ll)(dep[x]-dep[1]+1)+2ll*y*ask1(x,1);
update(x,1,y);
}
else
{
cout<<ans1+(ll)(dep[x]-dep[1]+2ll)*s[1]*s[1]-2ll*s[1]*ask1(x,1)<<endl;
}
}
return 0;
}