#include <iostream>
#include <vector>
#include <queue>
#include <limits>
using namespace std;
using ll = long long;
const ll INF = numeric_limits<ll>::max();
int main() {
ios::sync_with_stdio(false);
cin.tie(nullptr);
int N, M;
cin >> N >> M;
vector<vector<pair<int,int>>> adj(N+1);
for(int i = 0; i < M; i++){
int a,b,c;
cin >> a >> b >> c;
adj[a].push_back({b,c});
adj[b].push_back({a,c});
}
int S, T, U, V;
cin >> S >> T >> U >> V;
vector<ll> dS(N+1, INF), dT(N+1, INF);
auto dijkstra = [&](int src, vector<ll>& dist){
priority_queue<pair<ll,int>, vector<pair<ll,int>>, greater<pair<ll,int>>> pq;
dist[src] = 0;
pq.push({0, src});
while(!pq.empty()){
pair<ll,int> cur = pq.top(); pq.pop();
ll d = cur.first;
int u = cur.second;
if(d > dist[u]) continue;
for(auto &edge : adj[u]){
int v = edge.first;
int w = edge.second;
if(dist[v] > d + w){
dist[v] = d + w;
pq.push({dist[v], v});
}
}
}
};
dijkstra(S, dS);
dijkstra(T, dT);
ll D = dS[T];
vector<vector<pair<int,ll>>> adj2(N+1);
for(int u = 1; u <= N; u++){
for(auto &edge : adj[u]){
int v = edge.first;
int w = edge.second;
ll cost = w;
if (dS[u] + w + dT[v] == D || dS[v] + w + dT[u] == D) {
cost = 0;
}
adj2[u].push_back({v, cost});
}
}
vector<ll> dist(N+1, INF);
priority_queue<pair<ll,int>, vector<pair<ll,int>>, greater<pair<ll,int>>> pq;
dist[U] = 0;
pq.push({0, U});
while(!pq.empty()){
pair<ll,int> cur = pq.top(); pq.pop();
ll d = cur.first;
int u = cur.second;
if(d > dist[u]) continue;
for(auto &edge : adj2[u]){
int v = edge.first;
ll w = edge.second;
if(dist[v] > d + w){
dist[v] = d + w;
pq.push({dist[v], v});
}
}
}
cout << dist[V] << "\n";
return 0;
}