Files
goirsdk/variables.go
T
esilva e1a478d9b5 First commit
This project shall offer a iRacing telemetry parser with as little
dependencies as possible
2024-10-26 22:56:42 +01:00

168 lines
3.8 KiB
Go

package main
import (
"fmt"
)
const (
VarSize = 144
IRSDK_char = 0
IRSDK_bool = 1
IRSDK_int = 2
IRSDK_bitField = 3
IRSDK_float = 4
IRSDK_double = 5
)
// I think I can make an interface if IRSDK types with available types and
// that they need a parser (reads and type coerces I guess)
var (
VarTypes = map[int]VarType{
IRSDK_char: {1, "irsdk_char"},
IRSDK_bool: {1, "irsdk_bool"},
IRSDK_int: {4, "irsdk_int"},
IRSDK_bitField: {4, "irsdk_bitField"},
IRSDK_float: {4, "irsdk_float"},
IRSDK_double: {8, "irsdk_double"},
}
)
type VarType struct {
Size int // Size is the var type size in bytes
Name string // Name is the irsdk var name
}
type IBTVar struct {
Type int32
Offset int32
Count int32
CountAsTime bool
Padding [0]byte
Name [32]byte
Description [64]byte
Unit [32]byte
}
type Var struct {
Type int32
Offset int32
Count int32
CountAsTime bool
Name string
Description string
Unit string
// TODO
// Create an interface for this value
// Represent the IRSDK var types with a struct each that implements the Parse
// method or something like that I guess
Value interface{}
}
func (v *IBTVar) ToString() string {
return fmt.Sprintf(
"Type: %5d (0x%08x)\n"+
"Offset: %5d (0x%08x)\n"+
"Count: %5d (0x%08x)\n"+
"CountAsTime: %5t\n"+
"Name: %s\n"+
"Description: %s\n"+
"Unit: %s",
v.Type, v.Type, v.Offset, v.Offset, v.Count, v.Count,
v.CountAsTime, v.Name, v.Description, v.Unit,
)
}
type varBuffer struct {
tickCount int
bufOffset int
}
type TelemetryVars struct {
LastVersion int
Vars map[string]Var
}
// func findLatestBuffer(i *IBT) varBuffer {
// var vb varBuffer
// foundTickCount := 0
// for k := 0; k < int(i.Headers.NumBuf); k++ {
// rbuf := make([]byte, 16)
// _, err := i.File.ReadAt(rbuf, int64(48+k*16))
// if err != nil {
// log.Fatal(err)
// }
//
// currentVb := varBuffer{
// int(binary.LittleEndian.Uint32(rbuf[0:4])),
// int(binary.LittleEndian.Uint32(rbuf[4:8])),
// }
//
// if foundTickCount < currentVb.tickCount {
// foundTickCount = currentVb.tickCount
// vb = currentVb
// }
// }
//
// return vb
// }
// func (i *IBT) parseVariableHeaders(offset int32) (int32, error) {
// if i.Vars.Vars == nil {
// i.Vars.Vars = make(map[string]*Variable, i.Headers.NumVars)
// }
//
// var size int32 = 0
// for k := range i.Headers.NumVars {
// start := k * VarSize + offset
// size += start
//
// buf := make([]byte, VarSize)
// _, err := i.File.ReadAt(buf, int64(start))
// if err != nil {
// return 0, err
// }
//
// newVar, err := parseVariable(buf)
// i.Vars.Vars[string(newVar.Name[:])] = newVar
// }
//
// return size, nil
// }
// This function will read a single variable
// func parseVariable(buf []byte) (*Variable, error) {
// if len(buf)%VarSize != 0 {
// return nil, fmt.Errorf("buffer must be multiple of size: %d", VarSize)
// }
//
// dst := Variable{}
// err := binary.Read(bytes.NewBuffer(buf[:]), binary.LittleEndian, &dst)
// if err != nil {
// return nil, err
// }
//
// return &dst, nil
// }
// this function will read the variables
// func parseVariables(i *IBT) error {
// i.parseVariableHeaders(0)
// vb := findLatestBuffer(i)
// fmt.Printf("%+v\n", vb)
// if i.Vars.LastVersion < vb.tickCount {
// // Then we have new data
// i.Vars.LastVersion = vb.tickCount
// i.LastValidData = time.Now().Unix()
// for _, v := range i.Vars.Vars {
// // fmt.Printf("%s\n", v.ToString())
// rbuf := make([]byte, VarTypes[int(v.Type)].Size)
// _, err := i.File.ReadAt(rbuf, int64(vb.bufOffset + int(v.Offset)))
// if err != nil {
// log.Fatalf("Reading values: %v\n", err)
// }
// }
// }
//
// return nil
// }