• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

mlange-42 / ark / 13525392689

25 Feb 2025 03:54PM CUT coverage: 94.787%. Remained the same
13525392689

push

github

web-flow
Update CHANGELOG (#73)

3400 of 3587 relevant lines covered (94.79%)

52392.39 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

96.04
/ecs/column.go
1
package ecs
2

3
import (
4
        "reflect"
5
        "unsafe"
6
)
7

8
// column storage for components in an archetype.
9
type column struct {
10
        data     reflect.Value
11
        pointer  unsafe.Pointer
12
        itemSize uintptr
13
        len      uint32
14
}
15

16
// newColumn creates a new column for a given type and capacity.
17
func newColumn(tp reflect.Type, capacity uint32) column {
822✔
18
        // TODO: should be use a slice instead of an array here?
822✔
19
        data := reflect.New(reflect.ArrayOf(int(capacity), tp)).Elem()
822✔
20
        pointer := data.Addr().UnsafePointer()
822✔
21

822✔
22
        return column{
822✔
23
                data:     data,
822✔
24
                pointer:  pointer,
822✔
25
                itemSize: sizeOf(tp),
822✔
26
                len:      0,
822✔
27
        }
822✔
28
}
822✔
29

30
// Len returns the number of components in the column.
31
func (c *column) Len() int {
1,014,706✔
32
        return int(c.len)
1,014,706✔
33
}
1,014,706✔
34

35
// Cap returns the current capacity of the column.
36
func (c *column) Cap() int {
1,012,459✔
37
        return c.data.Cap()
1,012,459✔
38
}
1,012,459✔
39

40
// Get returns a pointer to the component at the given index.
41
func (c *column) Get(index uintptr) unsafe.Pointer {
5,066,614✔
42
        return unsafe.Add(c.pointer, index*c.itemSize)
5,066,614✔
43
}
5,066,614✔
44

45
// Add adds a component to the column.
46
func (c *column) Add(comp unsafe.Pointer) (unsafe.Pointer, uint32) {
503,928✔
47
        c.Extend(1)
503,928✔
48
        c.len++
503,928✔
49
        return c.Set(c.len-1, comp), c.len - 1
503,928✔
50
}
503,928✔
51

52
// Alloc allocates memory for the given number of components.
53
func (c *column) Alloc(n uint32) {
508,525✔
54
        c.Extend(n)
508,525✔
55
        c.len += n
508,525✔
56
}
508,525✔
57

58
func (c *column) AddAll(other *column) {
3✔
59
        oldLen := c.len
3✔
60
        c.Alloc(other.len)
3✔
61
        src := other.Get(0)
3✔
62
        dst := c.Get(uintptr(oldLen))
3✔
63
        copyPtr(src, dst, c.itemSize*uintptr(other.len))
3✔
64
}
3✔
65

66
// Set overwrites the component at the given index.
67
func (c *column) Set(index uint32, comp unsafe.Pointer) unsafe.Pointer {
1,013,607✔
68
        dst := c.Get(uintptr(index))
1,013,607✔
69
        if c.itemSize == 0 {
1,014,042✔
70
                return dst
435✔
71
        }
435✔
72

73
        copyPtr(comp, dst, uintptr(c.itemSize))
1,013,172✔
74
        return dst
1,013,172✔
75
}
76

77
// Remove swap-removes the component at the given index.
78
// Returns whether a swap was necessary.
79
func (c *column) Remove(index uint32, zero unsafe.Pointer) bool {
1,007,496✔
80
        lastIndex := uintptr(c.len - 1)
1,007,496✔
81
        swapped := index != uint32(lastIndex)
1,007,496✔
82

1,007,496✔
83
        if swapped && c.itemSize != 0 {
2,009,768✔
84
                src := unsafe.Add(c.pointer, lastIndex*c.itemSize)
1,002,272✔
85
                dst := unsafe.Add(c.pointer, uintptr(index)*c.itemSize)
1,002,272✔
86
                copyPtr(src, dst, uintptr(c.itemSize))
1,002,272✔
87
        }
1,002,272✔
88
        c.len--
1,007,496✔
89
        if zero != nil {
1,512,244✔
90
                c.Zero(lastIndex, zero)
504,748✔
91
        }
504,748✔
92
        return swapped
1,007,496✔
93
}
94

95
// Extend the column to be able to store the given number of additional components.
96
// Has no effect of the column's capacity is already sufficient.
97
// If the capacity needs to be increased, it will be doubled until it is sufficient.
98
func (c *column) Extend(by uint32) {
1,012,453✔
99
        required := c.Len() + int(by)
1,012,453✔
100
        cap := c.Cap()
1,012,453✔
101
        if cap >= required {
2,023,918✔
102
                return
1,011,465✔
103
        }
1,011,465✔
104
        for cap < required {
2,064✔
105
                cap *= 2
1,076✔
106
        }
1,076✔
107
        old := c.data
988✔
108
        c.data = reflect.New(reflect.ArrayOf(cap, old.Type().Elem())).Elem()
988✔
109
        c.pointer = c.data.Addr().UnsafePointer()
988✔
110
        reflect.Copy(c.data, old)
988✔
111
}
112

113
// Zero resets the memory at the given index.
114
func (c *column) Zero(index uintptr, zero unsafe.Pointer) {
504,748✔
115
        if c.itemSize == 0 {
504,784✔
116
                return
36✔
117
        }
36✔
118
        dst := unsafe.Add(c.pointer, index*c.itemSize)
504,712✔
119
        copyPtr(zero, dst, uintptr(c.itemSize))
504,712✔
120
}
121

122
// Zero resets a block of storage in one buffer.
123
func (c *column) ZeroRange(start, len uint32, zero unsafe.Pointer) {
2✔
124
        size := uint32(c.itemSize)
2✔
125
        if size == 0 {
3✔
126
                return
1✔
127
        }
1✔
128
        var i uint32
1✔
129
        for i = 0; i < len; i++ {
33✔
130
                dst := unsafe.Add(c.pointer, (i+start)*size)
32✔
131
                copyPtr(zero, dst, c.itemSize)
32✔
132
        }
32✔
133
}
134

135
func (c *column) Reset(zero unsafe.Pointer) {
3✔
136
        len := c.len
3✔
137
        if c.len == 0 {
3✔
138
                return
×
139
        }
×
140
        c.len = 0
3✔
141
        if zero == nil {
4✔
142
                return
1✔
143
        }
1✔
144
        if len <= 64 { // A coarse estimate where manually zeroing is faster
4✔
145
                c.ZeroRange(0, len, zero)
2✔
146
        } else {
2✔
147
                c.data.SetZero()
×
148
        }
×
149
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc