void SetU32::appendMerge()

in glean/rts/ownership/setu32.cpp [310:384]


void SetU32::appendMerge(SetU32::Block left, SetU32::Block right) {
  struct Local {
    static void mergeSparse(
        SetU32& set,
        uint32_t id,
        std::vector<uint8_t>::const_iterator ls,
        uint8_t ln,
        std::vector<uint8_t>::const_iterator rs,
        uint8_t rn) {
      uint8_t n = 0;
      while (ln != 0 && rn != 0 && fitsSparse(n,1)) {
        const auto l = *ls;
        const auto r = *rs;
        set.sparse.push_back(l <= r ? l : r);
        ++n;
        if (l <= r) {
          ++ls;
          --ln;
        }
        if (r <= l) {
          ++rs;
          --rn;
        }
      }
      if (fitsSparse(n, ln+rn)) {
        set.hdrs.push_back(Hdr::sparse(id, n+ln+rn));
        set.sparse.insert(set.sparse.end(), ls, ls+ln);
        set.sparse.insert(set.sparse.end(), rs, rs+rn);
      } else {
        const auto dense = Bits256(&*(set.sparse.end()-n),n).with(&*ls,ln).with(&*rs,rn);
        set.hdrs.push_back(Hdr::dense(id));
        set.dense.push_back(dense);
        set.sparse.resize(set.sparse.size()-n);
      }
    }
  };

  switch(left.hdr.type()) {
    case SetU32::Hdr::Sparse:
      switch(right.hdr.type()) {
        case SetU32::Hdr::Sparse:
          Local::mergeSparse(*this, left.hdr.id(), left.sparse, left.hdr.sparseLen(), right.sparse, right.hdr.sparseLen());
          break;

        case SetU32::Hdr::Dense:
          append(left.hdr.id(), right.dense->with(&*left.sparse, left.hdr.sparseLen()));
          break;

        case SetU32::Hdr::Full:
          hdrs.push_back(right.hdr);
          break;
      }
      break;

    case SetU32::Hdr::Dense:
      switch (right.hdr.type()) {
        case SetU32::Hdr::Sparse:
          append(left.hdr.id(), left.dense->with(&*right.sparse, right.hdr.sparseLen()));
          break;

        case SetU32::Hdr::Dense:
          append(left.hdr.id(), *left.dense | *right.dense);
          break;

        case SetU32::Hdr::Full:
          hdrs.push_back(right.hdr);
          break;
      }
      break;

    case SetU32::Hdr::Full:
      hdrs.push_back(left.hdr);
      break;
  }
}