#include <iostream>
#include <memory>
#include <vector>
using namespace std;
using ll=long long;
//定义二叉树
struct TreeNode{
int l,r;
ll sum=0;
ll lazy_tag=0;
unique_ptr<TreeNode> left;
unique_ptr<TreeNode> right;
TreeNode(int l,int r,ll sum):l(l),r(r),sum(sum),left(nullptr),right(nullptr){}
};
//定义全局sum数组
vector<ll> sum;
//定义arr数组
vector<int> arr;
//构建求和数组
void buildSumArr(int n){
sum[1]=arr[1];
for(int i=2;i<=n;i++){
sum[i]=sum[i-1]+arr[i];
}
}
//构建线段树
void buildSegmentTree(unique_ptr<TreeNode>& node){
if(node->l==node->r) return;
int mid=(node->l+node->r)/2;
ll leftSum=sum[mid]-sum[node->l-1];
ll rightSum=sum[node->r]-sum[mid];
node->left=make_unique<TreeNode>(node->l,mid,leftSum);
buildSegmentTree(node->left);
node->right=make_unique<TreeNode>(mid+1,node->r,rightSum);
buildSegmentTree(node->right);
}
//下推
void upDown(unique_ptr<TreeNode>& node){
if(node->left==nullptr || node->right==nullptr) return;
if(node->lazy_tag!=0){
node->left->sum+=node->lazy_tag*(node->left->r-node->left->l+1);
node->right->sum+=node->lazy_tag*(node->right->r-node->right->l+1);
node->left->lazy_tag+=node->lazy_tag;
node->right->lazy_tag+=node->lazy_tag;
node->lazy_tag=0;
}
}
//实现节点更新
void update(int L,int R,int x,unique_ptr<TreeNode>& node){
if(node->l>=L && node->r<=R){
node->sum+=(ll)x*(node->r-node->l+1);
node->lazy_tag+=x;
}else{
upDown(node);
//假设目标区间为【1,8】,mid为4,左子树为【1,4】,
//右子树为【5,8】
//查询【2,6】,则
// 递归更新左右子树
if (node->left&& L <= node->left->r ) {
update(L, R, x, node->left);
}
if (node->right && R>=node->right->l) {
update(L, R, x, node->right);
}
// 更新当前节点
if (node->left && node->right) {
node->sum = node->left->sum + node->right->sum;
}
}
}
//实现查询操作
void query(int L,int R,ll& totalSum,unique_ptr<TreeNode>& node){
if(node->l>=L && node->r<=R){
totalSum+=node->sum;
}else{
upDown(node);
if (node->left&& L <= node->left->r ) {
query(L, R, totalSum, node->left);
}
if (node->right && R>=node->right->l) {
query(L, R, totalSum, node->right);
}
}
}
int main(){
int n,q;
cin>>n>>q;
arr.resize(n+1, 0);
sum.resize(n+1,0);
for(int i=1;i<=n;i++){
cin>>arr[i];
}
buildSumArr(n);
unique_ptr<TreeNode> root=make_unique<TreeNode>(1,n,sum[n]);
buildSegmentTree(root);
while(q--){
int op;
cin>>op;
int l,r;
cin>>l>>r;
if(op==1){
int x;
cin>>x;
update(l, r, x, root);
}else{
ll totalSum=0;
query(l, r, totalSum, root);
cout<<totalSum<<endl;
}
}
return 0;
}
// 64 位输出请用 printf("%lld")