Recent cgen update breaks codegen with read_only temporary variables
The release of cgen 2019.1 changed the parentheses emitted in array and pointer-to POD data. As a result, the following kernel is incorrectly transpiled to C:
import numpy
import loopy
k = loopy.make_kernel("{ : }", "a[0] = b[0]",
[...],
temporary_variables={"b": loopy.TemporaryVariable("b", dtype=float, shape=(1, ),
initializer=numpy.arange(1, dtype=float),
read_only=True, address_space=loopy.AddressSpace.GLOBAL)},
target=loopy.CTarget())
print(loopy.generate_code_v2(k).device_code())
static double (const b)[1] = { 0.0 };
void loopy_kernel(double *__restrict__ (a))
{
a[0] = b[0];
}
I think this actually just exposes a long-time bug in the handling of temporary variable declarations in the codegen:
https://gitlab.tiker.net/inducer/loopy/blob/master/loopy/target/c/init.py#L719
Effectively declares read-only temporaries as "array of const foo", whereas it should be saying "const array of foo". I think this patch might be right?
diff --git a/loopy/target/c/__init__.py b/loopy/target/c/__init__.py
index 25b19080..892b2fa3 100644
--- a/loopy/target/c/__init__.py
+++ b/loopy/target/c/__init__.py
@@ -759,10 +759,6 @@ class CASTBuilder(ASTBuilderBase):
def get_temporary_decl(self, codegen_state, schedule_index, temp_var, decl_info):
temp_var_decl = POD(self, decl_info.dtype, decl_info.name)
- if temp_var.read_only:
- from cgen import Const
- temp_var_decl = Const(temp_var_decl)
-
if decl_info.shape:
from cgen import ArrayOf
ecm = self.get_expression_to_code_mapper(codegen_state)
@@ -770,6 +766,10 @@ class CASTBuilder(ASTBuilderBase):
ecm(p.flattened_product(decl_info.shape),
prec=PREC_NONE, type_context="i"))
+ if temp_var.read_only:
+ from cgen import Const
+ temp_var_decl = Const(temp_var_decl)
+
if temp_var.alignment:
from cgen import AlignedAttribute
temp_var_decl = AlignedAttribute(temp_var.alignment, temp_var_decl)
Edited by Lawrence Mitchell