#include <bits/stdc++.h>
#include <ext/pb_ds/assoc_container.hpp>
#include <ext/pb_ds/tree_policy.hpp>

using namespace std;
using namespace __gnu_pbds;

template <typename T>
using ordered_set = tree<T, null_type, less<T>, rb_tree_tag, tree_order_statistics_node_update>;

#define int long long
#define sz(x) (int)x.size()
#define all(x) x.begin(), x.end()
#define F first
#define S second
#define Vector2 pair <int, int>
#define print(a) for (const auto& x : a) cout << x << ' ';

const int INF = 1e16;

void solve()
{
	int n;
	cin >> n;
	vector <int> a(n + 1), b(n + 1);
	for (int i = 1; i <= n; ++i) {
		cin >> a[i] >> b[i];
	}
	vector <int> p(n + 1);
	for (int i = 1; i <= n; ++i) {
		cin >> p[i];
	}
	vector <int> mnt(n + 1, 0), mxt(n + 1);
	for (int i = 1; i <= n; ++i) {
		mxt[i] = i - 1;
	}
	int nd = 0;
	for (int x = 1; x <= n; ++x) {
		if (p[x] == -1) {
			continue;
		}
		nd = max(nd, p[x]);
		for (int j = 1; j <= p[x]; ++j) {
			mxt[j] = min(mxt[j], x - 1);
		}
		for (int j = p[x] + 1; j <= n; ++j) {
			mnt[j] = max(mnt[j], x);
		}
	}
	vector <int> pref(n, -INF), cur(n, -INF), prev(n, -INF);
	int ans = (nd == 0 ? 0 : -INF);
	for (int i = 1; i <= n; ++i) {
		fill(all(cur), -INF);
		if (i == 1) {
			for (int t = mnt[i]; t <= mxt[i]; ++t) {
				cur[t] = a[i] + b[i] * t;
			}
		} else {
			pref[0] = prev[0];
			for (int t = 1; t < n; ++t) {
				pref[t] = max(pref[t - 1], prev[t]);
			}
			for (int t = mnt[i]; t <= mxt[i]; ++t) {
				if (pref[t] == -INF) {
					continue;
				}
				cur[t] = pref[t] + a[i] + b[i] * t;
			}
		}
		if (i >= nd) {
			int res =  -INF;
			for (int t = 0; t < n; ++t) {
				res = max(res, cur[t]);
			}
			ans = max(ans, res);
		}
		prev.swap(cur);
	}
	cout << ans << '\n';
}

signed main()
{
	cin.tie(nullptr)->ios_base::sync_with_stdio(false);
	solve();
	return 0;
}