#include <bits/stdc++.h>
#pragma GCC optimize("Ofast,unroll-loops,no-stack-protector,fast-math")
#pragma GCC target( \
    "sse,sse2,sse3,ssse3,sse4,popcnt,abm,mmx,avx,avx2,tune=native")
using namespace std;
const long long MAX_N = 5e5 + 47, INF = 1e18;
long long ans[MAX_N], n, q, t[MAX_N * 4], to_leaf[MAX_N], dpl[MAX_N],
    dpr[MAX_N], d[MAX_N * 4];
tuple<long long, long long, long long> edge[MAX_N];
vector<long long> g[MAX_N];
vector<tuple<long long, long long, long long>> qq[MAX_N];
inline void build_to_leaf(long long u, long long pr = -1, long long sum = 0) {
  bool it_is_leaf = 1;
  dpl[u] = INF;
  dpr[u] = -INF;
  for (auto id : g[u]) {
    auto [curr, v, cost] = edge[id];
    if (curr != u) {
      swap(curr, v);
    }
    if (v != pr) {
      it_is_leaf = 0;
      build_to_leaf(v, u, sum + cost);
      dpl[u] = min(dpl[u], dpl[v]);
      dpr[u] = max(dpr[u], dpr[v]);
    }
  }
  if (u == 1) {
    it_is_leaf = 0;
  }
  if (it_is_leaf) {
    to_leaf[u] = sum;
    dpl[u] = dpr[u] = u;
  }
}
inline void push(long long v, long long tl, long long tr) {
  if (d[v]) {
    t[v] += d[v];
    if (tl != tr) {
      d[v << 1] += d[v];
      d[v << 1 | 1] += d[v];
    }
    d[v] = 0;
  }
}
inline void update(long long v, long long tl, long long tr, long long l,
                   long long r, long long x) {
  if (tl > r || tr < l || l > r) {
    return;
  }
  push(v, tl, tr);
  if (tl >= l && tr <= r) {
    d[v] += x;
    push(v, tl, tr);
    return;
  }
  long long tm = (tl + tr) >> 1;
  update(v << 1, tl, tm, l, r, x);
  update(v << 1 | 1, tm + 1, tr, l, r, x);
  t[v] = min(t[v << 1], t[v << 1 | 1]);
}
inline long long get_mn(long long v, long long tl, long long tr, long long l,
                        long long r) {
  push(v, tl, tr);
  if (tl > r || tr < l) {
    return INF;
  }
  if (tl >= l && tr <= r) {
    return t[v];
  }
  long long tm = (tl + tr) >> 1;
  return min(get_mn(v << 1, tl, tm, l, r),
             get_mn(v << 1 | 1, tm + 1, tr, l, r));
}
inline void dfs(long long u, long long pr = -1, long long cost = 0) {
  update(1, 1, n, dpl[u], dpr[u], -cost);
  update(1, 1, n, 1, dpl[u] - 1, +cost);
  update(1, 1, n, dpr[u] + 1, n, +cost);
  for (auto [l, r, id] : qq[u]) {
    ans[id] = get_mn(1, 1, n, l, r);
  }
  for (auto id : g[u]) {
    auto [curr, v, cost] = edge[id];
    if (curr != u) {
      swap(curr, v);
    }
    if (v != pr) {
      dfs(v, u, cost);
    }
  }
  update(1, 1, n, dpl[u], dpr[u], +cost);
  update(1, 1, n, 1, dpl[u] - 1, -cost);
  update(1, 1, n, dpr[u] + 1, n, -cost);
}
void build(long long v, long long tl, long long tr) {
  if (tl == tr) {
    t[v] = (to_leaf[tl] == 0 ? INF : to_leaf[tl]);
  } else {
    long long tm = (tl + tr) >> 1;
    build(v << 1, tl, tm);
    build(v << 1 | 1, tm + 1, tr);
    t[v] = min(t[v << 1], t[v << 1 | 1]);
  }
}
signed main() {
  ios_base::sync_with_stdio(0), cin.tie(0), cout.tie(0);
  cin >> n >> q;
  for (long long i = 2; i <= n; i++) {
    long long pr, cost;
    cin >> pr >> cost;
    long long id = i;
    edge[id] = {pr, i, cost};
    g[pr].push_back(id);
    g[i].push_back(id);
  }
  for (long long i = 1; i <= q; i++) {
    long long l, r, u;
    cin >> u >> l >> r;
    qq[u].push_back({l, r, i});
  }
  build_to_leaf(1);
  build(1, 1, n);
  dfs(1);
  for (long long i = 1; i <= q; i++) {
    cout << ans[i] << '\n';
  }
  return 0;
}
