Avoiding RangeError getting address of empty seq

2020-07-23 Thread lscrd
I think we were in a dialog of deaf. You were focused on the difference between uninitialized (with {.noinit.}) and initialized sequences (other sequences) whereas I was focused on the difference between sequences with no explicit initialization and sequences with explicit initialization. What

Avoiding RangeError getting address of empty seq

2020-07-23 Thread jibal
> It doesn't matter, actually. Note my comment above: "there is a subtlety: the quoted C standard says that "pointer arguments on such a call shall still have valid values", which is not true of NULL (nil). But few implementations check the pointer when the len is 0, so people get away with it.

Avoiding RangeError getting address of empty seq

2020-07-23 Thread snej
> But, then there is a inconsistency as some sequences of length 0 (those non > allocated) will return nil, while others (those empty) will return a non nil > value. It would be better to return nil in both cases. It doesn't matter, actually. Any two zero-length byte ranges (slices) are equival

Avoiding RangeError getting address of empty seq

2020-07-23 Thread jibal
> Yes, indeed, except that the compiler processes them the same way, i.e. both > are considered to have length 0. No, you're misunderstanding, and making the same mistake. An uninitialized seq, which you can get with {.noinit.}, has not been zero-filled ... it contains junk, and using it is lik

Avoiding RangeError getting address of empty seq

2020-07-23 Thread lscrd
No, you can’t avoid the test as the area containing the length, the capacity and the items may not have been allocated yet, as in `var s: seq[int]`. You can’t return the address of something which doesn’t exist. Now, I agree that if this area has been allocated, it would be possible to simply r

Avoiding RangeError getting address of empty seq

2020-07-23 Thread snej
A predefined proc for this could avoid the unnecessary range check and simply return the internal `seq` field that points to the items — that would boil down to one CPU instruction. If the seq is empty the result would presumably be `nil`, but as explained several times above (thanks, @jibal!)

Avoiding RangeError getting address of empty seq

2020-07-23 Thread lscrd
> Empty is not uninitialized--they are two completely different concepts. Yes, indeed, except that the compiler processes them the same way, i.e. both are considered to have length 0. In fact, there are no uninitialized objects in Nim. If you write `var s: seq[int]`, the memory area representin

Avoiding RangeError getting address of empty seq

2020-07-23 Thread jibal
C and C++ define the address of the element one beyond the end of an array to be referable but not dereferenceable ... that is, you can take its address but you can't access its content. Nim considers merely taking the address of the element one beyond the end of an array or sequence to be a ran

Avoiding RangeError getting address of empty seq

2020-07-22 Thread Stefan_Salewski
> how do I get a pointer to its items Well you did it the right and common way in your first post: socket.send(addr data[0], data.len) Run When we have var s1: seq[T] then addr(s1[0]) is the address of the first element. But as I told you, the dereference s1[0] may fa

Avoiding RangeError getting address of empty seq

2020-07-22 Thread snej
Um ... I think both of you misunderstood my question, since neither of your replies make any sense to me. Let me be specific. Given a `seq`, how do I get a pointer to its items, in a way that doesn't fail when the seq is empty? I'm looking for something equivalent to C++'s `std::vector::data()`

Avoiding RangeError getting address of empty seq

2020-07-22 Thread Stefan_Salewski
> A seq is just 3 values (len, ptr and cap). I thinbk that is wrong for modern Nim. Sizeof(seq) is 8. I think onje of the two ints, cap or len is not stored in the seq value object, but in the data buffer.

Avoiding RangeError getting address of empty seq

2020-07-22 Thread Stefan_Salewski
The problem is not that the seq is empty, but it is in an uninitialized state still. var s1: seq[int] var s2 = newSeq[int]() Run s2 should give no problem. Core part of a seq is a pointer to the actual data. I think for s1 that pointer is just nil still. Unfortuna

Avoiding RangeError getting address of empty seq

2020-07-22 Thread treeform
I don't think so. When data.len == 0 there is no allocation storage. The pointer pointing to the array is nil. A seq is just 3 values (len, ptr and cap). When len = 0 its just (0, 0, 0) everywhere. You will be just sending it: socket.send(nil, 0) Run

Avoiding RangeError getting address of empty seq

2020-07-22 Thread snej
There are times I need to pass a seq as a pointer and byte-count, usually to C code but sometimes to Nim code like AsyncSocket.send. If I do it like this: socket.send(addr data[0], data.len) Run it unfortunately raises a RangeError when `data` is empty. So I have to