#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef pair<int, int> ii;
const int INF = 1e9;
const ll LINF = 1e18;
const int MOD = 1e9 + 7;
const int N = 1e5 + 5;
int add(int a, int b) {
return (a + b) % MOD;
}
int mul(int a, int b) {
return 1ll * a * b % MOD;
}
int n, q;
int a[N];
int seg[4 * N];
ii lazy[4 * N]; // lazy[id] = {mul, add}: seg[id] * mul + add
void initLazy() {
for (int id = 1; id <= 4 * n; id++) lazy[id] = {1, 0};
}
void build(int id, int l, int r) {
if (l == r) {
seg[id] = a[l];
return;
}
int mid = (l + r) >> 1;
build(id * 2, l, mid);
build(id * 2 + 1, mid + 1, r);
seg[id] = add(seg[id * 2], seg[id * 2 + 1]);
}
void push(int id, int l, int r) {
int mid = (l + r) >> 1;
seg[id * 2] = add(mul(seg[id * 2], lazy[id].first), mul(mid - l + 1, lazy[id].second));
lazy[id * 2].first = mul(lazy[id * 2].first, lazy[id].first);
lazy[id * 2].second = add(mul(lazy[id * 2].second, lazy[id].first), lazy[id].second);
seg[id * 2 + 1] = add(mul(seg[id * 2 + 1], lazy[id].first), mul(r - mid, lazy[id].second));
lazy[id * 2 + 1].first = mul(lazy[id * 2 + 1].first, lazy[id].first);
lazy[id * 2 + 1].second = add(mul(lazy[id * 2 + 1].second, lazy[id].first), lazy[id].second);
lazy[id] = {1, 0};
}
void update(int id, int l, int r, int u, int v, ii val) {
if (l > v || r < u) return;
if (u <= l && r <= v) {
seg[id] = add(mul(seg[id], val.first), mul(r - l + 1, val.second));
lazy[id].first = mul(lazy[id].first, val.first);
lazy[id].second = add(mul(lazy[id].second, val.first), val.second);
return;
}
push(id, l, r);
int mid = (l + r) >> 1;
update(id * 2, l, mid, u, v, val);
update(id * 2 + 1, mid + 1, r, u, v, val);
seg[id] = add(seg[id * 2], seg[id * 2 + 1]);
}
int get(int id, int l, int r, int u, int v) {
if (l > v || r < u) return 0;
if (u <= l && r <= v) return seg[id];
push(id, l, r);
int mid = (l + r) >> 1;
return add(get(id * 2, l, mid, u, v), get(id * 2 + 1, mid + 1, r, u, v));
}
int main() {
ios::sync_with_stdio(0); cin.tie(0);
cin >> n >> q;
for (int i = 1; i <= n; i++) cin >> a[i];
build(1, 1, n);
initLazy();
while (q--) {
int type, l, r;
cin >> type >> l >> r;
if (type == 4) {
cout << get(1, 1, n, l, r) << '\n';
}
else {
int x; cin >> x;
ii val;
if (type == 1) val = {1, x};
if (type == 2) val = {x, 0};
if (type == 3) val = {0, x};
update(1, 1, n, l, r, val);
}
}
}
I2luY2x1ZGUgPGJpdHMvc3RkYysrLmg+IAp1c2luZyBuYW1lc3BhY2Ugc3RkOyAgCgp0eXBlZGVmIGxvbmcgbG9uZyBsbDsgIAp0eXBlZGVmIHBhaXI8aW50LCBpbnQ+IGlpOyAgCgpjb25zdCBpbnQgSU5GID0gMWU5OyAgCmNvbnN0IGxsIExJTkYgPSAxZTE4OyAgCgpjb25zdCBpbnQgTU9EID0gMWU5ICsgNzsgIAoKY29uc3QgaW50IE4gPSAxZTUgKyA1OyAgCgppbnQgYWRkKGludCBhLCBpbnQgYikgewoJcmV0dXJuIChhICsgYikgJSBNT0Q7ICAKfQoKaW50IG11bChpbnQgYSwgaW50IGIpIHsKCXJldHVybiAxbGwgKiBhICogYiAlIE1PRDsgCn0KCmludCBuLCBxOyAKaW50IGFbTl07ICAKCmludCBzZWdbNCAqIE5dOyAgCmlpIGxhenlbNCAqIE5dOyAvLyBsYXp5W2lkXSA9IHttdWwsIGFkZH06IHNlZ1tpZF0gKiBtdWwgKyBhZGQKCnZvaWQgaW5pdExhenkoKSB7Cglmb3IgKGludCBpZCA9IDE7IGlkIDw9IDQgKiBuOyBpZCsrKSBsYXp5W2lkXSA9IHsxLCAwfTsgCn0KCnZvaWQgYnVpbGQoaW50IGlkLCBpbnQgbCwgaW50IHIpIHsKCWlmIChsID09IHIpIHsKCQlzZWdbaWRdID0gYVtsXTsgCgkJcmV0dXJuOyAKCX0KCglpbnQgbWlkID0gKGwgKyByKSA+PiAxOyAKCWJ1aWxkKGlkICogMiwgbCwgbWlkKTsgCglidWlsZChpZCAqIDIgKyAxLCBtaWQgKyAxLCByKTsgIAoKCXNlZ1tpZF0gPSBhZGQoc2VnW2lkICogMl0sIHNlZ1tpZCAqIDIgKyAxXSk7IAp9Cgp2b2lkIHB1c2goaW50IGlkLCBpbnQgbCwgaW50IHIpIHsKCWludCBtaWQgPSAobCArIHIpID4+IDE7ICAKCglzZWdbaWQgKiAyXSA9IGFkZChtdWwoc2VnW2lkICogMl0sIGxhenlbaWRdLmZpcnN0KSwgbXVsKG1pZCAtIGwgKyAxLCBsYXp5W2lkXS5zZWNvbmQpKTsgCglsYXp5W2lkICogMl0uZmlyc3QgPSBtdWwobGF6eVtpZCAqIDJdLmZpcnN0LCBsYXp5W2lkXS5maXJzdCk7IAoJbGF6eVtpZCAqIDJdLnNlY29uZCA9IGFkZChtdWwobGF6eVtpZCAqIDJdLnNlY29uZCwgbGF6eVtpZF0uZmlyc3QpLCBsYXp5W2lkXS5zZWNvbmQpOyAKCglzZWdbaWQgKiAyICsgMV0gPSBhZGQobXVsKHNlZ1tpZCAqIDIgKyAxXSwgbGF6eVtpZF0uZmlyc3QpLCBtdWwociAtIG1pZCwgbGF6eVtpZF0uc2Vjb25kKSk7IAoJbGF6eVtpZCAqIDIgKyAxXS5maXJzdCA9IG11bChsYXp5W2lkICogMiArIDFdLmZpcnN0LCBsYXp5W2lkXS5maXJzdCk7IAoJbGF6eVtpZCAqIDIgKyAxXS5zZWNvbmQgPSBhZGQobXVsKGxhenlbaWQgKiAyICsgMV0uc2Vjb25kLCBsYXp5W2lkXS5maXJzdCksIGxhenlbaWRdLnNlY29uZCk7IAoKCWxhenlbaWRdID0gezEsIDB9OyAKfQoKdm9pZCB1cGRhdGUoaW50IGlkLCBpbnQgbCwgaW50IHIsIGludCB1LCBpbnQgdiwgaWkgdmFsKSB7CglpZiAobCA+IHYgfHwgciA8IHUpIHJldHVybjsgCgoJaWYgKHUgPD0gbCAmJiByIDw9IHYpIHsKCQlzZWdbaWRdID0gYWRkKG11bChzZWdbaWRdLCB2YWwuZmlyc3QpLCBtdWwociAtIGwgKyAxLCB2YWwuc2Vjb25kKSk7CgkJbGF6eVtpZF0uZmlyc3QgPSBtdWwobGF6eVtpZF0uZmlyc3QsIHZhbC5maXJzdCk7CgkJbGF6eVtpZF0uc2Vjb25kID0gYWRkKG11bChsYXp5W2lkXS5zZWNvbmQsIHZhbC5maXJzdCksIHZhbC5zZWNvbmQpOyAKCQlyZXR1cm47ICAKCX0KCglwdXNoKGlkLCBsLCByKTsgICAKCglpbnQgbWlkID0gKGwgKyByKSA+PiAxOyAKCXVwZGF0ZShpZCAqIDIsIGwsIG1pZCwgdSwgdiwgdmFsKTsgCgl1cGRhdGUoaWQgKiAyICsgMSwgbWlkICsgMSwgciwgdSwgdiwgdmFsKTsgCgoJc2VnW2lkXSA9IGFkZChzZWdbaWQgKiAyXSwgc2VnW2lkICogMiArIDFdKTsgCn0KCmludCBnZXQoaW50IGlkLCBpbnQgbCwgaW50IHIsIGludCB1LCBpbnQgdikgewoJaWYgKGwgPiB2IHx8IHIgPCB1KSByZXR1cm4gMDsgCgoJaWYgKHUgPD0gbCAmJiByIDw9IHYpIHJldHVybiBzZWdbaWRdOyAgCgoJcHVzaChpZCwgbCwgcik7ICAKCglpbnQgbWlkID0gKGwgKyByKSA+PiAxOyAgCglyZXR1cm4gYWRkKGdldChpZCAqIDIsIGwsIG1pZCwgdSwgdiksIGdldChpZCAqIDIgKyAxLCBtaWQgKyAxLCByLCB1LCB2KSk7IAp9CgppbnQgbWFpbigpIHsKCWlvczo6c3luY193aXRoX3N0ZGlvKDApOyBjaW4udGllKDApOyAgCQoJY2luID4+IG4gPj4gcTsgCglmb3IgKGludCBpID0gMTsgaSA8PSBuOyBpKyspIGNpbiA+PiBhW2ldOwoKCWJ1aWxkKDEsIDEsIG4pOyAKCWluaXRMYXp5KCk7ICAgCgoJd2hpbGUgKHEtLSkgewoJCWludCB0eXBlLCBsLCByOyAKCQljaW4gPj4gdHlwZSA+PiBsID4+IHI7IAoKCQlpZiAodHlwZSA9PSA0KSB7CgkJCWNvdXQgPDwgZ2V0KDEsIDEsIG4sIGwsIHIpIDw8ICdcbic7IAoJCX0KCQllbHNlIHsKCQkJaW50IHg7IGNpbiA+PiB4OyAgCgoJCQlpaSB2YWw7IAoJCQlpZiAodHlwZSA9PSAxKSB2YWwgPSB7MSwgeH07IAoJCQlpZiAodHlwZSA9PSAyKSB2YWwgPSB7eCwgMH07ICAKCQkJaWYgKHR5cGUgPT0gMykgdmFsID0gezAsIHh9OyAKCgkJCXVwZGF0ZSgxLCAxLCBuLCBsLCByLCB2YWwpOyAgCgkJfQoJfQp9