#include using namespace std; using ll = long long; using ld = long double; const int mod = 1e9 + 7; template T add(T x) { return x; } template T add(T x, Ts... y) { T res = x + add(y...); if (res >= mod) res -= mod; return res; } template T sub(T x, Ts... y) { return add(x, mod - add(y...)); } template void udd(T& x, Ts... y) { x = add(x, y...); } template void uub(T& x, Ts... y) { x = sub(x, y...); } template T mul(T x) { return x; } template T mul(T x, Ts... y) { return (x * 1ll * mul(y...)) % mod; } template void uul(T& x, Ts... y) { x = mul(x, y...); } int bin(int a, ll deg) { int r = 1; while (deg) { if (deg & 1) uul(r, a); deg >>= 1; uul(a, a); } return r; } int inv(int x) { assert(x); return bin(x, mod - 2); } const int maxn = 2000200; int S[maxn]; int S2[maxn]; vector gen_array(vector v) { vector res; for (int k = 1; k <= (int) v.size(); ++k) { for (int l = 0; l + k <= (int) v.size(); ++l) { int r = l + k; int mx = 0; for (int i = l; i < r; ++i) { mx = max(mx, v[i]); } res.push_back(mx); } } return res; } int c2(ll x) { return (x * (x + 1) / 2) % mod; } int cfast(int a, int b) { if (a > b) { swap(a, b); } if (a == 0) { return S[b]; } int cur = sub(S2[a + b], S2[b - a]); return add(cur, cfast(0, b - a)); } int calc2(int a, int b) { assert(a >= 0 && b >= 0); return cfast(a, b); int res = 0; while (a || b) { int k = a + b; udd(res, (k * ll(k + 1) / 2) % mod); if (a) { --a; } if (b) { --b; } } return res; } int solve(vector a) { int n = (int) a.size(); vector> v(n); set s; s.insert(-1); s.insert(n); for (int i = 0; i < n; ++i) { v[i] = {a[i], i}; } sort(v.begin(), v.end()); reverse(v.begin(), v.end()); int total = (n * ll(n + 1) / 2) % mod; total = (total * ll(total + 1) / 2) % mod; int bad = 0; int res = 0; for (auto p : v) { int pos = p.second; int val = p.first; auto nx = s.lower_bound(pos); auto pr = prev(nx); int l = pos - *pr - 1; int r = *nx - pos - 1; s.insert(pos); //cerr << "put " << pos << '\n'; int k = l + r + 1; if (k != n) { int cnt = 0; int tend = n - *prev(prev(s.end())) - 1; int tbegin = *next(s.begin()); if (*pr == -1 && tend > 0) { int t = tend; //cerr << "TL " << t << '\n'; cnt = c2(k); udd(cnt, calc2(t, k - 1)); uub(cnt, c2(l)); uub(cnt, calc2(max(0, l - 1), t)); uub(cnt, calc2(r, 0)); } else if (*nx == n && tbegin > 0) { int t = tbegin; //cerr << "TR " << t << '\n'; cnt = calc2(k, t - 1); uub(cnt, calc2(l, 0)); uub(cnt, calc2(r, t - 1)); } else { cnt = calc2(k, 0); uub(cnt, calc2(l, 0)); uub(cnt, calc2(r, 0)); } cerr << "cnt: " << cnt << '\n'; udd(bad, cnt); udd(res, mul(cnt, val)); } } int cnt_max = sub(total, bad); //cerr << "cnt_max: " << cnt_max << '\n'; udd(res, mul(cnt_max, v[0].first)); return res; } int naive(vector a) { auto vans = gen_array(gen_array(a)); return accumulate(vans.begin(), vans.end(), 0ll) % mod; } signed main() { #ifdef LOCAL assert(freopen("g.in", "r", stdin)); #endif int n; cin >> n; vector a(n); for (int i = 0; i < n; ++i) { cin >> a[i]; } for (int i = 0; i < maxn; ++i) { S[i] = i ? S[i - 1] : 0; S2[i] = i > 1 ? S2[i - 2] : 0; udd(S[i], c2(i)); udd(S2[i], c2(i)); } cout << solve(a) << '\n'; //mt19937 rr; //while (true) { //int n = 50; //vector a(n); //for (int i = 0; i < n; ++i) { //a[i] = rr() % int(1e6); //} //int res = solve(a); //int res2 = naive(a); //for (int x : a) { //cerr << x << ' '; //} //cerr << '\n'; //cerr << res << ' ' << res2 << '\n'; //assert(res == res2); //} }