#include<bits/stdc++.h>

using namespace std;
#define int long long
struct edge
{
    int v, u, cost, dist;
};
vector<edge>kek;
int cnt[300200];
int b[200200];
int counter[300200];
int K = 350;
int sum = 0;
bool cmp(pair<pair<int, int>, int>a, pair<pair<int, int>, int>b)
{
    if (a.first.first / K != b.first.first / K)
        return a.first.first < b.first.first;
    else
        return a.first.second / K < b.first.second / K;
}
map<pair<int, int>, int>mp;
vector<pair<pair<int, int>, int > >query;
vector<int>g[300200];
vector<int>eu;
int fir[300200];
int from[300200];
int full = 0;
void dfs(int vv, int p = -1)
{
    if (p != -1)
    {
        eu.push_back(mp[{vv, p}]);
        fir[vv] = eu.size();
    }
    for(int i = 0; i < g[vv].size(); ++i)
    {
        int to = g[vv][i];
        if (to == p)
            continue;
        dfs(to, vv);
        eu.push_back(mp[{vv, to}]);
    }
    return;
}
int cc[500200];
void update(int x, int dist, int del)
{
    full += del * dist;
    cc[x] += del;
    cnt[x] += del * dist;
}
int l, r;
void Lleft()
{
    --l;
    counter[eu[l]] ^= 1;
    if (counter[eu[l]] == 1)
        update(kek[eu[l]].cost, kek[eu[l]].dist, 1);
    else
        update(kek[eu[l]].cost, kek[eu[l]].dist, -1);
}
void Lright()
{
    counter[eu[l]] ^= 1;
    if (counter[eu[l]] == 1)
        update(kek[eu[l]].cost, kek[eu[l]].dist, 1);
    else
        update(kek[eu[l]].cost, kek[eu[l]].dist, -1);
    ++l;
}
void Rright()
{
    ++r;
    counter[eu[r]] ^= 1;
    if (counter[eu[r]] == 1)
        update(kek[eu[r]].cost, kek[eu[r]].dist, 1);
    else
        update(kek[eu[r]].cost, kek[eu[r]].dist, -1);
}
void Rleft()
{
    counter[eu[r]] ^= 1;
    if (counter[eu[r]] == 1)
        update(kek[eu[r]].cost, kek[eu[r]].dist, 1);
    else
        update(kek[eu[r]].cost, kek[eu[r]].dist, -1);
    --r;
}
int get(int f1, int f2)
{
    int s1 = cc[f1] * f2;
    int dl = s1 - cnt[f1];
    return full + dl;
}
int ans[500200];
int cur_d[500200];
pair<int, int> qw[500200];
signed main()
{
    int n, q;
    cin >> n >> q;
    for(int i = 0; i + 1 < n; ++i)
    {
        int v, u, cost, dd;
        cin >> v >> u >> cost >> dd;
        --v, --u;
        kek.push_back({v, u, cost, dd});
        g[v].push_back(u);
        g[u].push_back(v);
        mp[{v, u}] = mp[{u, v}] = i;
    }
    dfs(0);
    fir[0] = 0;
   // for(int i = 0; i < eu.size(); ++i)
   //     cout << eu[i] << " ";
   // cout << endl;
   //vector<bool>used(q, false);
    for(int i = 0; i < q; ++i)
    {
        int a, b, c, d;
        cin >> c >> d >> a >> b;
        qw[i] = {c, d};
        --a, --b;
        if (a == b)
            continue;
        a = fir[a];
        b = fir[b];
        if (a > b)
            swap(a, b);
        //if (a != -1)
         //   ++a;
        --b;
        query.push_back({{a, b}, i});
    }
    sort(query.begin(), query.end(), &cmp);
    l = 0, r = -1;
    //update(eu[l], 1);
    //counter[kek[eu[l]].cost] ^= 1;
    int ii = 0;
    while(ii < query.size())
    {
        int left = query[ii].first.first;
        int right = query[ii].first.second;
        while(l > left)
            Lleft();
        while(r < right)
            Rright();
        while(l < left)
            Lright();
        while(r > right)
            Rleft();
        ans[query[ii].second] = get(qw[query[ii].second].first, qw[query[ii].second].second);
        ++ii;
    }
    for(int i = 0; i < q; ++i)
        cout << ans[i] << '\n';
    return 0;
}


Measured memory_bytes: 61292