Files
qb/atree/atree.go

225 lines
4.5 KiB
Go
Raw Normal View History

2026-02-10 14:02:11 +00:00
package atree
import (
2026-06-15 05:32:15 +03:00
"errors"
2026-02-10 14:02:11 +00:00
"os"
"sync"
)
const (
2026-06-15 05:32:15 +03:00
filePerm = 0666
2026-02-10 14:02:11 +00:00
)
2026-06-15 05:32:15 +03:00
type PeriodsWriter interface {
Feed(uint32, float64)
FeedNoSend(uint32, float64)
Close() error
}
type WorkerMeasureConsumer interface {
FeedNoSend(uint32, float64)
}
type AtreeMeasureConsumer interface {
Feed(uint32, float64)
}
//
2026-02-10 14:02:11 +00:00
type _page struct {
PageNo uint32
Buf []byte
ReferenceCount int
}
type Atree struct {
2026-06-15 05:32:15 +03:00
indexFile *os.File
dataFile *os.File
mutex sync.Mutex
pages map[uint32]*_page
pageWaits map[uint32][]chan readResult
pagesToRead []uint32
readSignalCh chan struct{}
2026-02-10 14:02:11 +00:00
}
type Options struct {
2026-06-15 05:32:15 +03:00
IndexFile *os.File
DataFile *os.File
2026-02-10 14:02:11 +00:00
}
func New(opt Options) (*Atree, error) {
2026-06-15 05:32:15 +03:00
if opt.IndexFile == nil {
return nil, errors.New("IndexFile option is required")
}
if opt.DataFile == nil {
return nil, errors.New("DataFile option is required")
}
s := &Atree{
indexFile: opt.IndexFile,
dataFile: opt.DataFile,
pages: make(map[uint32]*_page),
pageWaits: make(map[uint32][]chan readResult),
readSignalCh: make(chan struct{}, 1),
}
return s, nil
2026-02-10 14:02:11 +00:00
}
func (s *Atree) Run() {
2026-05-10 00:59:47 +00:00
//go s.pageWriter()
2026-02-10 14:02:11 +00:00
go s.pageReader()
}
// FIND
func (s *Atree) findDataPage(rootPageNo uint32, timestamp uint32) (uint32, []byte, error) {
2026-06-10 06:18:45 +03:00
// indexPageNo := rootPageNo
// for {
// buf, err := s.fetchIndexPage(indexPageNo)
// if err != nil {
// return 0, nil, fmt.Errorf("fetchIndexPage(%d): %s", indexPageNo, err)
// }
// foundPageNo := findPageNo(buf, timestamp)
// s.releasePage(indexPageNo)
// // fix
// if buf[isLastLevelIdx] == 1 {
// buf, err := s.fetchDataPage(foundPageNo)
// if err != nil {
// return 0, nil, fmt.Errorf("fetchDataPage(%d): %s", foundPageNo, err)
// }
// return foundPageNo, buf, nil
// }
// // вглубь
// indexPageNo = foundPageNo
// }
return 0, nil, nil
2026-02-10 14:02:11 +00:00
}
2026-05-10 00:59:47 +00:00
type PathLeg struct {
2026-02-10 14:02:11 +00:00
PageNo uint32
Data []byte
}
2026-05-10 00:59:47 +00:00
type PathToDataPage struct {
Legs []PathLeg
2026-02-10 14:02:11 +00:00
LastPageNo uint32
}
2026-05-10 00:59:47 +00:00
func (s *Atree) FindPathToLastPage(rootPageNo uint32) (_ PathToDataPage, err error) {
2026-06-10 06:18:45 +03:00
// var (
// pageNo = rootPageNo
// legs []PathLeg
// )
// for {
// var buf []byte
// buf, err = s.fetchIndexPage(pageNo)
// if err != nil {
// err = fmt.Errorf("FetchIndexPage(%d): %s", pageNo, err)
// return
// }
// legs = append(legs, PathLeg{
// PageNo: pageNo,
// Data: buf,
// // childIdx не нужен
// })
// foundPageNo := getLastPageNo(buf)
// // fix
// if buf[isLastLevelIdx] == 1 {
// return PathToDataPage{
// Legs: legs,
// LastPageNo: foundPageNo,
// }, nil
// }
// // вглубь
// pageNo = foundPageNo
// }
return
2026-02-10 14:02:11 +00:00
}
// DELETE
type Level struct {
PageNo uint32
PageData []byte
Idx int
ChildQty int
}
2026-05-10 00:59:47 +00:00
func (s *Atree) GetAllPages(rootPageNo uint32) (_ []uint32, err error) {
2026-06-10 06:18:45 +03:00
// var (
// pageNumbers []uint32
// levels []*Level
// )
// buf, err := s.fetchIndexPage(rootPageNo)
// if err != nil {
// return nil, fmt.Errorf("fetchIndexPage(%d): %s", rootPageNo, err)
2026-05-10 00:59:47 +00:00
// }
2026-06-10 06:18:45 +03:00
// pageNumbers = append(pageNumbers, rootPageNo)
// // if buf[isDataPageNumbersIdx] == 1 {
// // pageNumbers := listPageNumbers(buf)
// // dataPages = append(dataPages, pageNumbers...)
// // s.releasePage(rootPageNo)
// // return PageLists{
// // DataPages: dataPages,
// // IndexPages: indexPages,
// // }, nil
// // }
// childQty, _ := bin.GetUint16(buf[indexRecordsQtyIdx:])
// levels = append(levels, &Level{
// PageNo: rootPageNo,
// PageData: buf,
// Idx: 0,
// ChildQty: int(childQty),
// })
// for {
// if len(levels) == 0 {
// return pageNumbers, nil
// }
// lastIdx := len(levels) - 1
// level := levels[lastIdx]
// if level.Idx < level.ChildQty {
// pageNo := getPageNo(level.PageData, level.Idx)
// level.Idx++
// var buf []byte
// buf, err = s.fetchPage(pageNo)
// if err != nil {
// return nil, fmt.Errorf("fetchPage(%d): %s", pageNo, err)
// }
// pageNumbers = append(pageNumbers, pageNo)
// if buf[pageTypeIdx] == PageTypeData {
// //pageNumbers := listPageNumbers(buf)
// //dataPages = append(dataPages, pageNumbers...)
// s.releasePage(pageNo)
// } else {
// childQty, _ = bin.GetUint16(buf[indexRecordsQtyIdx:])
// levels = append(levels, &Level{
// PageNo: pageNo,
// PageData: buf,
// Idx: 0,
// ChildQty: int(childQty),
// })
// }
// } else {
// s.releasePage(level.PageNo)
// levels = levels[:lastIdx]
// }
// }
return
2026-02-10 14:02:11 +00:00
}