6 * An IEStream is a sorted list of index entries.
11 u64int off; /* read position within part */
12 u64int n; /* number of valid ientries left to read */
13 u32int size; /* allocated space in buffer */
15 u8int *pos; /* current place in buffer */
16 u8int *epos; /* end of valid buffer contents */
20 initiestream(Part *part, u64int off, u64int clumps, u32int size)
26 ies->buf = MKN(u8int, size);
37 freeiestream(IEStream *ies)
46 * Return the next IEntry (still packed) in the stream.
49 peekientry(IEStream *ies)
53 n = ies->epos - ies->pos;
55 memmove(ies->buf, ies->pos, n);
56 ies->epos = &ies->buf[n];
59 if(nn > ies->n * IEntrySize)
60 nn = ies->n * IEntrySize;
64 //fprint(2, "peek %d from %llud into %p\n", nn, ies->off, ies->epos);
65 if(readpart(ies->part, ies->off, ies->epos, nn) < 0){
66 seterr(EOk, "can't read sorted index entries: %r");
76 * Compute the bucket number for the given IEntry.
77 * Knows that the score is the first thing in the packed
81 iebuck(Index *ix, u8int *b, IBucket *ib, IEStream *ies)
85 return hashbits(b, 32) / ix->div;
89 * Fill ib with the next bucket in the stream.
92 buildbucket(Index *ix, IEStream *ies, IBucket *ib, uint maxdata)
104 //fprint(2, "b=%p ies->n=%lld ib.n=%d buck=%d score=%V\n", b, ies->n, ib->n, iebuck(ix, b, ib, ies), b);
106 buck = iebuck(ix, b, ib, ies);
108 if(buck != iebuck(ix, b, ib, ies))
110 if(ientrycmp(&ib->data[(ib->n - 1)* IEntrySize], b) == 0){
112 * guess that the larger address is the correct one to use
114 unpackientry(&ie1, &ib->data[(ib->n - 1)* IEntrySize]);
115 unpackientry(&ie2, b);
116 seterr(EOk, "duplicate index entry for score=%V type=%d", ie1.score, ie1.ia.type);
118 if(ie1.ia.addr > ie2.ia.addr)
119 memmove(b, &ib->data[ib->n * IEntrySize], IEntrySize);
122 if((ib->n+1)*IEntrySize > maxdata){
123 seterr(EOk, "bucket overflow");
126 memmove(&ib->data[ib->n * IEntrySize], b, IEntrySize);
129 ies->pos += IEntrySize;