#include <bits/stdc++.h>
using namespace std;
ifstream fin("heavypath.in");
ofstream fout("heavypath.out");
const int dim=1e5+10;
struct MaximumSegmentTree{
int aint[4*dim];
void update(int nod,int tl,int tr,int poz,int val){
if(tl==tr){
aint[nod]=val;
return;
}
int tm=(tl+tr)/2;
if(poz<=tm){
update(2*nod,tl,tm,poz,val);
}
else{
update(2*nod+1,tm+1,tr,poz,val);
}
aint[nod]=max(aint[2*nod],aint[2*nod+1]);
}
int query(int nod,int tl,int tr,int l,int r){
if(l==tl && r==tr){
return aint[nod];
}
int tm=(tl+tr)/2;
if(r<=tm){
return query(2*nod,tl,tm,l,r);
}
if(l>tm){
return query(2*nod+1,tm+1,tr,l,r);
}
return max(query(2*nod,tl,tm,l,tm),query(2*nod+1,tm+1,tr,tm+1,r));
}
}DS;
vector<int>adj[dim];
int n,m,v[dim],timer;
int sz[dim],depth[dim],parent[dim];
int HPindex[dim],heavyChild[dim],heavyHead[dim];
void dfs(int x){
sz[x]=1;
heavyChild[x]=0;
for(int y:adj[x]){
if(!sz[y]){
parent[y]=x;
depth[y]=depth[x]+1;
dfs(y);
sz[x]+=sz[y];
if(sz[y]>sz[heavyChild[x]]){
heavyChild[x]=y;
}
}
}
}
void dfsHeavyFirst(int x){
HPindex[x]=++timer;
if(heavyChild[x]){
heavyHead[heavyChild[x]]=heavyHead[x];
dfsHeavyFirst(heavyChild[x]);
}
for(int y:adj[x]){
if(y!=heavyChild[x]&&y!=parent[x]){
heavyHead[y]=y;
dfsHeavyFirst(y);
}
}
}
int maximumOnPath(int x,int y){
if(heavyHead[x]==heavyHead[y]){
if(depth[x]<depth[y]){
return DS.query(1,1,n,HPindex[x],HPindex[y]);
}else{
return DS.query(1,1,n,HPindex[y],HPindex[x]);
}
}
if(depth[heavyHead[x]]<depth[heavyHead[y]]){
return max(DS.query(1,1,n,HPindex[heavyHead[y]],HPindex[y]),maximumOnPath(x,parent[heavyHead[y]]));
}else{
return max(DS.query(1,1,n,HPindex[heavyHead[x]],HPindex[x]),maximumOnPath(parent[heavyHead[x]],y));
}
}
signed main(){
fin>>n>>m;
for(int i=1;i<=n;i++){
fin>>v[i];
}
for(int i=1;i<n;i++){
int x,y;
fin>>x>>y;
adj[x].push_back(y);
adj[y].push_back(x);
}
depth[1]=1;
dfs(1);
heavyHead[1]=1;
dfsHeavyFirst(1);
for(int i=1;i<=n;i++){
DS.update(1,1,n,HPindex[i],v[i]);
}
while(m--){
bool op;
fin>>op;
if(op==0){
int poz,val;
fin>>poz>>val;
DS.update(1,1,n,poz,val);
}else{
int x,y;
fin>>x>>y;
fout<<maximumOnPath(x,y)<<'\n';
}
}
}