#include <algorithm>
#include <bitset>
#include <cassert>
#include <cfloat>
#include <climits>
#include <cmath>
#include <complex>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <ctime>
#include <fstream>
#include <functional>
#include <iomanip>
#include <iostream>
#include <list>
#include <map>
#include <memory>
#include <numeric>
#include <queue>
#include <set>
#include <sstream>
#include <stack>
#include <string>
#include <utility>
#include <vector>

// c++11
#include <array>
#include <tuple>
#include <unordered_map>
#include <unordered_set>

#define mp make_pair
#define mt make_tuple
#define rep(i, n) for (int i = 0; i < (n); i++)

using namespace std;

using ll = long long;
using ull = unsigned long long;
using pii = pair<int, int>;

const int INF = 1 << 29;
const ll LL_INF = 1LL << 60;
const double EPS = 1e-9;
const ll MOD = 1000000007;

const int dx[] = {1, 0, -1, 0}, dy[] = {0, -1, 0, 1};
//begin
template <class T>
class SqrtDecompositionRangeAddRangeSum
{
  private:
    int N, K;
    int sqrtN;
    vector<T> data;
    vector<T> bucket_sum;
    vector<T> bucket_add;

  public:
    SqrtDecompositionRangeAddRangeSum(int n) : N(n), K(0), sqrtN(1)
    {
        while (sqrtN * sqrtN <= N)
        {
            sqrtN++;
        }
        K = (N + sqrtN - 1) / sqrtN;
        data.assign(K * sqrtN, 0);
        bucket_sum.assign(K, 0);
        bucket_add.assign(K, 0);
    }
    // [s, t)
    void add(int s, int t, T x)
    {
        int p = s / sqrtN;
        int q = t / sqrtN;
        for (int k = p; k <= q; ++k)
        {
            int l = k * sqrtN, r = (k + 1) * sqrtN;
            if (r <= s || t <= l)
                continue;
            if (s <= l && r <= t)
            {
                bucket_add[k] += x;
            }
            else
            {
                eval(k);
                for (int i = max(s, l); i < min(t, r); ++i)
                {
                    data[i] += x;
                    bucket_sum[k] += x;
                }
            }
        }
    }
    // [s, t)
    T get_sum(int s, int t)
    {
        int p = s / sqrtN;
        int q = t / sqrtN;
        T sum = 0;
        for (int k = p; k <= q; ++k)
        {
            int l = k * sqrtN, r = (k + 1) * sqrtN;
            if (r <= s || t <= l)
                continue;
            if (s <= l && r <= t)
            {
                sum += bucket_sum[k] + bucket_add[k] * sqrtN;
            }
            else
            {
                eval(k);
                for (int i = max(s, l); i < min(t, r); ++i)
                {
                    // sum += data[i] + bucket_add[k];
                    sum += data[i];
                }
            }
        }
        return sum;
    }
    void update(int i, T val)
    {
        int k = i / sqrtN;
        eval(k);
        data[i] = val;
    }
    void eval(int k)
    {
        if (bucket_add[k] == 0)
        {
            return;
        }
        for (int i = sqrtN * k; i < sqrtN * (k + 1); i++)
        {
            data[i] += bucket_add[k];
            bucket_sum[k] += bucket_add[k];
        }
        bucket_add[k] = 0;
    }
    T get(int i)
    {
        int k = i / sqrtN;
        return data[i] + bucket_add[k];
    }
};
//end
int main()
{
    ios::sync_with_stdio(false);
    int N, Q;
    cin >> N >> Q;
    SqrtDecompositionRangeAddRangeSum<ll> decomp(N);
    while (Q--)
    {
        int c;
        cin >> c;
        if (c == 0)
        {
            int s, t, x;
            cin >> s >> t >> x;

            decomp.add(s - 1, t, (long long)x);
        }
        else
        {
            int s, t;
            cin >> s >> t;

            cout << decomp.get_sum(s - 1, t) << endl;
        }
    }

    // for (int i = 0; i < N; i++)
    // {
    //     cout << decomp.get(i) << " ";
    // }

    // cout << endl;
    // cout << decomp.get_sum(0, 3) << endl;
    // cout << decomp.get(3) << endl;
}

Measured memory_bytes: 3616