clad icon indicating copy to clipboard operation
clad copied to clipboard

Clad generates functions that cannot be compiled afterwards

Open parth-07 opened this issue 3 years ago • 7 comments

Some of the reverse mode derived functions generated by Clad cannot be compiled afterwards because they contain a variable declaration after the goto labels (used for return statements), and thus give the following error:

error: cannot jump from this goto statement to its label
note: jump bypasses variable initialization

One example of this issue from the test/Gradient/Gradients.C:

double f_decls3(double x, double y) {
  double a = 3 * x;
  double c = 333 * y;
  if (x > 1)
    return 2 * a;  // We add a goto statement in the forward pass 
  else if (x < -1)
    return -2 * a;  // We add a variable declaration for the return value followed by a goto statement. Both in the forward pass.
  double b = a * a;  // We add a variable declaration in the forward pass
  return b;  // We add a variable declaration for the return value followed by a  goto statement. Both in the forward pass.
}

One way to resolve this issue is by declaring all the variables currently being declared after a goto statement, at the beginning of the function. We already use a similar idea for the derived variables

parth-07 avatar Feb 01 '22 19:02 parth-07

@parth-07 the thing i can do in this function is to add the variable whose name is double b; after that the thing we can impliment is double a = 3 * x; double c = 333 * y; double b=0; if (x > 1) goto jump1; else if (x < -1) goto jump2; else goto jump3;

jump1: (b= 2 * a); jump2: (b= -2 * a); jump3: b=a*a; return b; i think this can work

rajeck1234 avatar Mar 11 '23 13:03 rajeck1234

Hello @parth-07 @vgvassilev, may this can solve this issue, Please give me feedback on this solution.

To resolve this issue, we need to declare all the variables currently being declared after a goto statement at the beginning of the function. This will ensure that the variable initialization happens before the goto statement is executed. Here's how we can modify the function f_decls3 to fix this issue:

  double a, b, c;
  a = 3 * x;
  c = 333 * y;
  if (x > 1)
    goto label1;
  else if (x < -1) {
    double temp = -2 * a;
    goto label2;
  }
  b = a * a;
label1:
  return 2 * a;
label2:
  return temp;
}

In this modified code, we declare all the variables a, b, and c at the beginning of the function before any goto statements. For the goto statement in the first if condition, we don't need to declare any new variables, so we can simply jump to the appropriate label. For the goto statement in the second else if condition, we declare a new variable temp before the goto statement, and then jump to the appropriate label. Finally, we declare the variable b before the final return statement and then return its value.

By following this approach, we ensure that all variables are initialized before any goto statements are executed, and we avoid the error of jumping past variable initialization.

ro4i7 avatar Mar 11 '23 15:03 ro4i7

Hello @parth-07,

I ran the attached code and did not receive any errors. I tested the code using the "f_decls3" function (the example given in the issue) and the "f_add2" function as provided in the "Gradients.c" file in the test folder.

The objective of the code was to verify the following:

1. The "f_decls3_grad" and "f_add2_grad" functions were successfully auto generated upon calling their respective clad::gradient(). These derived functions could also be called in the main() function. (See the attached code.)

2. The function generated by the "dump()" function is the same function that has been commented in the attached file. Additionally, when we simply define the "f_add2_grad" function and call it, we get the same result. Note that in this case, we do not call the clad::gradient() and TEST() macros.

auto f = clad::gradient(f_decls3);
f.dump();

3. If we call TEST() macro and define f_add2_grad() then only we get the following error.

error: definition with same mangled name 'Z11f_add2_gradddN4clad9array_refIdEES1' as another definition goto.cpp:12:9: note: previous definition is here void f_add2_grad(double x, double y, clad::array_ref _d_x, clad::array_ref _d_y) { ^ 1 error generated.

This error is to be expected because clad::gradient(...); generates its respective grad function which clashes with the manually written grad function.

I think this issue should be closed. I did not encounter the error mentioned in the issue. Can you please tell me how you were able to reproduce this error?

Shounak_test.txt

ShounakDas101 avatar Mar 12 '23 14:03 ShounakDas101

This is the output of test/Gradient/Gradients.C Screenshot from 2023-03-16 18-11-38

As it can be seen the expected result and the my output result are same. I did not encounter the error mentioned in the issue. Can you please tell me how you were able to reproduce this error?

ShounakDas101 avatar Mar 16 '23 12:03 ShounakDas101