I was debugging some code which makes heavy use of Matrices and Vectors which I defined using static[int]. I had some random crashes and wrong calculations in my code which I could not explain.
I was able to pin down the problem to the usage of the Matrix and Vector types within tuple and object types. It seems like the compiler creates some wrong types for these.
I did create a very small program replicating the problem:
type
Vector[N: static[int]] = array[N, float64]
TwoVectors[Na, Nb: static[int]] = tuple
a: Vector[Na]
b: Vector[Nb]
when isMainModule:
var v: TwoVectors[2, 100]
echo v.a.len
echo v.b.len
v.b[50] = 0.0
This outputs:
2
2
SIGSEGV: Illegal storage access. (Attempt to read from nil?)
I would have expected 2 and 100 as output (and no crash). The generated c code seems to confirm that something is wrong. Both fields have the same type.
typedef NF Vector91035[2];
struct Twovectors91032 {
Vector91035 Field0;
Vector91035 Field1;
};
Do I make some wrong assumptions about how I use these types? Or is there indeed something wrong with the generated code ?
It's a very serious bug.
However, I get "index out of bounds" at compile-time and when I workaround with a runtime based index, I get an "index out of bounds" exception. So I cannot see how this can happen
Thanks for the swift response. At least I know I'm not doing something wrong. I'll try to find a work-around for my code.
... I get "index out of bounds" at compile-time ...
I tend to compile with -d:release and then it is not mentioned. My mistake :-)
But my real code is a little bit more involved, with less obvious inference of the length of the Vectors and Matrices. The same error happens in that code (when looking at the generated C code). But I don't get an index out of bounds warning/error with or without -d:release. Most of the time it just gives wrong results, but from time to time it just crashes. I did have a look at the C code and it looks like it sometimes overwrites some other parts in the generated structs. (But it could as well be normal bugs in my code)
If you want me too, I can hunt again for such an example if that would be usefull ...
... and wrong calculations ...
I do use m.high and iterators over arrays a lot in my generic functions. With a wrong type, all these functions still work but give unexpected results.
If you want me too, I can hunt again for such an example if that would be usefull ..
Wrong indexing in debug mode should always raise an exception.
@Araq: Thanks for the fix. I can confirm that it fixes the bug. My main code works perfect now.
I did hunt again for the crash. And I can confirm that in debug mode I can not reproduce such a crash. Looking at the generated C code, it also seems to have all of the right checks in place to check for bounds errors.
So, it must have been a combination of my code assuming the correct type together with my -d:release compilation that produced the crash.
Parenthetical remark: this may be a good use case for my linalg library
It allows computations with matrices and vectors of static size, delegating actual work to whatever implementation of BLAS is linked, and I am in the process of also making it run on the GPU. In fact I wrote it with the aim of making a neural network library on top of it.
I am sure there will be issues, since it is pretty young, but I would be happy to give you help and fix any bugs that may come around.
(Sorry for hijacking the thread, but I noticed the similarity of what you were doing with what I have done)
@andrea: I did have a look at your library some time ago. It does look promising. Being able to easily use BLAS would be nice.
But for these small initial tests, I didn't want too much dependencies. (And I have to admit that I wanted to have a play with an implementation of Matrices and Vectors myself too :-) )
I'm sure that - once we figured out which algorithms we will use - we'll have a look at your library again. (and maybe join forces)