Skip to content

Commit

Permalink
wip serde
Browse files Browse the repository at this point in the history
  • Loading branch information
lunfardo314 committed May 13, 2024
1 parent 77a4863 commit ff0f679
Show file tree
Hide file tree
Showing 2 changed files with 72 additions and 16 deletions.
65 changes: 54 additions & 11 deletions library.go
Original file line number Diff line number Diff line change
Expand Up @@ -136,10 +136,24 @@ func (lib *Library) PrintLibraryStats() {

// embedShort embeds short-callable function into the library
func (lib *Library) embedShort(sym string, requiredNumPar int, evalFun EvalFunction) byte {
Assert(lib.numEmbeddedShort < MaxNumEmbeddedShort, "too many embedded short functions")
Assert(!lib.existsFunction(sym), "EasyFL: !existsFunction(sym)")
Assert(requiredNumPar <= 15, "EasyFL: can't be more than 15 parameters")
Assert(requiredNumPar >= 0, "EasyFL: short embedded vararg functions are not allowed")
ret, err := lib.embedShortErr(sym, requiredNumPar, evalFun)
AssertNoError(err)
return ret
}

func (lib *Library) embedShortErr(sym string, requiredNumPar int, evalFun EvalFunction) (byte, error) {
if lib.numEmbeddedShort >= MaxNumEmbeddedShort {
return 0, fmt.Errorf("EasyFL: too many embedded short functions")
}
if lib.existsFunction(sym) {
return 0, fmt.Errorf("EasyFL: repeating function '%s'", sym)
}
if requiredNumPar > 15 {
return 0, fmt.Errorf("EasyFL: can't be more than 15 parameters")
}
if requiredNumPar < 0 {
return 0, fmt.Errorf("EasyFL: short embedded vararg functions are not allowed")
}
if traceYN {
evalFun = wrapWithTracing(evalFun, sym)
}
Expand All @@ -162,13 +176,26 @@ func (lib *Library) embedShort(sym string, requiredNumPar int, evalFun EvalFunct
AssertNoError(err)
Assert(len(codeBytes) == 1, "expected short code")
}
return byte(dscr.funCode)
return byte(dscr.funCode), nil
}

func (lib *Library) embedLong(sym string, requiredNumPar int, evalFun EvalFunction) uint16 {
Assert(lib.numEmbeddedLong < MaxNumEmbeddedLong, "too many embedded long functions")
Assert(!lib.existsFunction(sym), "!existsFunction(sym)")
Assert(requiredNumPar <= 15, "can't be more than 15 parameters")
ret, err := lib.embedLongErr(sym, requiredNumPar, evalFun)
AssertNoError(err)
return ret
}

func (lib *Library) embedLongErr(sym string, requiredNumPar int, evalFun EvalFunction) (uint16, error) {
if lib.numEmbeddedLong > MaxNumEmbeddedLong {
return 0, fmt.Errorf("EasyFL: too many embedded long functions")
}
if lib.existsFunction(sym) {
return 0, fmt.Errorf("EasyFL: repeating function '%s'", sym)
}
if requiredNumPar > 15 {
return 0, fmt.Errorf("EasyFL: can't be more than 15 parameters")
}

if traceYN {
evalFun = wrapWithTracing(evalFun, sym)
}
Expand All @@ -191,19 +218,35 @@ func (lib *Library) embedLong(sym string, requiredNumPar int, evalFun EvalFuncti
AssertNoError(err)
Assert(len(codeBytes) == 2, "expected long code")
}
return dscr.funCode
return dscr.funCode, nil
}

func (lib *Library) EmbedShort(funList ...*EmbedFunction) {
err := lib.EmbedShortErr(funList...)
AssertNoError(err)
}

func (lib *Library) EmbedShortErr(funList ...*EmbedFunction) (err error) {
for _, fun := range funList {
lib.embedShort(fun.Sym, fun.RequiredNumPar, fun.EvalFun)
if _, err = lib.embedShortErr(fun.Sym, fun.RequiredNumPar, fun.EvalFun); err != nil {
return
}
}
return
}

func (lib *Library) EmbedLong(funList ...*EmbedFunction) {
err := lib.EmbedLongErr(funList...)
AssertNoError(err)
}

func (lib *Library) EmbedLongErr(funList ...*EmbedFunction) (err error) {
for _, fun := range funList {
lib.embedLong(fun.Sym, fun.RequiredNumPar, fun.EvalFun)
if _, err = lib.embedLongErr(fun.Sym, fun.RequiredNumPar, fun.EvalFun); err != nil {
return
}
}
return
}

func (lib *Library) Extend(funList ...*ExtendFunction) {
Expand Down
23 changes: 18 additions & 5 deletions serde.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,14 @@ func (lib *Library) LibraryHash() [32]byte {
func (lib *Library) libraryBytes() []byte {
var buf bytes.Buffer

var uint16Bin [2]byte
binary.BigEndian.PutUint16(uint16Bin[:], lib.numEmbeddedShort)
buf.Write(uint16Bin[:])
binary.BigEndian.PutUint16(uint16Bin[:], lib.numEmbeddedLong)
buf.Write(uint16Bin[:])
binary.BigEndian.PutUint16(uint16Bin[:], lib.numExtended)
buf.Write(uint16Bin[:])

funCodes := make([]uint16, 0, len(lib.funByFunCode))
for funCode := range lib.funByFunCode {
funCodes = append(funCodes, funCode)
Expand All @@ -31,6 +39,11 @@ func (lib *Library) libraryBytes() []byte {
return buf.Bytes()
}

func (lib *Library) fromBytes(data []byte) (err error) {
// TODO
return nil
}

func (fd *funDescriptor) write(w io.Writer) {
var uint16Bin [2]byte
// fun code
Expand Down Expand Up @@ -81,12 +94,12 @@ func (fd *funDescriptor) read(r io.Reader, lib *Library) error {
}
} else {
// embedded
var fi *funInfo
if fi, err = lib.functionByName(fd.sym); err != nil {
return err
var sym string
if fd.evalFun, fd.requiredNumParams, sym, err = lib.functionByCode(fd.funCode); err != nil {
return fmt.Errorf("can't find embedded function '%s' with code %d: %w", fd.sym, fd.funCode, err)
}
if fd.evalFun, fd.requiredNumParams, _, err = lib.functionByCode(fi.FunCode); err != nil {
return fmt.Errorf("can't find embedded function '%s' with code %d: %w", fi.Sym, fi.FunCode, err)
if sym != fd.sym {
return fmt.Errorf("embedded function with code %d: expected name '%s', got '%s'", fd.funCode, fd.sym, sym)
}
}
return nil
Expand Down

0 comments on commit ff0f679

Please sign in to comment.