#include <iostream>
#include <vector>
#include <algorithm>
#include <map>
#include <string>
#include <queue>
#include <fstream>
#include <string>
#include <math.h>
#include <set>
#include <string>
#include <bitset>
#include <fstream>
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
typedef pair<ll, ll> P;
//typedef pair<ll, P> T;

#define rep(i, n) for (ll i = 0; i < (n); i++)
#define revrep(i, n) for (ll i = (n) - 1; i >= 0; i--)
#define f first
#define s second
#define pb push_back

ll mod = 1000000007;
const ll INF = 100000000000010000;
//const ull B = 998244353;
//ll kai[3010];

//void pres(double A, ll x = 20) { printf("%.20f\n", x); }

vector<ll> dx = { 0, 1, 0, -1, 1, -1, 1, -1, 0};
vector<ll> dy = { 1, 0, -1, 0, 1, 1, -1, -1, 0};

void chmin(double& x, double y) {
	x = min(x, y);
}

void chmax(double& x, double y) {
	x = max(x, y);
}

ll pow_long(ll x, ll y) {
	ll res = 1;
	while (y > 0) {
		if (y % 2 == 1) res *= x;
		x *= x;
		y /= 2;
	}
	return res;
}

void test() {
	cout << "888888888888888888888888" << endl;
}

ll gcd(ll x, ll y) {
	if (y == 0) return x;
	return gcd(y, x % y);
}

ll pow_mod(ll x, ll k) {
	x %= mod;
	ll res = 1;
	while (k > 0) {
		if (k % 2) {
			res *= x; res %= mod;
		}
		x *= x; x %= mod;
		k /= 2;
	}
	return res;
}

ll div_mod(ll x) {
	return pow_mod(x, mod - 2);
}

//コンビネーション
const int MAXcomb = 1000010;
ll fac[MAXcomb], finv[MAXcomb], inv[MAXcomb];
//facはn!,finvは1/n!
//invは逆元
void COMinit() {
	fac[0] = fac[1] = 1;
	finv[0] = finv[1] = 1;
	inv[1] = 1;
	for (int i = 2; i < MAXcomb; i++) {
		fac[i] = fac[i - 1] * i % mod;
		inv[i] = mod - inv[mod%i] * (mod / i) % mod;
		finv[i] = finv[i - 1] * inv[i] % mod;
	}
}
ll comb(int n, int k) {
	if (n < k) return 0;
	if (n < 0 || k < 0) return 0;
	return fac[n] * finv[k] % mod * finv[n - k] % mod;
}

ll N, Q;
ll a[100010], b[100010], c[100010], d[100010];
ll x[100010], y[100010], u[100010], v[100010];
struct edge{ ll to, color, cost; };
vector<edge> E[100010];
vector<P> queryColor[100010][2]; // 0はプラス、1はマイナス、P(色、クエリ番号)
ll dep[100010], len[100010], par[20][100010];
ll num_cl[100010], len_cl[100010];
ll ans[100010];

void make_depth(ll now, ll from, ll d) {
	dep[now] = d;
	for (edge e: E[now]) {
		if (e.to == from) continue;
		make_depth(e.to, now, d + 1);
	}
}

void make_parents(ll now, ll from) {
	par[0][now] = from;
	for (edge e: E[now]) {
		if (e.to == from) continue;
		make_parents(e.to, now);
	}
}

void make_length(ll now, ll from, ll l) {
	len[now] = l;
	for (edge e: E[now]) {
		if (e.to == from) continue;
		make_length(e.to, now, l + e.cost);
	}
}

void init_lca(ll V) {
	make_depth(1, 0, 0);
	make_length(1, 0, 0);
	make_parents(1, 0);

	for (ll k = 0; k < 19; k++) {
		for (ll v = 1; v <= V; v++) {
			if (par[k][v] == 0) continue;
			par[k + 1][v] = par[k][par[k][v]];
		}
	}
}

ll lca(ll u, ll v) {
	if (dep[u] > dep[v]) swap(u, v);
	for (ll k = 0; k < 19; k++) {
		if ((dep[u] - dep[v]) >> k & 1) v = par[k][v];
	}
	if (u == v) return u;
	for (ll k = 19; k >= 0; k--) {
		if (par[k][u] != par[k][v]) {
			u = par[k][u], v = par[k][v];
		}
	}
	return par[0][u];
}

void dfs(ll now, ll from) {
	ll col = 0, l = 0;
	for (edge e: E[now]) if (e.to == from) col = e.color, l = e.cost;
	num_cl[col]++, len_cl[col] += l;
	for (P p: queryColor[now][0]) {
		ans[p.s] -= len_cl[p.f];
		ans[p.s] += num_cl[p.f] * y[p.s];
	}
	for (P p: queryColor[now][1]) {
		ans[p.s] += 2 * len_cl[p.f];
		ans[p.s] -= 2 * num_cl[p.f] * y[p.s];
	}
	for (edge e: E[now]) {
		if (e.to == from) continue;
		dfs(e.to, now);
	}
	num_cl[col]--, len_cl[col] -= l;
}

void solve() {
	cin >> N >> Q;
	rep(i, N - 1) {
		cin >> a[i] >> b[i] >> c[i] >> d[i];
		E[a[i]].pb(edge{b[i], c[i], d[i]});
		E[b[i]].pb(edge{a[i], c[i], d[i]});
	}
	init_lca(N);
	rep(i, Q) {
		cin >> x[i] >> y[i] >> u[i] >> v[i];
		ans[i] = len[u[i]] + len[v[i]] - 2 * len[lca(u[i], v[i])];
		queryColor[u[i]][0].pb(P(x[i], i));
		queryColor[v[i]][0].pb(P(x[i], i));
		queryColor[lca(u[i], v[i])][1].pb(P(x[i], i));
	}
	dfs(1, 0);
	//rep(i, N) cout << len[i + 1] << endl;
	rep(i, Q) cout << ans[i] << endl;
}

int main() {
	cin.tie(0);
	ios::sync_with_stdio(false);
	ll T = 1;
	//cin >> T;
	rep(i, T) solve();
}


Measured memory_bytes: 53876