#define _GLIBCXX_DEBUG 1
#include <bits/stdc++.h>
#include <ext/pb_ds/assoc_container.hpp>
#include <ext/pb_ds/tree_policy.hpp>
// #pragma GCC optimize("O3")
// #pragma GCC target("avx2,bmi,bmi2")
#define endl "\n"
#define all(x) x.begin(), x.end()
#define f first
#define s second
#define pb push_back
#define pop pop_back

using namespace std;
using namespace __gnu_pbds;

using ll = long long;
using ld = long double;

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

template <typename T>
using ordered_multiset = tree<T, null_type, less_equal<>, rb_tree_tag, tree_order_statistics_node_update>;

constexpr ll INF = 1e9;
constexpr ll LINF = 1e18;
constexpr ld EPS = 1e-5;
constexpr ll MOD = 1e9 + 7, MOD2 = 998244353;

ll add(ll a, ll b, ll mod) {
    if (a + b >= mod) return a + b - mod;
    return a + b;
}

ll sub(ll a, ll b, ll mod) {
    if (a >= b) return a - b;
    return a - b + mod;
}

ll mul(ll a, ll b, ll mod) {
    return 1ll * a * b % mod;
}

ll binpow(ll a, ll b, ll mod) {
    if (b == 0) return 1;
    ll x = binpow(a, b / 2, mod);
    if (b % 2) return mul(x, mul(x, a, mod), mod);
    return mul(x, x, mod);
}

mt19937 rnd(1337228666);

void solve() {
    ll n;
    cin >> n;
    vector <ll> a(n), b(n), pa(n + 1), pb(n + 1);
    for (ll i = 0; i < n; i++) {
        cin >> a[i] >> b[i];
        pa[i + 1] = pa[i] + a[i];
        pb[i + 1] = pb[i] + b[i];
    }
    vector <ll> p(n), next(n, n - 1), prev(n + 1);
    for (ll i = 0; i < n; i++) {
        cin >> p[i];
        if (p[i] != -1) {
            prev[i + 1] = i;
            p[i]--;
        } else {
            prev[i + 1] = prev[i];
        }
    }

    for (ll i = n - 2; i >= 0; i--) {
        if (p[i] != -1) {
            next[i] = p[i];
        } else {
            next[i] = next[i + 1];
        }
    }

    vector <ll> c2(n);
    ll last = -1;
    for (ll i = 0; i < n; i++) {
        if (p[i] != -1) {
            last = p[i];
            for (ll j = p[i] + 1; j <= next[i + 1]; j++) {
                c2[j] = i + 1;
            }
        }
    }

    vector <ll> c1(n);
    iota(all(c1), 0);
    for (ll i = n - 1; i >= 0; i--) {
        if (p[i] != -1) {
            for (ll j = p[i]; i ? j > p[prev[i]] : j >= 0; j--) {
                c1[j] = min(c1[j], i);
            }
        }
    }

    // теперь начнем дпшку
    vector <ll> dp(n + 1), t(n), pt(n + 1), pans(n + 1);
    for (ll i = 0; i < n; i++) {
        if (b[i] > 0) {
            t[i] = c1[i];
            pt[i + 1] = pt[i] + t[i];
            pans[i + 1] = pans[i] + a[i] + 1ll * b[i] * t[i];
            dp[i + 1] = dp[i] + (a[i] + b[i] * t[i]);
        } else {
            ll maxans = -LINF, best_j = -1;
            for (ll j = c2[i]; j <= c1[i]; j++) {
                // всех слева больших j заменим потом на j (c1 тоже возрастают, это возможно), и пересчитаем ответ
                // это можно префсуммами делать. применение ответа тоже можно сделать. будем жадничать крч
                auto it = upper_bound(t.begin(), t.begin() + i, j) - t.begin();
                ll change = 0;
                change = -(pans[i] - pans[it]) + (pa[i] - pa[it]) + (pb[i] - pb[it]) * j;
                if (maxans < dp[i] + a[i] + b[i] * j + change) {
                    maxans = dp[i] + a[i] + b[i] * j + change;
                    best_j = j;
                }
            }

            dp[i + 1] = maxans;
            ll it = upper_bound(t.begin(), t.begin() + i, best_j) - t.begin();
            for (ll j = it; j < i; j++) {
                t[j] = best_j;
                pt[j + 1] = pt[j] + t[j];
                pans[j + 1] = pans[j] + a[j] + 1ll * b[j] * t[j];
            }
            t[i] = best_j;
        }
    }

    ll maxans = -LINF;
    for (ll i = max(last + 1, 1ll); i <= n; i++) {
        maxans = max(maxans, dp[i]);
    }
    cout << maxans << endl;
}

signed main() {
    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);
    ll t = 1;
    // cin >> t;
    while (t--) solve();
}