#include <bits/stdc++.h>
#define Nmax 100001
#define ls ((1<<(nod+1))-1)
#define rs (1<<(nod+1))
using namespace std;
ifstream f("heavypath.in");
ofstream g("heavypath.out");
int v[Nmax],nr_chain[Nmax],poz[Nmax],lvl[Nmax],weight[Nmax],t[Nmax];
list <int> arb[Nmax];
vector <int> chain[Nmax];
vector <int> Aint[Nmax];
int N,changed,nr_arb,lsh,rsh;
void DFS(int x)
{
int nr=0,nod=0;
for(list <int> :: iterator it=arb[x].begin();it!=arb[x].end();++it)
if(!lvl[*it])
{
nr++;
t[*it]=x;
lvl[*it]=lvl[x]+1;
DFS(*it);
if(weight[*it]>weight[nod])
nod=*it;
}
weight[x]=nr+1;
if(nr)
{
nr_chain[x]=nr_chain[nod];
chain[nr_chain[x]].push_back(x);
}
else
{
nr_chain[x]=++N;
chain[N].push_back(x);
}
}
inline bool cmp(const int &x, const int &y)
{
return lvl[x]<lvl[y];
}
void build(int p, int q, int nod)
{
if(p==q)
Aint[nr_arb][nod]=v[chain[nr_arb][p]];
else
{
int m=(p+q)>>1;
build(p,m,ls);
build(m+1,q,rs);
Aint[nr_arb][nod]=max(Aint[nr_arb][ls],Aint[nr_arb][rs]);
}
}
void update(int p, int q, int nod)
{
if(p==q) Aint[nr_arb][nod]=v[chain[nr_arb][p]];
else
{
int m=(p+q)>>1;
if(changed<=m) update(p,m,ls);
else update(m+1,q,rs);
Aint[nr_arb][nod]=max(Aint[nr_arb][ls],Aint[nr_arb][rs]);
}
}
int query(int p, int q, int nod)
{
if(lsh<=p and q<=rsh) return Aint[nr_arb][nod];
else
{
int m=(p+q)>>1,max1=-INT_MAX,max2=-INT_MAX;
if(lsh<=m) max1=query(p,m,ls);
if(m<rsh) max2=query(m+1,q,rs);
return max(max1,max2);
}
}
int heavy_path_query(int x, int y)
{
if(nr_chain[x]==nr_chain[y])
{
nr_arb=nr_chain[x];
lsh=poz[x];
rsh=poz[y];
if(lsh>rsh) swap(lsh,rsh);
return query(0,chain[nr_arb].size()-1,0);
}
else
{
if(lvl[chain[nr_chain[x]][0]]<lvl[chain[nr_chain[y]][0]]) swap(x,y);
lsh=0;
rsh=poz[x];
nr_arb=nr_chain[x];
int max1=query(0,chain[nr_arb].size()-1,0);
int max2=heavy_path_query(t[chain[nr_chain[x]][0]],y);
return max(max1,max2);
}
}
int main()
{
int n,Q,i,j,x,y,op;
f>>n>>Q;
for(i=1;i<=n;i++)
f>>v[i];
for(i=1;i<n;i++)
{
f>>x>>y;
arb[x].push_back(y);
arb[y].push_back(x);
}
lvl[1]=1;
DFS(1);
for(i=1;i<=N;i++)
{
sort(chain[i].begin(),chain[i].end(),cmp);
for(j=0;j<(int)chain[i].size();j++)
poz[chain[i][j]]=j;
Aint[i].reserve(20*chain[i].size());
nr_arb=i;
build(0,chain[i].size()-1,0);
}
while(Q--)
{
f>>op>>x>>y;
switch(op)
{
case 0:
{
v[x]=y;
nr_arb=nr_chain[x];
changed=poz[x];
update(0,chain[nr_arb].size()-1,0);
break;
}
case 1:
{
g<<heavy_path_query(x,y)<<'\n';
break;
}
}
}
return 0;
}