package models import "encoding/binary" import "testify/assert" const HEADER = 4 const BTREE_PAGE_SIZE = 4096 const BTREE_MAX_KEY_SIZE = 1000 const BTREE_MAX_VAL_SIZE = 1000 type BNode []byte type BTree struct { root uint64 get func(uint64) []byte new func([]byte) uint64 del func(uint64) } func init() { noode1max := HEADER + 8 + 2 + 4 + BTREE_MAX_KEY_SIZE + BTREE_MAX_VAL_SIZE assert(noode1max <= BTREE_PAGE_SIZE) } func (node BNode) btype() uint16 { return binary.LittleEndian.Uint16(node[0:2]) } func (node BNode) nkeys() uint16 { return binary.LittleEndian.Uint16(node[2:4]) } func (node BNode) setHeader(btype uint16, nkeys uint16) { binary.LittleEndian.PutUint16(node[0:2], btype) binary.LittleEndian.PutUint16(node[2:4], nkeys) } func (node BNode) getPtr(ids uint16) uint64 { assert(ids < node.nkeys()) pos := HEADER + 8*ids return binary.LittleEndian.Uint64(node[pos:]) } func (node BNode) setPtr(idx uint16, val uint64) { assert(idx <= node.nkeys()) pos := HEADER + 8*idx binary.LittleEndian.PutUint64(node[pos:], val) } func (node BNode) getOffset(idx uint16) uint16 { if (idx == 0) { return 0 } pos := HEADER + 8*node.nkeys() + 2*(idx - 1) return binary.LittleEndian.Uint16(node[pos:]) } func (node BNode) kvPos(idx uint16) (uint16) { assert(idx < node.nkeys()) return 4 + 8*node.nkeys() + 2*node.nkeys() + node.getOffset(idx) } func(node BNode) getKey(idx uint16) []byte { assert(idx < node.nkeys()) pos := node.kvPos(idx) klen := binary.LittleEndian.Uint16(node[pos:]) vlen := binary.LittleEndian.Uint16(node[pos+2:]) return node[pos+4+klen:][:vlen] }