Anonymous avatar Anonymous committed 31309e7

working (and faster) groot-ls

Comments (0)

Files changed (12)

cmd/groot-ls/main.go

 import (
 	"flag"
 	"fmt"
+	"log"
 	"os"
+	"runtime/pprof"
 	"strings"
 
 	"bitbucket.org/binet/go-root/pkg/groot"
 )
 
 var fname = flag.String("f", "ntuple.root", "ROOT file to inspect")
+var cpuprofile = flag.String("cpuprofile", "cpu.prof", "write cpu profile to file")
 
 func normpath(path []string) string {
 	name := strings.Join(path, "/")
 		if i+1 >= nkeys {
 			str = "`--"
 		}
-		fmt.Printf("%s%s %s title='%s' type=%s\n",
-			indent, str, k.Name(), k.Title(), k.Class())
-		if v, ok := k.Value().(*groot.Directory); ok {
+		switch v := k.Value().(type) {
+		default:
+			fmt.Printf("%s%s %s title='%s' type=%s\n",
+				indent, str, k.Name(), k.Title(), k.Class())
+			
+		case *groot.Directory:
+			fmt.Printf("%s%s %s title='%s' type=%s\n",
+				indent, str, 
+				k.Name(), k.Title(), k.Class())
 			path := append(path, k.Name())
 			inspect(v, path, indent+"    ")
+
+		case *groot.Tree:
+			fmt.Printf("%s%s %s title='%s' entries=%v nbranches=%v type=%s\n",
+				indent, str, 
+				k.Name(), k.Title(), v.Entries(), len(v.Branches()), k.Class())
 		}
 	}
 }
 	fmt.Printf(":: groot-ls ::\n")
 	flag.Parse()
 
+	if *cpuprofile != "" {
+        f, err := os.Create(*cpuprofile)
+        if err != nil {
+            log.Fatal(err)
+        }
+        pprof.StartCPUProfile(f)
+        defer pprof.StopCPUProfile()
+    }
+
 	f, err := groot.NewFileReader(*fname)
 	if err != nil {
 		fmt.Printf("**error**: %v\n", err)

pkg/groot/base_leaf.go

 	spos := b.Pos()
 
 	vers, pos, bcnt := b.read_version()
-	dprintf("baseleaf-vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
+	printf("baseleaf-vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
 	base.name, base.title = b.read_tnamed()
-	dprintf("baseleaf-name='%v' title='%v'\n", base.name, base.title)
+	printf("baseleaf-name='%v' title='%v'\n", base.name, base.title)
 	base.length = b.ntou4()
-	dprintf("baseleaf-length=%v\n", base.length)
+	printf("baseleaf-length=%v\n", base.length)
 	b.ntoi4() // fLengthType
 	b.ntoi4() // fOffset
 	b.ntobyte() // fIsRange
 	b.ntobyte() // fIsUnsigned
 
 	obj := b.read_object()
-	dprintf("baseleaf-nobjs: %v\n", obj)
+	printf("baseleaf-nobjs: %v\n", obj)
 	if obj != nil {
 		base.leaf_count = obj.(ibaseLeaf).toBaseLeaf()
 	}

pkg/groot/basket.go

 	}
 
 	vers, pos, bcnt := b.read_version()
-	dprintf("vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
+	printf("basket-vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
 	bufsz := b.ntou4()
 	basket.nev_bufsz = b.ntou4()
 	basket.nev = b.ntou4()
 		err = fmt.Errorf("groot.basket.ROOTDecode: bad flag (=%v)",
 			int(flag))
 	}
+	//FIXME: incomplete!! see basket basket::stream
 	return
 }
 

pkg/groot/branch.go

 	"reflect"
 )
 
+type ibranch interface {
+	toBranch() *Branch
+}
+
 type Branch struct {
 	name  string
 	title string
 	basketSeek  []int64 // addresses of baskets on file
 }
 
+func (branch *Branch) toBranch() *Branch {
+	return branch
+}
+
 func (branch *Branch) Class() Class {
 	panic("not implemented")
 }
 func (branch *Branch) ROOTDecode(b *Buffer) (err error) {
 	spos := b.Pos()
 	vers, pos, bcnt := b.read_version()
-	dprintf("vers=%v spos=%v pos=%v bcnt=%v\n", vers, spos, pos, bcnt)
+	printf("[branch] vers=%v spos=%v pos=%v bcnt=%v\n", vers, spos, pos, bcnt)
 	branch.name, branch.title = b.read_tnamed()
-	dprintf("name='%v' title='%v'\n", branch.name, branch.title)
-	dprintf("spos=%v\n", b.Pos())
+	printf("name='%v' title='%v'\n", branch.name, branch.title)
 
 	maxbaskets := uint32(0)
 	splitlvl := int32(0)
 		b.ntou8() // tot_bytes
 		b.ntou8() // zip_bytes
 	}
-	dprintf("::branch::stream : [%s] split-lvl= %v\n", branch.name, splitlvl)
+	printf("::branch::stream : [%s] split-lvl= %v\n", branch.name, splitlvl)
 
-	dprintf("::branch::stream : branches : begin\n")
+	printf("::branch::stream : branches : begin\n")
 	branches := b.read_obj_array()
-	dprintf("::branch::stream : branches : end\n")
-	dprintf("sub-branches: %v\n", len(branches))
+	printf("::branch::stream : branches : end\n")
+	printf("sub-branches: %v\n", len(branches))
 
-	dprintf("::branch::stream : leaves : begin\n")
+	printf("::branch::stream : leaves : begin\n")
 	leaves := b.read_obj_array()
-	dprintf("::branch::stream : leaves : end\n")
-	dprintf("sub-leaves: %v\n", len(leaves))
+	printf("::branch::stream : leaves : end\n")
+	printf("sub-leaves: %v\n", len(leaves))
 
-	dprintf("::branch::stream : streamed_baskets : begin\n")
+	printf("::branch::stream : streamed_baskets : begin\n")
 	baskets := b.read_obj_array()
-	dprintf("::branch::stream : streamed_baskets : end\n")
-	dprintf("baskets: %v\n", len(baskets))
+	printf("::branch::stream : streamed_baskets : end\n")
+	printf("baskets: %v\n", len(baskets))
 
 	branch.basketEntry = make([]int32, 0, int(maxbaskets))
 	branch.basketBytes = make([]int32, 0, int(maxbaskets))
 
 	if vers > 2 {
 		fname := b.read_tstring()
-		dprintf("fname=%s\n", fname)
+		printf("fname=%s\n", fname)
 	}
-	dprintf("spos=%v\n", b.Pos())
 	b.check_byte_count(pos, bcnt, spos, "TBranch")
 	return
 }

pkg/groot/branch_element.go

 	stype  int // branch streamer type
 }
 
+func (be *BranchElement) toBranch() *Branch {
+	return &be.branch
+}
+
 func (be *BranchElement) Class() Class {
 	panic("not implemented")
 }
 
 	spos := b.Pos()
 	vers, pos, bcnt := b.read_version()
-	dprintf("vers=%v spos=%v pos=%v bcnt=%v\n", vers, spos, pos, bcnt)
+	printf("[branch_element] vers=%v spos=%v pos=%v bcnt=%v\n", 
+		vers, spos, pos, bcnt)
 	err = be.branch.ROOTDecode(b)
 	if err != nil {
 		return err

pkg/groot/buffer.go

 	"bytes"
 	"encoding/binary"
 	"fmt"
+	"reflect"
 	"unsafe"
 )
 
 		data:  data,
 		klen:  klen,
 	}
-	b.buf = bytes.NewBuffer(b.data[:])
+	b.buf = bytes.NewBuffer(b.data)
 	return
 }
 
 }
 
 func (b *Buffer) Len() int {
-	return len(b.Bytes())
+	return b.buf.Len()
 }
 
 func (b *Buffer) Bytes() []byte {
 }
 
 func (b *Buffer) clone() *Buffer {
-	bb, err := NewBuffer(b.data[:], b.order, b.klen)
+	bb, err := NewBuffer(b.data, b.order, b.klen)
 	if err != nil {
 		return nil
 	}
-	bb.read_nbytes(b.Pos())
+	bb.buf.Next(b.Pos())
+	//bb.read_nbytes(b.Pos())
 	return bb
 }
 
 }
 
 func (b *Buffer) read_nbytes(nbytes int) (o []byte) {
+	// o = make([]byte, nbytes)
+	// err := binary.Read(b.buf, b.order, o)
+	// if err != nil {
+	// 	panic(err)
+	// }
+	// return
 	o = make([]byte, nbytes)
-	err := binary.Read(b.buf, b.order, o)
+	_, err := b.buf.Read(o)
 	if err != nil {
 		panic(err)
 	}
 	startbuf := b.clone()
 
 	clsname, bcnt, isref := b.read_class()
-	dprintf(">>[class=%s] [bcnt=%v] [isref=%v]\n", clsname, bcnt, isref)
+	printf(">>[class=%s] [bcnt=%v] [isref=%v]\n", clsname, bcnt, isref)
 	if isref {
 		bb := b.clone()
-		dprintf("obj_offset: [%v] -> [%v] -> [%v]\n",
+		printf("obj_offset: [%v] -> [%v] -> [%v]\n",
 			bcnt, bcnt-kMapOffset, bcnt-kMapOffset-bb.klen)
 		bb.rewind_nbytes(b.Pos() - int(bcnt - kMapOffset - bb.klen))
 		ii := bb.ntou4()
 
 			factory := Factory.Get(clsname)
 			if factory == nil {
-				dprintf("**err** no factory for class [%s]\n", clsname)
-				return
+				dprintf("**err** no factory for class [%s] (registering a dummy one!)\n", clsname)
+				
+
+				f := func() reflect.Value {
+					o := &dummyObject{}
+					return reflect.ValueOf(o)
+				}
+				Factory.db[clsname] = f
+				factory = Factory.Get(clsname)
 			}
 
 			vv := factory()
 				if err != nil {
 					panic(err)
 				} else {
-					dprintf("--decoded[%s]--\n", o.Name())
+					printf("--decoded[%s/%s]--\n", o.Name(), clsname)
 				}
 			} else {
 				dprintf("**err** class [%s] does not satisfy the ROOTStreamer interface\n", clsname)
 
 	//var bufvers = 0
 	i := b.ntou4()
-	dprintf("..first_int: %x (len=%d)\n", i, b.Len()/8)
+	printf("..first_int: %x (len=%d)\n", i, b.Len()/8)
 	if i == kNullTag {
 		/*empty*/
-		dprintf("read_class: first_int is kNullTag\n")
+		printf("read_class: first_int is kNullTag\n")
 	} else if (i & kByteCountMask) != 0 {
 		//bufvers = 1
-		dprintf("read_class: first_int & kByteCountMask\n")
+		printf("read_class: first_int & kByteCountMask\n")
 		clstag := b.read_class_tag()
 		if clstag == "" {
 			panic("groot.Buffer.read_class: empty class tag")
 		}
 		name = clstag
 		bcnt = uint32(int64(i) & ^kByteCountMask)
-		dprintf("read_class: kNewClassTag: read class name='%s' bcnt=%d\n",
+		printf("read_class: kNewClassTag: read class name='%s' bcnt=%d\n",
 			name, bcnt)
 	} else {
-		dprintf("read_class: first_int %x ==> position toward object.\n", i)
+		printf("read_class: first_int %x ==> position toward object.\n", i)
 		bcnt = uint32(i)
 		isref = true
 	}
-	dprintf("--[cls=%s] [bcnt=%v] [isref=%v]\n", name, bcnt, isref)
+	printf("--[cls=%s] [bcnt=%v] [isref=%v]\n", name, bcnt, isref)
 	return
 }
 
 	tag_new_class := tag == kNewClassTag
 	tag_class_mask := (int64(tag) & (^int64(kClassMask))) != 0
 
-	dprintf("--tag:%v %x -> new_class=%v class_mask=%v\n", 
+	printf("--tag:%v %x -> new_class=%v class_mask=%v\n", 
 		tag, tag, 
 		tag_new_class,
 		tag_class_mask)
 
 	if tag_new_class {
 		clstag = b.read_string(80)
-		dprintf("--class+tag: [%v] - kNewClassTag\n", clstag)
+		printf("--class+tag: [%v] - kNewClassTag\n", clstag)
 	} else if tag_class_mask {
 		ref := uint32(int64(tag) & (^int64(kClassMask)))
-		dprintf("--class-tag: [%v] & kClassMask -- ref=%d -- recurse\n", 
+		printf("--class-tag: [%v] & kClassMask -- ref=%d -- recurse\n", 
 			clstag, ref)
 		bb := b.clone()
-		dprintf("cl_offset: [%v] -> [%v] -> [%v]\n",
+		printf("cl_offset: [%v] -> [%v] -> [%v]\n",
 			ref, ref-kMapOffset, ref-kMapOffset-bb.klen)
 		bb.rewind_nbytes(b.Pos() - int(ref - kMapOffset - bb.klen))
 		clstag = bb.read_class_tag()
 	nobjs := int(b.ntoi4())
 	lbound := b.ntoi4()
 
-	dprintf("read_obj_array: vers=%v pos=%v bcnt=%v name='%v' nobjs=%v lbound=%v\n",
+	printf("read_obj_array: vers=%v pos=%v bcnt=%v name='%v' nobjs=%v lbound=%v\n",
 		vers, pos, bcnt, name, nobjs, lbound)
 
-	elmts = make([]Object, nobjs)
+	elmts = make([]Object, 0, nobjs)
 	for i := 0; i < nobjs; i++ {
-		dprintf("read_obj_array: %d/%d...\n", i, nobjs)
+		printf("read_obj_array: %d/%d...\n", i, nobjs)
 		obj := b.read_object()
-		dprintf("read_obj_array: %d/%d...[done]\n", i, nobjs)
-		elmts[i] = obj
+		printf("read_obj_array: %d/%d...[done]\n", i, nobjs)
+		elmts = append(elmts, obj)
 	}
 
 	b.check_byte_count(pos, bcnt, spos, "TObjArray")
 		err := fmt.Errorf(
 			"buffer.check_count: object of class [%s] read too few bytes (%d missing)",
 			cls, lenbuf-diff)
-		fmt.Printf("**error** %s\n", err.Error())
+		printf("**error** %s\n", err.Error())
 		//panic(err)
 
-		dprintf("-->pos= %v\n", b.Pos())
 		b.read_nbytes(int(lenbuf-diff))
-		dprintf("-->pos= %v\n", b.Pos())
 		return true
 	}
 	if diff > lenbuf {
 		err := fmt.Errorf(
 			"buffer.check_count: object of class [%s] read too many bytes (%d in excess)",
 			cls, diff-lenbuf)
-		fmt.Printf("**error** %s\n", err.Error())
+		printf("**error** %s\n", err.Error())
 
 		//panic(err)
-		dprintf("-->pos= %v\n", b.Pos())
 		b.rewind_nbytes(int(diff -lenbuf))
-		dprintf("-->pos= %v\n", b.Pos())
 		return true
 	}
 	return false

pkg/groot/core.go

 
 import (
 	"fmt"
+	"os"
 )
 
 var g_verbose = false
 
 func printf(format string, args ...interface{}) {
 	if g_verbose {
-		fmt.Printf(format, args...)
+		fmt.Fprintf(os.Stderr, format, args...)
 	}
 }
 
 func dprintf(format string, args ...interface{}) {
-	fmt.Printf(format, args...)
+	fmt.Fprintf(os.Stderr, format, args...)
+	//printf(format, args...)
 }
 
 const (

pkg/groot/leaf.go

 	"reflect"
 )
 
+// leaf of bytes
+
+type LeafB struct {
+	base baseLeaf
+	min int32
+	max int32
+	data []byte
+}
+
+func (leaf *LeafB) toBaseLeaf() *baseLeaf {
+	return &leaf.base
+}
+
+func (leaf *LeafB) Class() Class {
+	panic("not implemented")
+}
+
+func (leaf *LeafB) Name() string {
+	return leaf.base.name
+}
+
+func (leaf *LeafB) Title() string {
+	return leaf.base.title
+}
+
+func (leaf *LeafB) ROOTDecode(b *Buffer) (err error) {
+	spos := b.Pos()
+	vers, pos, bcnt := b.read_version()
+	printf("[leafB] vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
+	err = leaf.base.ROOTDecode(b)
+	if err != nil {
+		return err
+	}
+	leaf.min = b.ntoi4()
+	leaf.max = b.ntoi4()
+	leaf.data = make([]byte, int(leaf.base.length))
+	printf("leafI min=%v max=%v len=%d\n", leaf.min, leaf.max, len(leaf.data))
+	b.check_byte_count(pos,bcnt,spos, "LeafB")
+	return
+}
+
+func (leaf *LeafB) ROOTEncode(b *Buffer) (err error) {
+	//FIXME
+	panic("not implemented")
+}
+
+// leaf of shorts
+
+type LeafS struct {
+	base baseLeaf
+	min int32
+	max int32
+	data []int8
+}
+
+func (leaf *LeafS) toBaseLeaf() *baseLeaf {
+	return &leaf.base
+}
+
+func (leaf *LeafS) Class() Class {
+	panic("not implemented")
+}
+
+func (leaf *LeafS) Name() string {
+	return leaf.base.name
+}
+
+func (leaf *LeafS) Title() string {
+	return leaf.base.title
+}
+
+func (leaf *LeafS) ROOTDecode(b *Buffer) (err error) {
+	spos := b.Pos()
+	vers, pos, bcnt := b.read_version()
+	printf("[leafS] vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
+	err = leaf.base.ROOTDecode(b)
+	if err != nil {
+		return err
+	}
+	leaf.min = b.ntoi4()
+	leaf.max = b.ntoi4()
+	leaf.data = make([]int8, int(leaf.base.length))
+	printf("leafI min=%v max=%v len=%d\n", leaf.min, leaf.max, len(leaf.data))
+	b.check_byte_count(pos,bcnt,spos, "LeafS")
+	return
+}
+
+func (leaf *LeafS) ROOTEncode(b *Buffer) (err error) {
+	//FIXME
+	panic("not implemented")
+}
+
 // leaf of ints
 
 type LeafI struct {
 }
 
 func (leaf *LeafI) ROOTDecode(b *Buffer) (err error) {
-
+	spos := b.Pos()
 	vers, pos, bcnt := b.read_version()
-	dprintf("leafI-vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
+	printf("leafI-vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
 	err = leaf.base.ROOTDecode(b)
 	if err != nil {
 		return err
 	leaf.min = b.ntoi4()
 	leaf.max = b.ntoi4()
 	leaf.data = make([]int, int(leaf.base.length))
-	dprintf("leafI min=%v max=%v len=%d\n", leaf.min, leaf.max, len(leaf.data))
+	printf("leafI min=%v max=%v len=%d\n", leaf.min, leaf.max, len(leaf.data))
+	b.check_byte_count(pos,bcnt,spos, "LeafI")
 	return
 }
 
 }
 
 func (leaf *LeafL) ROOTDecode(b *Buffer) (err error) {
-
+	spos := b.Pos()
 	vers, pos, bcnt := b.read_version()
-	dprintf("leafL-vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
+	printf("leafL-vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
 	err = leaf.base.ROOTDecode(b)
 	if err != nil {
 		return err
 	leaf.min = b.ntoi4()
 	leaf.max = b.ntoi4()
 	leaf.data = make([]int64, int(leaf.base.length))
-	dprintf("leafL min=%v max=%v len=%d\n", leaf.min, leaf.max, len(leaf.data))
+	printf("leafL min=%v max=%v len=%d\n", leaf.min, leaf.max, len(leaf.data))
+	b.check_byte_count(pos,bcnt,spos, "LeafL")
 	return
 }
 
 }
 
 func (leaf *LeafF) ROOTDecode(b *Buffer) (err error) {
-
+	spos := b.Pos()
 	vers, pos, bcnt := b.read_version()
-	dprintf("leafF-vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
+	printf("leafF-vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
 	err = leaf.base.ROOTDecode(b)
 	if err != nil {
 		return err
 	leaf.min = b.ntoi4()
 	leaf.max = b.ntoi4()
 	leaf.data = make([]float32, int(leaf.base.length))
-	dprintf("leafF min=%v max=%v len=%d\n", leaf.min, leaf.max, len(leaf.data))
+	printf("leafF min=%v max=%v len=%d\n", leaf.min, leaf.max, len(leaf.data))
+	b.check_byte_count(pos,bcnt,spos, "LeafF")
 	return
 }
 
 }
 
 func (leaf *LeafD) ROOTDecode(b *Buffer) (err error) {
-
+	spos := b.Pos()
 	vers, pos, bcnt := b.read_version()
-	dprintf("leafD-vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
+	printf("leafD-vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
 	err = leaf.base.ROOTDecode(b)
 	if err != nil {
 		return err
 	leaf.min = b.ntoi4()
 	leaf.max = b.ntoi4()
 	leaf.data = make([]float64, int(leaf.base.length))
-	dprintf("leafD min=%v max=%v len=%d\n", leaf.min, leaf.max, len(leaf.data))
+	printf("leafD min=%v max=%v len=%d\n", leaf.min, leaf.max, len(leaf.data))
+	b.check_byte_count(pos,bcnt,spos, "LeafD")
 	return
 }
 
 	panic("not implemented")
 }
 
+// leaf of a string
+
+type LeafC struct {
+	base baseLeaf
+	min int32
+	max int32
+	data string
+}
+
+func (leaf *LeafC) toBaseLeaf() *baseLeaf {
+	return &leaf.base
+}
+
+func (leaf *LeafC) Class() Class {
+	panic("not implemented")
+}
+
+func (leaf *LeafC) Name() string {
+	return leaf.base.name
+}
+
+func (leaf *LeafC) Title() string {
+	return leaf.base.title
+}
+
+func (leaf *LeafC) ROOTDecode(b *Buffer) (err error) {
+	spos := b.Pos()
+	vers, pos, bcnt := b.read_version()
+	printf("[leafC] vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
+	err = leaf.base.ROOTDecode(b)
+	if err != nil {
+		return err
+	}
+	leaf.min = b.ntoi4()
+	leaf.max = b.ntoi4()
+	printf("leafC min=%v max=%v len=%d\n", leaf.min, leaf.max, len(leaf.data))
+	b.check_byte_count(pos,bcnt,spos, "LeafC")
+	return
+}
+
+func (leaf *LeafC) ROOTEncode(b *Buffer) (err error) {
+	//FIXME
+	panic("not implemented")
+}
+
+// leaf of bool
+
+type LeafO struct {
+	base baseLeaf
+	min int32
+	max int32
+	data []bool
+}
+
+func (leaf *LeafO) toBaseLeaf() *baseLeaf {
+	return &leaf.base
+}
+
+func (leaf *LeafO) Class() Class {
+	panic("not implemented")
+}
+
+func (leaf *LeafO) Name() string {
+	return leaf.base.name
+}
+
+func (leaf *LeafO) Title() string {
+	return leaf.base.title
+}
+
+func (leaf *LeafO) ROOTDecode(b *Buffer) (err error) {
+	spos := b.Pos()
+	vers, pos, bcnt := b.read_version()
+	printf("[leafO] vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
+	err = leaf.base.ROOTDecode(b)
+	if err != nil {
+		return err
+	}
+	leaf.min = b.ntoi4()
+	leaf.max = b.ntoi4()
+	leaf.data= make([]bool, int(leaf.base.length))
+	printf("leafO min=%v max=%v len=%d\n", leaf.min, leaf.max, len(leaf.data))
+	b.check_byte_count(pos,bcnt,spos, "LeafO")
+	return
+}
+
+func (leaf *LeafO) ROOTEncode(b *Buffer) (err error) {
+	//FIXME
+	panic("not implemented")
+}
+
 func init() {
+
+	{
+		f := func() reflect.Value {
+			o := &LeafO{}
+			return reflect.ValueOf(o)
+		}
+		Factory.db["TLeafO"] = f
+		Factory.db["*groot.LeafO"] = f
+	}
+
+	{
+		f := func() reflect.Value {
+			o := &LeafB{}
+			return reflect.ValueOf(o)
+		}
+		Factory.db["TLeafB"] = f
+		Factory.db["*groot.LeafB"] = f
+	}
+
+	{
+		f := func() reflect.Value {
+			o := &LeafS{}
+			return reflect.ValueOf(o)
+		}
+		Factory.db["TLeafS"] = f
+		Factory.db["*groot.LeafS"] = f
+	}
+
 	{
 		f := func() reflect.Value {
 			o := &LeafI{}
 		Factory.db["TLeafD"] = f
 		Factory.db["*groot.LeafD"] = f
 	}
+
+	{
+		f := func() reflect.Value {
+			o := &LeafC{}
+			return reflect.ValueOf(o)
+		}
+		Factory.db["TLeafC"] = f
+		Factory.db["*groot.LeafC"] = f
+	}
 }
 
+// check interfaces
+var _ Object = (*LeafO)(nil)
+var _ ROOTStreamer = (*LeafO)(nil)
+
+var _ Object = (*LeafB)(nil)
+var _ ROOTStreamer = (*LeafB)(nil)
+
+var _ Object = (*LeafS)(nil)
+var _ ROOTStreamer = (*LeafS)(nil)
+
+var _ Object = (*LeafI)(nil)
+var _ ROOTStreamer = (*LeafI)(nil)
+
+var _ Object = (*LeafL)(nil)
+var _ ROOTStreamer = (*LeafL)(nil)
+
+var _ Object = (*LeafF)(nil)
+var _ ROOTStreamer = (*LeafF)(nil)
+
+var _ Object = (*LeafD)(nil)
+var _ ROOTStreamer = (*LeafD)(nil)
+
+var _ Object = (*LeafC)(nil)
+var _ ROOTStreamer = (*LeafC)(nil)
+
 // EOF

pkg/groot/leaf_element.go

 
 	spos := b.Pos()
 	vers, pos, bcnt := b.read_version()
-	dprintf("vers=%v spos=%v pos=%v bcnt=%v\n", vers, spos, pos, bcnt)
+	printf("[leafelement] vers=%v spos=%v pos=%v bcnt=%v\n", 
+		vers, spos, pos, bcnt)
 	err = le.base.ROOTDecode(b)
 	if err != nil {
 		return err

pkg/groot/list.go

 package groot
 
 import (
-	"reflect"
+	//"reflect"
 )
 
+// FIXME: make List a struct ?
+
 type List []Object
 
+func (lst *List) Class() Class {
+	panic("not implemented")
+}
+
+func (lst *List) Name() string {
+	return "list-name"
+}
+
+func (lst *List) Title() string {
+	return "list-title"
+}
+
 func (lst *List) ROOTDecode(b *Buffer) (err error) {
 
 	vers, pos, bcnt := b.read_version()
 
 func init() {
 
-	new_lst := func() reflect.Value {
-		o := make(List, 0)
-		return reflect.ValueOf(&o)
-	}
-
-	Factory.db["TList"] = new_lst
-	Factory.db["*groot.List"] = new_lst
+	//FIXME...
+	// new_lst := func() reflect.Value {
+	// 	o := make(List, 0)
+	// 	return reflect.ValueOf(&o)
+	// }
+	//Factory.db["TList"] = new_lst
+	//Factory.db["*groot.List"] = new_lst
 }
 
+// check interfaces
+var _ Object = (*List)(nil)
+var _ ROOTStreamer = (*List)(nil)
+
 // EOF

pkg/groot/reader.go

 	return
 
 	lst := make(List, 0)
-	dprintf("lst: %v\n", lst)
+	printf("lst: %v\n", lst)
 
 	var buf []byte
 
 			lst = obj
 		}
 	}
-	dprintf("buf: %v\n", len(buf))
+	printf("buf: %v\n", len(buf))
 
 	return err
 }

pkg/groot/tree.go

 	return tree.entries
 }
 
+func (tree *Tree) Branches() []Branch {
+	return tree.branches
+}
+
 func (tree *Tree) ROOTDecode(b *Buffer) (err error) {
-
+	spos := b.Pos()
 	vers, pos, bcnt := b.read_version()
-	dprintf("vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
+	printf("[tree] vers=%v pos=%v bcnt=%v\n", vers, pos, bcnt)
 	tree.name, tree.title = b.read_tnamed()
-	dprintf("name='%v' title='%v'\n", tree.name, tree.title)
+	printf("name='%v' title='%v'\n", tree.name, tree.title)
 	b.read_attline()
 	b.read_attfill()
 	b.read_attmarker()
 		b.ntoi8() //fEstimate
 	}
 
-	dprintf("=> (%s) entries=%v tot_bytes=%v zip_bytes=%v\n", 
+	printf("=> (%s) entries=%v tot_bytes=%v zip_bytes=%v\n", 
 		tree.name, tree.entries, tree.tot_bytes, tree.zip_bytes)
 
 	branches := b.read_obj_array()
-	dprintf("-- #nbranches: %v\n", len(branches))
+	printf("-- #nbranches: %v\n", len(branches))
+	tree.branches = make([]Branch, len(branches))
+	for i,v := range branches {
+		tree.branches[i] = *(v.(ibranch).toBranch())
+	}
+	leaves := b.read_obj_array()
+	printf("-- #nleaves: %v\n", len(leaves))
 
-	leaves := b.read_obj_array()
-	dprintf("-- #nleaves: %v\n", len(leaves))
+	if vers >= 10 {
+		b.read_object() // fAliases *TList
+	}
 
+	b.read_array_D() // fIndexValues TArrayD
+	b.read_array_I() // fIndex TArrayI
+
+	if vers >= 16 {
+		b.read_object() // fTreeIndex *TVirtualIndex // FIXME?
+	}
+	if vers >= 6 {
+		b.read_object() // fFriends *TList
+	}
+	if vers >= 16 {
+		b.read_object() // fUserInfo *TList
+		b.read_object() // fBranchRef *TBranchRef
+	}
+
+	b.check_byte_count(pos,bcnt, spos, "TTree")
 	return
 }
 
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.