|
|
|
|
|
by trealira
941 days ago
|
|
The main issue is that C doesn't have a way to pass arrays of any size to functions while preserving their type (the size is part of an array's type in C); by convention, one generally passes a pointer to its first element and a separate length parameter. A compiler cannot know that any two pointers do not point to the same location. Hence, it's harder to vectorize code like this, because each store to result[i] may affect arr1[i] or arr2[i]; in other words, the pointers might alias. In C89: /* They're all the same length */
void add(float *result, float *arr1, float *arr2, size_t len)
{
size_t i;
for (i = 0; i < len; ++i)
result[i] = arr1[i] + arr2[i];
}
The solution is supposed to be the "restrict" keyword, which informs the compiler that other pointers do not alias this one. It was added in C99. You declare a pointer that doesn't alias like this: float *restrict float_ptr;
If a restrict pointer is aliased by another pointer, the behavior is undefined.https://en.wikipedia.org/wiki/Restrict It's hard to judge the extent to which this helps. Apparently, when Rust annotated all its mutable references and Box<T> types with the LLVM equivalent of the "restrict" annotation, they exposed a lot of bugs in LLVM's implementation of it, because most C code doesn't use "restrict" pointers as extensively as Rust code uses mutable references and Boxes. |
|