#include <iostream>
#include <sstream>
#include <vector>
#include <algorithm>
#include <iterator>
#include <cstdint>
using namespace std;
struct TagHeader {
uint16_t tag_code;
uint32_t tag_length;
};
static const int bits_per_byte = 8;
template<class int_type, class iterator_type>
static int_type parse_int_le(iterator_type& i, iterator_type eof = iterator_type {}) {
std::array<unsigned char, sizeof(int_type)> bytes;
std::copy_n(i, sizeof(bytes), std::begin(bytes));
i++;
int_type value = 0;
for(int byte_offset = sizeof(int_type) - 1; byte_offset >= 0; byte_offset--) {
value |= static_cast<int_type>(bytes[byte_offset]) << byte_offset * bits_per_byte;
}
return value;
}
template<class iterator_type>
static TagHeader parse_tag_header(iterator_type& i, iterator_type eof) {
TagHeader h;
auto code_and_length = parse_int_le<uint16_t>(i, eof);
std::cout << "code_and_length = " << code_and_length << "\n";
h.tag_code = (code_and_length & (0xffff << 6)) >> 6; // top 10 bits are tag type
h.tag_length = code_and_length & (0xffff >> 10); // lower 6 bits are length
if(h.tag_length >= 63) {
h.tag_length = parse_int_le<uint32_t>(i, eof);
}
return h;
}
int main() {
{
stringstream sstr;
sstr << "\x8b\x15";
istreambuf_iterator<char> i(sstr);
istreambuf_iterator<char> eof;
auto th = parse_tag_header(i, eof);
std::cout << th.tag_length << "\n";
}
std::cout << "\n";
{
stringstream sstr;
sstr << "\x8b\x15";
istreambuf_iterator<char> i(sstr);
istreambuf_iterator<char> eof;
std::vector<char> tag_data(2);
std::copy_n(i, 2, tag_data.begin());
i++;
auto tag_i = tag_data.begin();
auto tag_eof = tag_data.end();
auto th = parse_tag_header(tag_i, tag_eof);
std::cout << th.tag_length << "\n";
}
return 0;
}
I2luY2x1ZGUgPGlvc3RyZWFtPgojaW5jbHVkZSA8c3N0cmVhbT4KI2luY2x1ZGUgPHZlY3Rvcj4KI2luY2x1ZGUgPGFsZ29yaXRobT4KI2luY2x1ZGUgPGl0ZXJhdG9yPgojaW5jbHVkZSA8Y3N0ZGludD4KCnVzaW5nIG5hbWVzcGFjZSBzdGQ7CgpzdHJ1Y3QgVGFnSGVhZGVyIHsKICAgIHVpbnQxNl90IHRhZ19jb2RlOwogICAgdWludDMyX3QgdGFnX2xlbmd0aDsKfTsKCnN0YXRpYyBjb25zdCBpbnQgYml0c19wZXJfYnl0ZSA9IDg7Cgp0ZW1wbGF0ZTxjbGFzcyBpbnRfdHlwZSwgY2xhc3MgaXRlcmF0b3JfdHlwZT4Kc3RhdGljIGludF90eXBlIHBhcnNlX2ludF9sZShpdGVyYXRvcl90eXBlJiBpLCBpdGVyYXRvcl90eXBlIGVvZiA9IGl0ZXJhdG9yX3R5cGUge30pIHsKICAgIHN0ZDo6YXJyYXk8dW5zaWduZWQgY2hhciwgc2l6ZW9mKGludF90eXBlKT4gYnl0ZXM7CiAgICBzdGQ6OmNvcHlfbihpLCBzaXplb2YoYnl0ZXMpLCBzdGQ6OmJlZ2luKGJ5dGVzKSk7CiAgICBpKys7CiAgICBpbnRfdHlwZSB2YWx1ZSA9IDA7CiAgICBmb3IoaW50IGJ5dGVfb2Zmc2V0ID0gc2l6ZW9mKGludF90eXBlKSAtIDE7IGJ5dGVfb2Zmc2V0ID49IDA7IGJ5dGVfb2Zmc2V0LS0pIHsKICAgICAgICB2YWx1ZSB8PSBzdGF0aWNfY2FzdDxpbnRfdHlwZT4oYnl0ZXNbYnl0ZV9vZmZzZXRdKSA8PCBieXRlX29mZnNldCAqIGJpdHNfcGVyX2J5dGU7CiAgICB9CiAgICByZXR1cm4gdmFsdWU7Cn0KCnRlbXBsYXRlPGNsYXNzIGl0ZXJhdG9yX3R5cGU+CnN0YXRpYyBUYWdIZWFkZXIgcGFyc2VfdGFnX2hlYWRlcihpdGVyYXRvcl90eXBlJiBpLCBpdGVyYXRvcl90eXBlIGVvZikgewogICAgVGFnSGVhZGVyIGg7CiAgICBhdXRvIGNvZGVfYW5kX2xlbmd0aCA9IHBhcnNlX2ludF9sZTx1aW50MTZfdD4oaSwgZW9mKTsKICAgIHN0ZDo6Y291dCA8PCAiY29kZV9hbmRfbGVuZ3RoID0gIiA8PCBjb2RlX2FuZF9sZW5ndGggPDwgIlxuIjsKICAgIGgudGFnX2NvZGUgPSAoY29kZV9hbmRfbGVuZ3RoICYgKDB4ZmZmZiA8PCA2KSkgPj4gNjsgLy8gdG9wIDEwIGJpdHMgYXJlIHRhZyB0eXBlCiAgICBoLnRhZ19sZW5ndGggPSBjb2RlX2FuZF9sZW5ndGggJiAoMHhmZmZmID4+IDEwKTsgLy8gbG93ZXIgNiBiaXRzIGFyZSBsZW5ndGgKICAgIGlmKGgudGFnX2xlbmd0aCA+PSA2MykgewogICAgICAgIGgudGFnX2xlbmd0aCA9IHBhcnNlX2ludF9sZTx1aW50MzJfdD4oaSwgZW9mKTsKICAgIH0KICAgIHJldHVybiBoOwp9CmludCBtYWluKCkgewoJewoJCXN0cmluZ3N0cmVhbSBzc3RyOwoJCXNzdHIgPDwgIlx4OGJceDE1IjsKCQlpc3RyZWFtYnVmX2l0ZXJhdG9yPGNoYXI+IGkoc3N0cik7CgkJaXN0cmVhbWJ1Zl9pdGVyYXRvcjxjaGFyPiBlb2Y7CgkJCgkJYXV0byB0aCA9IHBhcnNlX3RhZ19oZWFkZXIoaSwgZW9mKTsKCQlzdGQ6OmNvdXQgPDwgdGgudGFnX2xlbmd0aCA8PCAiXG4iOwoJfQoJc3RkOjpjb3V0IDw8ICJcbiI7Cgl7CgkJc3RyaW5nc3RyZWFtIHNzdHI7CgkJc3N0ciA8PCAiXHg4Ylx4MTUiOwoJCWlzdHJlYW1idWZfaXRlcmF0b3I8Y2hhcj4gaShzc3RyKTsKCQlpc3RyZWFtYnVmX2l0ZXJhdG9yPGNoYXI+IGVvZjsKCQkKCQlzdGQ6OnZlY3RvcjxjaGFyPiB0YWdfZGF0YSgyKTsKCQlzdGQ6OmNvcHlfbihpLCAyLCB0YWdfZGF0YS5iZWdpbigpKTsKCQlpKys7CgkJCgkJYXV0byB0YWdfaSA9IHRhZ19kYXRhLmJlZ2luKCk7CgkJYXV0byB0YWdfZW9mID0gdGFnX2RhdGEuZW5kKCk7CgkJCgkJYXV0byB0aCA9IHBhcnNlX3RhZ19oZWFkZXIodGFnX2ksIHRhZ19lb2YpOwoJCXN0ZDo6Y291dCA8PCB0aC50YWdfbGVuZ3RoIDw8ICJcbiI7Cgl9CglyZXR1cm4gMDsKfQ==