#include <bits/stdc++.h>
using namespace std;
struct edge {
  long long to, cost;
  edge() {}
  edge(long long a, long long b) { to = a, cost = b; }
};
long long n, m, Q;
long long dp[2005][2005];
vector<edge> G[2005];
vector<pair<long long, long long> > vec;
vector<pair<long long, pair<long long, long long> > > evec;
long long r[2005];
map<long long, long long> mp;
long long get(long long a, long long b, long long c, long long d) {
  long long ub = Q + 1, lb = 0, mid;
  while (ub - lb > 1) {
    mid = (ub + lb) / 2;
    if (a * mid + b >= c * mid + d)
      lb = mid;
    else
      ub = mid;
  }
  return lb;
}
long long calc(long long l, long long r, long long a, long long b) {
  b = (b % 1000000007 + 1000000007) % 1000000007;
  long long ret = r * (r + 1) / 2 - l * (l - 1) / 2;
  ret %= 1000000007;
  ret *= a, ret %= 1000000007;
  ret += b * (r - l + 1) % 1000000007, ret %= 1000000007;
  return ret;
}
int main(void) {
  ios::sync_with_stdio(0);
  cin.tie(0);
  cin >> n >> m >> Q;
  long long u, v, w;
  for (int i = 1; i <= m; i++) {
    cin >> u >> v >> w;
    G[u].push_back(edge(v, w));
    G[v].push_back(edge(u, w));
    evec.push_back(pair<long long, pair<long long, long long> >(
        w, pair<long long, long long>(u, v)));
  }
  for (int i = 0; i <= n; i++) {
    for (int j = 1; j <= n; j++) {
      dp[i][j] = -1e18;
    }
  }
  dp[0][1] = 0;
  for (int i = 0; i <= n; i++) {
    for (int j = 1; j <= n; j++) {
      for (int k = 0; k < G[j].size(); k++) {
        long long u = G[j][k].to;
        (dp[i + 1][u]) = max((dp[i + 1][u]), (dp[i][j] + G[j][k].cost));
      }
    }
  }
  long long ans = 0;
  for (int i = 0; i <= min(Q, n); i++) {
    long long mx = -1e18;
    for (int j = 1; j <= n; j++) {
      mx = max(mx, dp[i][j]);
    }
    ans += mx, ans %= 1000000007;
  }
  for (int i = 0; i < evec.size(); i++) {
    long long w = evec[i].first, u = evec[i].second.first,
              v = evec[i].second.second;
    long long mx = -1e18;
    for (int j = 0; j <= n; j++) {
      if (dp[j][u] < 0) continue;
      mx = max(mx, dp[j][u] - w * j);
    }
    for (int j = 0; j <= n; j++) {
      if (dp[j][v] < 0) continue;
      mx = max(mx, dp[j][v] - w * j);
    }
    if (mp.count(w) == 0) mp[w] = -1e18;
    mp[w] = max(mp[w], mx);
  }
  for (auto it = mp.begin(); it != mp.end(); it++)
    vec.push_back(pair<long long, long long>(it->first, it->second));
  sort(vec.begin(), vec.end());
  for (int i = 0; i < vec.size(); i++) {
    long long a = vec[i].first, b = vec[i].second;
    r[i] = Q;
    for (int j = i + 1; j < vec.size(); j++) {
      long long c = vec[j].first, d = vec[j].second;
      if (b <= d) {
        r[i] = -1;
        continue;
      }
      r[i] = min(r[i], get(a, b, c, d));
    }
  }
  long long l = n + 1;
  for (int i = 0; i < vec.size(); i++) {
    if (r[i] < l) continue;
    ans += calc(l, r[i], vec[i].first, vec[i].second);
    ans %= 1000000007;
    l = r[i] + 1;
  }
  cout << ans << endl;
  return 0;
}
