#include<iostream>
#include<string>
#include<algorithm>
#include<vector>
#include<iomanip>
#include<math.h>
#include<complex>
#include<queue>
#include<deque>
#include<stack>
#include<map>
#include<set>
#include<bitset>
#include<functional>
#include<assert.h>
#include<numeric>
using namespace std;
#define REP(i,m,n) for(int i=(int)(m) ; i < (int) (n) ; ++i )
#define rep(i,n) REP(i,0,n)
using ll = long long;
constexpr int inf=1e9+7;
constexpr ll longinf=1LL<<60 ;
constexpr ll mod=1e9+7 ;

struct Edge{
    int to; ll t; ll k;
};

int main(){
    cin.tie(nullptr);
    ios::sync_with_stdio(false);
    int n,m,s,t;
    cin>>n>>m>>s>>t;
    --s;--t;
    vector<vector<Edge>> v(n);
    rep(i,m){
        int x,y,z,w;
        cin>>x>>y>>z>>w;
        --x;--y;
        v[x].push_back({y,z,w});
        v[y].push_back({x,z,w});
    }
    vector<ll> dist(n, longinf);
    using P = pair<ll,int>;
    priority_queue<P, vector<P>, greater<P>> pq;
    pq.emplace(0,s);
    dist[s]=0;
    while(pq.size()){
        auto p = pq.top();pq.pop();
        ll d = p.first, x = p.second;
        if(d>dist[x])continue;
        for(auto e: v[x]){
            ll nd = (d+e.k-1)/e.k*e.k + e.t;
            if(dist[e.to] > nd){
                dist[e.to] = nd;
                pq.emplace(nd,e.to);
            }
        }
    }
    if(dist[t]>=longinf)cout<<-1<<endl;
    else cout<<dist[t]<<endl;
    return 0;
}
#define fs first
#define sc second
#include <bits/stdc++.h>

using namespace std;

typedef pair<long long, int> pii;

const int maxn = 1e5 + 10;

int n, m, x, y, a, b, t, k;

struct edge{
	int to, t, k;
};

vector<edge> G[maxn];

priority_queue<pii, vector<pii>, greater<pii>> pq;

bool vis[maxn];

long long dis[maxn];

int main() {
	ios::sync_with_stdio(false);
	cin.tie(NULL);
	cin >> n >> m >> x >> y;
	while (m--) {
		cin >> a >> b >> t >> k;
		G[a].push_back({b, t, k});
		G[b].push_back({a, t, k});
	}
	memset(vis, false, sizeof(vis));
	memset(dis, 0x3f, sizeof(dis));
	dis[x] = 0;
	pq.emplace(0, x);
	while (pq.size()) {
		int u = pq.top().sc;
		long long tt = pq.top().fs;
		pq.pop();
		if (vis[u])
			continue;
		vis[u] = true;
		for (edge e: G[u]) {
			long long ttt = tt + (e.k - tt % e.k) % e.k + e.t;
			if (ttt < dis[e.to])
				dis[e.to] = ttt, pq.emplace(ttt, e.to);
		}
	}
	if (dis[y] == 0x3f3f3f3f3f3f3f3fLL)
		cout << "-1\n";
	else
		cout << dis[y] << '\n';
	return 0;
}
