// P1266 速度限制
// Memory Limit: 256 MB
// Time Limit: 1000 ms
#include<bits/stdc++.h>
using namespace std;
const int N = 503;
int n , m , e;
struct edge{
int u , v , w , cx;
void add(int a , int b , int c , int d){
u = a , v = b , w = c , cx = d;
}
};
struct node{
int opt , d , sp;
bool operator < (const node& A) const {
return d > A.d;
}
};
vector<edge> ve[N];
int pre[N][N][2];
double dis[N][N];
bool vis[N][N];
void print(int u , int v){
if(u){
print(pre[u][v][0] , pre[u][v][1]);
}
cout << u << " ";
}
void dijkstra(int st){
for(int i = 0 ; i < n ; i++){
for(int j = 0 ; j < N ; j++){
dis[i][j] = 1e9 + 7;
}
}
dis[st][70] = 0;
priority_queue<node> qu;
qu.push({st , 0 , 70});
while(!qu.empty()){
int u = qu.top().opt;
int sp = qu.top().sp;
qu.pop();
if(vis[u][sp]) continue;
vis[u][sp] = 1;
for(auto ed : ve[u]){
int v = ed.v , w = ed.w , cx = ed.cx ? ed.cx : sp;
double len = (double)w / (double)cx;
if(dis[v][cx] > dis[u][sp] + len){
dis[v][cx] = dis[u][sp] + len;
pre[v][cx][0] = u;
pre[v][cx][1] = sp;
if(!vis[v][cx]){
qu.push({v , dis[v][cx] , cx});
}
}
}
}
}
int main(){
cin >> n >> m >> e;
for(int i = 1 ; i <= m ; i++){
int x , y , z , l;
cin >> x >> y >> z >> l;
ve[x].push_back({x , y , l , z});
}
dijkstra(0);
int s = 0;
for(int i = 1 ; i < N ; i++){
if(dis[e][i] < dis[e][s]){
s = i;
}
}
print(e , s);
return 0;
}