#include <bits/stdc++.h>
#define rep(i, a, n) for(int i = a; i < n; i++)
#define repb(i, a, b) for(int i = a; i >= b; i--)
#define all(a) a.begin(), a.end()
#define o(a) cout << a << endl
#define fi first
#define se second
#define int long long
using namespace std;
typedef pair<int, int> P;
typedef pair<int, P> PP;

struct edge{
    int to, l, r;
};

const int INF = 1e9;
int n, m, si, ti;
vector<edge> G[100010];
vector<int> g[100010], d[100010];
vector<vector<edge> > nG[100010];

int getid(int pos, int t){
    vector<int> :: iterator it;
    it = lower_bound(all(g[pos]), t);
    assert(g[pos].end() != it);
    assert(*it == t);
    return it - g[pos].begin();
}

int dijkstra(){
    rep(i, 0, n){
        d[i].resize(g[i].size());
        rep(j, 0, d[i].size()){
            d[i][j] = INF;
        }
    }
    priority_queue<PP, vector<PP>, greater<PP> > q;
    d[si][0] = 0;
    q.push(PP(0, P(si, 0)));

    while(!q.empty()){
        PP p = q.top(); q.pop();
        int pos = p.se.fi;
        int tm = p.se.se;
        int cost = p.fi;
        if(cost > d[pos][tm]) continue;
        if(pos == ti) return cost;

        rep(i, 0, nG[pos][tm].size()){
            edge e = nG[pos][tm][i];
            int ntm = getid(e.to, e.r);
            if(d[e.to][ntm] > cost){
                d[e.to][ntm] = cost;
                q.push(PP(cost, P(e.to, ntm)));
            }
        }
        if(tm == g[pos].size() - 1) continue;
        int ncost = cost + g[pos][tm + 1] - g[pos][tm];
        if(d[pos][tm + 1] > ncost){
            d[pos][tm + 1] = ncost;
            q. push(PP(ncost, P(pos, tm + 1)));
        }
    }
    assert(0);
    return -1;
}

signed main(){
    cin >> n >> m >> si >> ti;
    si--; ti--;
    g[si]. push_back(0);
    rep(i, 0, m){
        int a, b, c, d;
        cin >> a >> b >> c >> d;
        a--; b--;
        G[a]. push_back((edge){b, c, c + d});
        g[a]. push_back(c);
        g[b]. push_back(c + d);
    }
    rep(i, 0, n){
        sort(all(g[i]));
        g[i].erase(unique(all(g[i])), g[i].end());
    }
    rep(i, 0, n){
        nG[i].resize(g[i].size());
        rep(j, 0, G[i].size()){
            edge e = G[i][j];
            int id = getid(i, e.l);
            nG[i][id]. push_back(e);
        }
    }
    cout << dijkstra() << endl;
}