#include <iostream>
#include <fstream>
#define dim (1<<17)+5
using namespace std;
ifstream fin("hotel.in");
ofstream fout("hotel.out");
struct aiNod
{
int l, mid, r;
aiNod()
{
l=mid=r=1;
}
};
aiNod arb[dim];
int n,m,op, A,B,N,ex1[dim], st,dr,val;
void constructTree(int nod, int low, int high)
{
if(low == high)return;
int mid = (low+high)/2;
constructTree(nod*2, low, mid);
constructTree(nod*2+1, mid+1, high);
if(ex1[nod]==0)
{
arb[nod].l = arb[nod].r = arb[nod].mid = arb[nod*2].mid + arb[nod*2+1].mid;
return;
}
arb[nod].l = arb[nod*2].l;
arb[nod].r = arb[nod*2+1].r;
arb[nod].mid = max(max(arb[nod*2].mid, arb[nod*2+1].mid),arb[nod*2].r+arb[nod*2+1].l);
}
void Update_ex1(int nod, int left, int right)
{
if(left==right && st<=left && left <= dr)
{
ex1[nod] = val;
return;
}
if(left > dr || right < st)return;
int mid = (left+right)/2;
Update_ex1(nod*2, left, mid);
Update_ex1(nod*2+1, mid+1, right);
ex1[nod] = ex1[nod*2] + ex1[nod*2+1];
}
void UpdateTree(int nod, int left, int right)
{
if(left==right && st<=left && left <= dr)
{
arb[nod].l = arb[nod].r = arb[nod].mid = val;
return;
}
if(left > dr || right < st)return;
int mid = (left+right)/2;
UpdateTree(nod*2, left, mid);
UpdateTree(nod*2+1, mid+1, right);
if(ex1[nod]==0)
{
arb[nod].l = arb[nod].r = arb[nod].mid = arb[nod*2].mid + arb[nod*2+1].mid;
return;
}
arb[nod].l = arb[nod*2].l;
arb[nod].r = arb[nod*2+1].r;
arb[nod].mid = max(max(arb[nod*2].mid, arb[nod*2+1].mid),arb[nod*2].r+arb[nod*2+1].l);
}
int main()
{
fin>>n>>m;
for(N=1; N<n; N<<=1);
for(int i=n+1; i<=N; i++)arb[N+i-1].l= arb[N+i-1].mid=arb[N+i-1].r=0;
if(n<N){
st=N; dr=n+1; val=1;
Update_ex1(1,1,N);
}
constructTree(1,1,N);
while(m--)
{
fin>>op;
if(op==3)
fout<<max(max(arb[1].mid, arb[1].l),arb[1].r)<<'\n';
else
{
fin>>A>>B;
if(op==1)
{
st=A; dr=A+B-1; val=1;
Update_ex1(1,1,N);
val=0;
UpdateTree(1,1,N);
}
else
{
st=A; dr=A+B-1; val=0;
Update_ex1(1,1,N);
val=1;
UpdateTree(1,1,N);
}
}
}
return 0;
}