#include <bits/stdc++.h>
using namespace std;
const long long maxN = 100000;
long long a[maxN];
struct segment {
  long long ans = 0, len = 1;
  vector<pair<long long, long long>> suf, pre;
};
segment st[4 * maxN];
long long n, m, x;
segment merge(segment a, segment b) {
  if (a.ans == -1) {
    return b;
  }
  if (b.ans == -1) {
    return a;
  }
  segment ans;
  ans.len = a.len + b.len;
  ans.pre = a.pre;
  ans.suf = b.suf;
  for (auto &i : ans.suf) {
    i.second += a.len;
  }
  long long Or = ans.pre.back().first;
  for (auto i : b.pre) {
    if ((Or | i.first) != Or) {
      Or |= i.first;
      ans.pre.emplace_back(Or, i.second + a.len);
    }
  }
  reverse(a.suf.begin(), a.suf.end());
  reverse(ans.suf.begin(), ans.suf.end());
  Or = ans.suf.back().first;
  for (auto i : a.suf) {
    if ((Or | i.first) != Or) {
      Or |= i.first;
      ans.suf.emplace_back(Or, i.second);
    }
  }
  reverse(a.suf.begin(), a.suf.end());
  reverse(ans.suf.begin(), ans.suf.end());
  ans.ans = a.ans + b.ans;
  auto it = b.pre.begin();
  long long presuf = -1;
  for (auto i : a.suf) {
    while ((i.first | (it->first)) < x) {
      it++;
      if (it == b.pre.end()) {
        break;
      }
    }
    if (it == b.pre.end()) {
      break;
    }
    ans.ans += (i.second - presuf) * (b.len - it->second);
    presuf = i.second;
  }
  return ans;
}
void build(long long L = 0, long long R = n, long long i = 1) {
  if (R - L == 1) {
    st[i].ans = a[L] >= x;
    st[i].suf = {{a[L], 0}};
    st[i].pre = {{a[L], 0}};
    return;
  }
  long long mid = (L + R) / 2;
  build(L, mid, 2 * i);
  build(mid, R, 2 * i + 1);
  st[i] = merge(st[2 * i], st[2 * i + 1]);
}
void replace(long long j, long long y, long long L = 0, long long R = n,
             long long i = 1) {
  if (R - L == 1) {
    st[i].ans = a[L] >= x;
    st[i].suf = {{a[L], 0}};
    st[i].pre = {{a[L], 0}};
    return;
  }
  long long mid = (L + R) / 2;
  if (j < mid) {
    replace(j, y, L, mid, 2 * i);
  } else {
    replace(j, y, mid, R, 2 * i + 1);
  }
  st[i] = merge(st[2 * i], st[2 * i + 1]);
}
segment find(long long l, long long r, long long L = 0, long long R = n,
             long long i = 1) {
  if (l <= L and R <= r) {
    return st[i];
  }
  if (L >= r or R <= l) {
    segment tmp;
    tmp.ans = -1;
    return tmp;
  }
  long long mid = (L + R) / 2;
  return merge(find(l, r, L, mid, 2 * i), find(l, r, mid, R, 2 * i + 1));
}
int32_t main() {
  long long t, l, r, j, y;
  cin >> n >> m >> x;
  for (long long i = 0; i < n; i++) {
    cin >> a[i];
  }
  build();
  for (long long i = 0; i < m; i++) {
    cin >> t;
    if (t == 1) {
      cin >> j >> y;
      a[j - 1] = y;
      replace(j - 1, y);
    }
    if (t == 2) {
      cin >> l >> r;
      cout << find(l - 1, r).ans << "\n";
    }
  }
}
