#include <bits/stdc++.h>
using namespace std;
const int Maxn = 500010;
const long long inf = (1LL << 61);
int read() {
  int x = 0, f = 1;
  char ch = getchar();
  while (ch < '0' || ch > '9') {
    if (ch == '-') f = -1;
    ch = getchar();
  }
  while (ch >= '0' && ch <= '9')
    x = (x << 3) + (x << 1) + (ch ^ 48), ch = getchar();
  return x * f;
}
int n, q, p[Maxn], in[Maxn], out[Maxn];
long long dis[Maxn], w[Maxn];
bool mark[Maxn];
struct Edge {
  int y, next;
} e[Maxn];
int last[Maxn], len = 0;
void ins(int x, int y) {
  int t = ++len;
  e[t].y = y;
  e[t].next = last[x];
  last[x] = t;
}
void dfs(int x) {
  in[x] = out[x] = x;
  for (int i = last[x]; i; i = e[i].next) {
    int y = e[i].y;
    mark[x] = true;
    dis[y] = dis[x] + w[y];
    dfs(y);
    out[x] = out[y];
  }
}
struct Seg {
  int l, r, lc, rc;
  long long mn, tag;
} tr[Maxn << 1];
int tot = 0;
void Add(int x, long long v) { tr[x].mn += v, tr[x].tag += v; }
void up(int x) {
  int lc = tr[x].lc, rc = tr[x].rc;
  tr[x].mn = min(tr[lc].mn, tr[rc].mn);
}
void down(int x) {
  int lc = tr[x].lc, rc = tr[x].rc;
  if (tr[x].tag) {
    long long t = tr[x].tag;
    tr[x].tag = 0;
    Add(lc, t), Add(rc, t);
  }
}
void build(int l, int r) {
  int x = ++tot;
  tr[x].l = l;
  tr[x].r = r;
  tr[x].tag = 0;
  if (l == r) {
    if (mark[l])
      tr[x].mn = inf;
    else
      tr[x].mn = dis[l];
    return;
  }
  int mid = l + r >> 1;
  tr[x].lc = tot + 1, build(l, mid);
  tr[x].rc = tot + 1, build(mid + 1, r);
  up(x);
}
void add(int x, int l, int r, long long v) {
  if (tr[x].l == l && tr[x].r == r) {
    Add(x, v);
    return;
  }
  int mid = tr[x].l + tr[x].r >> 1, lc = tr[x].lc, rc = tr[x].rc;
  down(x);
  if (r <= mid)
    add(lc, l, r, v);
  else if (l > mid)
    add(rc, l, r, v);
  else
    add(lc, l, mid, v), add(rc, mid + 1, r, v);
  up(x);
}
long long query(int x, int l, int r) {
  if (tr[x].l == l && tr[x].r == r) return tr[x].mn;
  int mid = tr[x].l + tr[x].r >> 1, lc = tr[x].lc, rc = tr[x].rc;
  down(x);
  if (r <= mid) return query(lc, l, r);
  if (l > mid) return query(rc, l, r);
  return min(query(lc, l, mid), query(rc, mid + 1, r));
}
struct Query {
  int l, r;
} Q[Maxn];
long long ans[Maxn];
vector<int> h[Maxn];
void DFS(int x) {
  for (int i = 0; i < h[x].size(); i++) {
    int t = h[x][i];
    ans[t] = query(1, Q[t].l, Q[t].r);
  }
  for (int i = last[x]; i; i = e[i].next) {
    int y = e[i].y;
    add(1, in[y], out[y], -w[y]);
    if (in[y] > 1) add(1, 1, in[y] - 1, w[y]);
    if (out[y] < n) add(1, out[y] + 1, n, w[y]);
    DFS(y);
    add(1, in[y], out[y], w[y]);
    if (in[y] > 1) add(1, 1, in[y] - 1, -w[y]);
    if (out[y] < n) add(1, out[y] + 1, n, -w[y]);
  }
}
int main() {
  n = read(), q = read();
  for (int i = 2; i <= n; i++) p[i] = read(), w[i] = read();
  for (int i = n; i > 1; i--) ins(p[i], i);
  dis[1] = 0;
  dfs(1);
  build(1, n);
  for (int i = 1; i <= q; i++) {
    int x = read();
    Q[i].l = read(), Q[i].r = read();
    h[x].push_back(i);
  }
  DFS(1);
  for (int i = 1; i <= q; i++) printf("%lld\n", ans[i]);
}
