#include <iostream>
#include <stdio.h>
#include <string.h>
#include <algorithm>
#define lchild left,mid,root<<1
#define rchild mid+1,right,root<<1|1
using namespace std;
const int maxn = 100010;
int lsum[maxn<<2],rsum[maxn<<2],Max[maxn<<2],lazy[maxn<<2];
long long lnum[maxn<<2],rnum[maxn<<2];
///更新当前节点的值
void push_up(int left,int right,int root) {
lnum[root] = lnum[root<<1]; ///区间的左边界是其左区间的左边界
rnum[root] = rnum[root<<1|1]; ///区间的有边界是其右区间的右边界
lsum[root] = lsum[root<<1]; ///以左端点为开始的连续递增序列长度是其左区间以左边界开始的连续递增序列长度
rsum[root] = rsum[root<<1|1]; ///以右断电为结束的连续递增序列长度是其右区间以有边界结束的连续递增序列长度
Max[root] = max(Max[root<<1],Max[root<<1|1]);
long long leftright = rnum[root<<1]; ///左区间的右侧数字
long long rightleft = lnum[root<<1|1]; ///右区间的左侧数字
int mid = (left+right)>>1;
///两个区间可能拼接在一起。
if(leftright<rightleft) {
if(lsum[root] == mid-left+1) {
lsum[root] += lsum[root<<1|1];
}
if(rsum[root] == right-mid) {
rsum[root] += rsum[root<<1];
}
Max[root] = max(Max[root],rsum[root<<1]+lsum[root<<1|1]);
}
}
void push_down(int root) {
if(lazy[root]) {
lazy[root<<1] += lazy[root];
lazy[root<<1|1] += lazy[root];
lnum[root<<1] += lazy[root];
rnum[root<<1] += lazy[root];
lnum[root<<1|1] += lazy[root];
rnum[root<<1|1] += lazy[root];
lazy[root] = 0;
}
}
void build(int left,int right,int root) {
lazy[root] = 0;
if(left == right) {
scanf("%lld",&lnum[root]);
rnum[root] = lnum[root];
Max[root] = lsum[root] = rsum[root] = 1;
return;
}
int mid = (left+right)>>1;
build(lchild);
build(rchild);
push_up(left,right,root);
}
void update(int L,int R,int add,int left,int right,int root) {
if(L<=left && right<=R) {
lnum[root] += add;
rnum[root] += add;
lazy[root] += add;
return;
}
push_down(root);
int mid = (left+right)>>1;
if(L<=mid) update(L,R,add,lchild);
if(R>mid) update(L,R,add,rchild);
push_up(left,right,root);
}
int query(int L,int R,int left,int right,int root) {
if(L<=left && right<=R) {
return Max[root];
}
push_down(root);
int ans = 1;
int mid = (left+right)>>1;
if(L<=mid) ans = max(ans,query(L,R,lchild));
if(R>mid) ans = max(ans,query(L,R,rchild));
if(rnum[root<<1] < lnum[root<<1|1]) {
ans = max(ans,min(R,mid+lsum[root<<1|1])-max(L,mid-rsum[root<<1]+1)+1);
}
return ans;
}
int main() {
int T,Case=0;
scanf("%d",&T); ///T组测试数据
while(T--) {
int N,Q;
scanf("%d%d",&N,&Q); ///N个数字,Q次操作
build(1,N,1);
char op;
int L,R,V;
printf("Case #%d:\n",++Case);
while(Q--) {
scanf(" %c",&op);
if(op == 'a') {
scanf("%d%d%d",&L,&R,&V);
update(L,R,V,1,N,1);
} else {
scanf("%d%d",&L,&R);
int ans = query(L,R,1,N,1);
printf("%d\n",ans);
}
}
}
return 0;
}