#include <stdio.h>
#include <string.h>
#define MAXN 350
#define MAXM 12500
#define INF 2000000000
int ut[MAXN], nd[2 * MAXM], nxt[2 * MAXM], cost[2 * MAXM], cpc[2 * MAXM], fol[2 * MAXM], dr;
int dist[MAXN], q[MAXN * MAXN];
int heap[MAXN], hnod[MAXN], pozh[MAXN], prev[MAXN], mch[MAXN], dijdist[MAXN];
int real[MAXN];
inline void add(int x, int y, int c, int ct){
nd[dr] = y;
nxt[dr] = ut[x];
cost[dr] = ct;
cpc[dr] = c;
ut[x] = dr;
dr++;
}
void bell(int n, int s){
memset(dist, 0x7f, sizeof dist);
int poz, dr = 1, st = 0;
q[0] = s;
dist[s] = 0;
while(st < dr){
poz = ut[q[st]];
while(poz != -1){
if(dist[q[st]] + cost[poz] < dist[nd[poz]] && !(poz & 1)){
dist[nd[poz]] = dist[q[st]] + cost[poz];
q[dr] = nd[poz];
dr++;
}
poz = nxt[poz];
}
st++;
}
}
inline void intersch(int x, int y){
int aux;
pozh[hnod[x]] = y; pozh[hnod[y]] = x;
aux = heap[x]; heap[x] = heap[y]; heap[y] = aux;
aux = hnod[x]; hnod[x] = hnod[y]; hnod[y] = aux;
}
inline void urc(int x){
while(x > 0 && heap[x] < heap[(x - 1) / 2]){
intersch(x, (x - 1) / 2);
x = (x - 1) / 2;
}
}
inline void cobor(int x, int dr){
int best;
char g = 1;
while(g && 2 * x + 1 < dr){
best = 2 * x + 1;
if(2 * x + 2 < dr && heap[2 * x + 2] < heap[best])
best = 2 * x + 2;
if(heap[x] > heap[best]){
intersch(x, best);
x = best;
}
else
g = 0;
}
}
void dijkstra(int n, int s){
memset(pozh, -1, sizeof pozh);
memset(prev, -1, sizeof prev);
memset(mch, -1, sizeof mch);
memset(dijdist, -1, sizeof dijdist);
int dr = 1, ch, cn, poz, ad;
heap[0] = 0;
hnod[0] = s;
pozh[s] = 0;
dijdist[s] = 0;
while(dr > 0){
dijdist[hnod[0]] = heap[0];
ch = heap[0];
cn = hnod[0];
intersch(0, dr - 1);
pozh[hnod[dr - 1]] = -1;
dr--;
cobor(0, dr);
poz = ut[cn];
while(poz != -1){
if(cpc[poz] - fol[poz] > 0 && dijdist[nd[poz]] == -1){
if(poz & 1)
ad = dist[nd[poz - 1]] - dist[nd[poz]];
else
ad = dist[nd[poz + 1]] - dist[nd[poz]];
if(pozh[nd[poz]] == -1){
prev[nd[poz]] = cn;
mch[nd[poz]] = poz;
heap[dr] = ch + cost[poz] + ad;
real[nd[poz]] = real[cn] + cost[poz];
hnod[dr] = nd[poz];
pozh[nd[poz]] = dr;
urc(dr);
dr++;
}
else if(heap[pozh[nd[poz]]] > ch + cost[poz] + ad){
prev[nd[poz]] = cn;
mch[nd[poz]] = poz;
heap[pozh[nd[poz]]] = ch + cost[poz] + ad;
real[nd[poz]] = real[cn] + cost[poz];
urc(pozh[nd[poz]]);
}
}
poz = nxt[poz];
}
}
int i;
for(i = 0; i < n; i++)
dist[i] = real[i];
}
int main(){
FILE *in = fopen("fmcm.in", "r");
int n, m, s, d, i, x, y, z, t;
fscanf(in, "%d%d%d%d", &n, &m, &s, &d);
s--; d--;
memset(ut, -1, sizeof ut);
for(i = 0; i < m; i++){
fscanf(in, "%d%d%d%d", &x, &y, &z, &t);
x--; y--;
add(x, y, z, t);
add(y, x, 0, -t);
}
fclose(in);
bell(n, s);
int augm = 1, rez = 0, sum;
while(augm > 0){
dijkstra(n, s);
augm = 0;
if(prev[d] != -1){
augm = INF;
x = d;
sum = 0;
while(x != s){
if(augm > cpc[mch[x]] - fol[mch[x]])
augm = cpc[mch[x]] - fol[mch[x]];
if(mch[x] & 1)
sum += cost[mch[x]];
else
sum += cost[mch[x]];
x = prev[x];
}
x = d;
while(x != s){
fol[mch[x]] += augm;
x = prev[x];
}
rez += augm * sum;
}
}
FILE *out = fopen("fmcm.out", "w");
fprintf(out, "%d", rez);
fclose(out);
return 0;
}