#include<cstdio>
#include<iostream>
#include<vector>
#include<queue>
#include<bitset>
#include<string>
#include<stack>
#include<set>
#include<map>
#include<cstring>
#include<complex>
#include<cmath>
#include<algorithm>
#include<list>
#include<functional>
#define mp make_pair
#define X first
#define Y second
#define INF 1987654321
#define PI 3.14159265358979323846264
#define MOD 1000000007LL
#define fup(i,a,b,c) for(int (i)=(a);(i)<=(b);(i)+=(c))
#define fdn(i,a,b,c) for(int (i)=(a);(i)>=(b);(i)-=(c))
#define MEM0(a) memset(a,0,sizeof(a));
#define MEM_1(a) memset(a,-1,sizeof(a));
#define ALL(a) a.begin(),a.end()
using namespace std;
typedef long long ll;
typedef unsigned int uint;
typedef unsigned long long ull;
typedef pair<int, int> Pi;
typedef pair<ll, ll> Pll;
typedef pair<double, double> Pd;
typedef vector<int> Vi;
typedef vector<ll> Vll;
typedef vector<double> Vd;
typedef vector<Pi> VPi;
typedef vector<Pll> VPll;
typedef vector<Pd> VPd;
typedef complex<double> base;
ll POW(ll a, ll b) { if (b == 0)return 1; if (b == 1)return a; if (b & 1)return (a*POW(a, b - 1)) % MOD; ll t = POW(a, b / 2); return (t*t) % MOD; }
int gcd(int a, int b) { return b ? gcd(b, a%b) : a; }
int dx[] = { 0,-1,1,0 }, dy[] = { 1,0,0,-1 };//동북남서
int p[200001];
int Ltree[524288], Rtree[524288];
struct A {
int l, r, x;
};
void update(int node, int S, int E, int i)
{
if (S == E)
{
Ltree[node] = Rtree[node] = 1;
return;
}
if (i <= (S + E) / 2) update(node * 2, S, (S + E) / 2, i);
else update(node * 2 + 1, (S + E) / 2 + 1, E, i);
Ltree[node] = Ltree[node * 2];
if (Ltree[node] == (S + E) / 2 - S + 1)Ltree[node] += Ltree[node * 2 + 1];
Rtree[node] = Rtree[node * 2 + 1];
if (Rtree[node] == E-(S+E)/2)Rtree[node] += Rtree[node * 2];
}
A Lfind(int node, int S, int E, int i, int j)
{
if (i > E || j < S)return{ -1,-1,-1 };
if (i <= S && j >= E)return{ S,E,Ltree[node] };
A m1 = Lfind(node * 2, S, (S + E) / 2, i, j);
A m2 = Lfind(node * 2 + 1, (S + E) / 2 + 1, E, i, j);
if (m1.x == -1)return m2;
if (m2.x == -1)return m1;
if (m1.r - m1.l + 1 == m1.x)return{ m1.l,m2.r,m1.x + m2.x };
return m1;
}
A Rfind(int node, int S, int E, int i, int j)
{
if (i > E || j < S)return{ -1,-1,-1 };
if (i <= S && j >= E)return{ S,E,Rtree[node] };
A m1 = Rfind(node * 2, S, (S + E) / 2, i, j);
A m2=Rfind(node * 2 + 1, (S + E) / 2 + 1, E, i, j);
if (m1.x == -1)return m2;
if (m2.x == -1)return m1;
if (m2.r - m2.l + 1 == m2.x)return{ m1.l,m2.r,m1.x + m2.x };
return m2;
}
int main() {
int n;
scanf("%d", &n);
fup(i, 1, n, 1)
{
int x;
scanf("%d", &x);
p[x] = i;
}
ll ans = 0;
fdn(i, n, 1, 1)
{
int t = p[i];
update(1, 1, n, t);
ans += 1LL * i*Lfind(1, 1, n, t, n).x*Rfind(1, 1, n, 1, t).x;
}
printf("%lld", ans);
}