#include <bits/stdc++.h>
using namespace std;
typedef long long LL;
typedef pair<int, int> P;
template<typename T> inline void chkmin(T &a, const T &b) { a = a < b ? a : b; }
template<typename T> inline void chkmax(T &a, const T &b) { a = a > b ? a : b; }

const int MAXN = 140005;
struct Edge { int v, w; } son[MAXN][2];
struct Data { LL v, w; bool operator<(const Data &e) { return v == e.v ? w < e.w : v < e.v; } } arr[MAXN], brr[MAXN];
int n; LL cur;
void add_son(int u, int v, int w) {
	son[u][son[u][0].v > 0] = Edge { v, w };
}

vector<Data> dfs(int u) {
	if (!son[u][0].v) {
		vector<Data> v;
		v.push_back(Data { 0ll, 0ll });
		return v;
	}
	auto l = dfs(son[u][0].v), r = dfs(son[u][1].v);
	if (l.empty() || r.empty()) return vector<Data>();
	for (auto &p : l) p.v += son[u][0].w, p.w += son[u][0].w;
	for (auto &p : r) p.v += son[u][1].w, p.w += son[u][1].w;
	if (l.size() > r.size()) swap(l, r);
	int sl = l.size(), sr = r.size(), a = 0, b = 0, m = 0;
	for (int i = 0, j = sr - 1; i < sl; i++) {
		while (j >= 0 && r[j].v + l[i].v > cur) --j;
		if (j < 0) break;
		arr[++m] = Data { l[i].w, r[j].w };
		brr[m] = Data { r[j].w, l[i].w };
	}
	reverse(arr + 1, arr + 1 + m);
	vector<Data> vec;
	while (a < m || b < m) {
		Data &e = b == m || (a < m && arr[a + 1] < brr[b + 1]) ? arr[++a] : brr[++b];
		if (!vec.empty() && e.v >= vec.back().v && e.w >= vec.back().w) continue;
		vec.push_back(e);
	}
	return vec;
}

int main() {
	scanf("%d", &n);
	LL l = 0, r = 0;
	for (int i = 1; i < n; i++) {
		int v, w; scanf("%d%d", &v, &w);
		add_son(v, i + 1, w);
		r += w;
	}
	while (l + 1 < r) {
		cur = (l + r) >> 1;
		if (dfs(1).empty()) l = cur;
		else r = cur;
	}
	printf("%lld\n", r);
	return 0;
}