#include <bits/stdc++.h>
using namespace std;
ifstream in ("hotel.in");
ofstream out ("hotel.out");
struct node
{
int pref, suff, maxim, cnt;
int lazy;
};
node a[400005];
node operator + (node a, node b)
{
node ans;
if (a.cnt == a.pref)
ans.pref = a.cnt + b.pref;
else
ans.pref = a.pref;
if (b.cnt == b.suff)
ans.suff = b.cnt + a.suff;
else
ans.suff = b.suff;
ans.cnt = a.cnt + b.cnt;
ans.maxim = max(a.maxim, b.maxim);
ans.maxim = max(ans.maxim, ans.pref);
ans.maxim = max(ans.maxim, ans.suff);
ans.maxim = max(ans.maxim, a.suff + b.pref);
ans.lazy = 0;
return ans;
}
void propagate (int nod, int st, int dr)
{
if (a[nod].lazy == 0)
return;
if (a[nod].lazy > 0) /// lazy = 1 daca sunt ocupate
{
if (st < dr)
a[2*nod].lazy = a[2*nod+1].lazy = 1;
a[nod].lazy = 0;
a[nod].pref = a[nod].suff = a[nod].maxim = 0;
}
else /// lazy = -1 daca sunt libere
{
if (st < dr)
a[2*nod].lazy = a[2*nod+1].lazy = -1;
a[nod].lazy = 0;
a[nod].pref = a[nod].suff = a[nod].maxim = a[nod].cnt;
}
}
void build (int nod, int st, int dr)
{
if (st == dr)
{
a[nod] = {1, 1, 1, 1, 0};
return;
}
int mid = (st + dr) / 2;
build(2*nod, st, mid);
build(2*nod+1, mid+1, dr);
a[nod] = a[2*nod] + a[2*nod+1];
}
void update (int nod, int st, int dr, int l, int r, int val)
{
propagate(nod, st, dr);
if (l <= st && dr <= r)
{
a[nod].lazy = val;
propagate(nod, st, dr);
}
else
{
int mid = (st + dr) / 2;
if (l <= mid)
update(2*nod, st, mid, l, r, val);
if (mid < r)
update(2*nod+1, mid+1, dr, l, r, val);
propagate(2*nod, st, mid);
propagate(2*nod+1, mid+1, dr);
a[nod] = a[2*nod] + a[2*nod+1];
}
}
/**
1 2 3 4 5 6 7 8 9 10 11 12
x x x x
**/
int main()
{
int n, q;
in >> n >> q;
build(1, 1, n);
while (q--)
{
int op;
in >> op;
if (op == 1)
{
int x, y;
in >> x >> y;
update(1, 1, n, x, x+y-1, 1);
}
else if (op == 2)
{
int x, y;
in >> x >> y;
update(1, 1, n, x, x+y-1, -1);
}
else
out << a[1].maxim << '\n';
}
return 0;
}