We now just insert them one after the other in the vector. When rewind
is called, the vector is sorted. Iterating is just taking elements from
the vector.
Related to #191
SQLite3:
```sh
$ time sqlite3 testing/testing.db "SELECT id FROM users ORDER BY zipcode" > /dev/null
real 0m0.020s
user 0m0.013s
sys 0m0.008s
```
Limbo without this PR:
```sh
$ time target/release/limbo testing/testing.db "SELECT id FROM users ORDER BY zipcode" > /dev/null
real 0m0.285s
user 0m0.257s
sys 0m0.014s
```
Limbo with this PR:
```sh
$ time target/release/limbo testing/testing.db "SELECT id FROM users ORDER BY zipcode" > /dev/null
real 0m0.084s
user 0m0.043s
sys 0m0.032s
```
Closes#362
We now just insert them one after the other in the vector. When rewind
is called, the vector is sorted. Iterating is just taking elements from
the vector
interior index cells have values that are not in the leaves, e.g.
(interior: 3)
/ \
(leaf: 2) (leaf: 4)
so their values need to be emitted after the left subtree is emitted.
Relates to issue #144
> ## instr(X,Y)
>
> The instr(X,Y) function finds the first occurrence of string Y within
string X and returns the number of prior characters plus 1, or 0 if Y is
nowhere found within X. Or, if X and Y are both BLOBs, then instr(X,Y)
returns one more than the number bytes prior to the first occurrence of
Y, or 0 if Y does not occur anywhere within X. If both arguments X and Y
to instr(X,Y) are non-NULL and are not BLOBs then both are interpreted
as strings. If either X or Y are NULL in instr(X,Y) then the result is
NULL.
Closes#357
Closes#351
NextAwait's next instruction was pointing to RewindAwait earlier which
is not current. The instruction now points to the instruction after
RewindAwait, which will be the loop body. Hence, rename rewind_labels to
scan_loop_body_labels to make it clearer
Reviewed-by: Jussi Saurio <jussi.saurio@gmail.com>
Closes#354
Closes#351
NextAwait's next instruction was pointing to RewindAwait earlier which
is not current. The instruction now points to the instruction after
RewindAwait, which will be the loop body. Hence, rename rewind_labels to
scan_loop_body_labels to make it clearer
Add a `pending_ops` field to `InnerLinuxIO` struct which is incremented
for each operation submitted to the ring and decremented when they are
taken off the completion queue. With this, we can exit from run_once if
there are no pending operations. Otherwise, in that case, it would hang
indefinitely due to call of `ring.submit_and_wait(1)`
Closes#349
Adds a struct WrappedIOUring which contains a IoUring and a pending_ops
field. Entry submission and popping from the queue is done through
functions operating on it, which also maintains pending_ops count
NOTE: This is a bit weird/hacky since in get_completion we create a
CompletionQueue and just call its next(). If it were a normal iterator
it would always return the same first item. However it is a queue posing
as an iterator which makes this work.