#include<iostream>
#include<cstdio>
#include<algorithm>
#include<queue>
using namespace std;
int n,head[1010101],cnt,in[1010101],cycle[1010101][3];
struct node{
int v,prep,type;
long long w;
}edge[2020202];
void add(int u,int v,long long w){
edge[++cnt] = (node){v,head[u],0,w};
head[u] = cnt;
}queue<int> q;
deque<long long> q1;
deque<int> q2;
bool visit[1010101],vis[1010101],vis2[1010101];
long long maxdep[1010101],maxdis[1010101],ans;
void dfs(int u,int fa){
long long second = 0;
for(int i = head[u];i;i = edge[i].prep){
int v = edge[i].v,type = edge[i].type;
if(type) continue;
if(v==fa) continue;
dfs(v,u);
maxdis[u] = max(maxdis[u],maxdis[v]);
long long w = edge[i].w;
if(maxdep[u]<=maxdep[v]+w){second = maxdep[u];maxdep[u] = maxdep[v]+w;}
else if(second<maxdep[v]+w) second = maxdep[v]+w;
}maxdis[u] = max(maxdis[u],maxdep[u]+second);
}void dfs2(int u,int fa){
vis[u] = 1;
if(edge[cycle[u][1]].v==fa) swap(cycle[u][1],cycle[u][2]);
if(!vis[edge[cycle[u][1]].v]) dfs2(edge[cycle[u][1]].v,u);
}
int main(){
scanf("%d",&n);
for(int i = 1;i<=n;i++){
int v;long long w;
scanf("%d%lld",&v,&w);
add(i,v,w);add(v,i,w);
in[v]++;
}for(int i = 1;i<=n;i++) if(in[i]==0) q.push(i),visit[i] = 1;
while(!q.empty()){
int u = q.front();
q.pop();
for(int i = head[u];i;i = edge[i].prep){
int v = edge[i].v;
if(visit[v]) continue;
in[v]--;
if(in[v]<=0) q.push(v),visit[v] = 1;
}
}for(int u = 1;u<=n;u++){
if(!visit[u]){
for(int i = head[u];i;i = edge[i].prep){
int v = edge[i].v;
if(!visit[v]) edge[i].type = 1,cycle[u][++cycle[u][0]] = i;
}
}
}for(int u = 1;u<=n;u++) if(!visit[u]) dfs(u,0);
for(int u = 1;u<=n;u++) if(!vis[u]) dfs2(u,0);
for(int i = 1;i<=n;i++){
if(visit[i] || vis2[i]) continue;
int u = i;
long long minus = 0,sum = 0,res = maxdis[u];
q1.push_back(0),q2.push_back(u),vis2[u] = 1;
while(!vis2[edge[cycle[u][1]].v]){
sum += edge[cycle[u][1]].w;
long long w = sum+maxdep[edge[cycle[u][1]].v];
while(!q1.empty() && q1.back()<=w) q1.pop_back(),q2.pop_back();
q1.push_back(w),q2.push_back(edge[cycle[u][1]].v);
u = edge[cycle[u][1]].v;
res = max(res,maxdis[u]);
vis2[u] = 1;
res = max(res,q1.front()+maxdep[i]);
}
u = i;
while(edge[cycle[u][1]].v!=i){
int v = q2.back();long long w = q1.back();
if(q2.front()==u) q1.pop_front(),q2.pop_front();
minus += edge[cycle[u][1]].w;
int j = cycle[v][1];
w = w-maxdep[v]+edge[j].w+maxdep[edge[j].v];
v = edge[j].v;
u = edge[cycle[u][1]].v;
while(!q1.empty() && q1.back()<=w) q1.pop_back(),q2.pop_back();
q1.push_back(w),q2.push_back(v);
res = max(res,q1.front()-minus+maxdep[u]);
}ans += res;
while(!q1.empty()) q1.pop_back(),q2.pop_back();
}printf("%lld\n",ans);
return 0;
}