#include <bits/stdc++.h>
#define INF 1000000000007LL
using namespace std;
typedef long long ll;
typedef pair<int,int> P;
typedef pair<ll,P> PP;
typedef pair<ll,int> PPP;

struct edge{
	int t;
	ll c;
	edge(){}
	edge(int tt,ll cc){
		t=tt;
		c=cc;
	}
};

int n,m,s1,s2,t;
ll a[2001],b[2001];
string w[2001];
vector<edge> G[1001];
vector<edge> G2[1001];
ll dist[2][1001][101];

ll labs(ll x){
	if(x<0LL)return -x;
	return x;
}

ll getnumber(string s){
	ll ans=0;
	for(int i=0;i<s.size();i++){
		ans*=10LL;
		ans+=(ll)(s[i]-'0');
	}
	return ans;
}

int ag2;

void dijk(int type,int s){
	dist[type][s][0]=0;
	priority_queue<PP,vector<PP>,greater<PP> > que;
	que.push(PP(0,P(s,0)));
	while(que.size()){
		PP p=que.top();
		que.pop();
		ll curc=p.first;
		int curv=p.second.first;
		int curu=p.second.second;
		if(dist[type][curv][curu]<curc)continue;
		for(int i=0;i<G[curv].size();i++){
			edge e=G[curv][i];
			if(e.c+dist[type][curv][curu]<dist[type][e.t][curu]){
				dist[type][e.t][curu]=e.c+dist[type][curv][curu];
				que.push(PP(dist[type][e.t][curu],P(e.t,curu)));
			}
		}
		if(curu==100)continue;
		for(int i=0;i<G2[curv].size();i++){
			edge e=G2[curv][i];
			if(e.c+dist[type][curv][curu]<dist[type][e.t][curu+1]){
				dist[type][e.t][curu+1]=e.c+dist[type][curv][curu];
				que.push(PP(dist[type][e.t][curu+1],P(e.t,curu+1)));
			}
		}
	}
}

ll getMin(int ty,int i,int j){
	if(ty==0){
		if(dist[0][t][i]>=INF)return INF;
		if(dist[1][t][j]>=INF)return INF;
	}
	if(ty==1){
		if(dist[0][t][i]>=INF)return INF;
		if(dist[0][t][j]>=INF)return INF;
	}
	if(ty==2){
		if(dist[1][t][i]>=INF)return INF;
		if(dist[1][t][j]>=INF)return INF;
	}
	if(i==j){
		if(ty==1 || ty==2)return INF;
		ll va=INF;
		ll vb=INF;
		for(ll l=0;l<=ag2;l++){
			va=min(va,dist[0][t][l]);
			vb=min(vb,dist[1][t][l]);
		}
		if(va==INF || vb==INF)return INF;
		return labs(va-vb);
	}
	ll b=(ll)(dist[1][t][j]-dist[0][t][i])/(i-j);
	if(ty==1){
		b=(ll)(dist[0][t][j]-dist[0][t][i])/(i-j);
	}
	if(ty==2){
		b=(ll)(dist[1][t][j]-dist[1][t][i])/(i-j);
	}
	ll ans=INF;
	for(ll k=max(b-3LL,0LL);k<=max(b+3LL,0LL);k++){
		ll va=INF;
		ll vb=INF;
		for(ll l=0;l<=ag2;l++){
			va=min(va,dist[0][t][l]+l*k);
			vb=min(vb,dist[1][t][l]+l*k);
		}
		if(va>=INF || vb>=INF)continue;
		ans=min(ans,labs(va-vb));
	}
	return ans;
}

void solve(){
	for(int i=0;i<n;i++){
		G[i].clear();
		G2[i].clear();
	}
	for(int i=0;i<m;i++){
		if(w[i]!="x"){
			ll val=getnumber(w[i]);
			G[a[i]].push_back(edge(b[i],val));
			G[b[i]].push_back(edge(a[i],val));
		}else{
			G2[a[i]].push_back(edge(b[i],0));
			G2[b[i]].push_back(edge(a[i],0));
		}
	}
	for(int i=0;i<2;i++){
		for(int j=0;j<n;j++){
			for(int k=0;k<=ag2;k++){
				dist[i][j][k]=INF;
			}
		}
	}
	dijk(0,s1);
	dijk(1,s2);
	ll ans=INF;
	for(int i=0;i<=ag2;i++){
		for(int j=0;j<=ag2;j++){
			ans=min(ans,getMin(0,i,j));
			ans=min(ans,getMin(1,i,j));
			ans=min(ans,getMin(2,i,j));
		}
	}
	printf("%lld\n",ans);
}

int main(void){
	while(1){
		scanf("%d%d%d%d%d",&n,&m,&s1,&s2,&t);
		if(n==0 && m==0 && s1==0 && s2==0 && t==0)break;
		s1--;
		s2--;
		t--;
		ag2=0;
		for(int i=0;i<m;i++){
			cin >> a[i] >> b[i] >> w[i];
			a[i]--;
			b[i]--;
			if(w[i]=="x")ag2++;
		}
		solve();
	}
	return 0;
}

Measured memory_bytes: 7004