-
Notifications
You must be signed in to change notification settings - Fork 58
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
copilot-c99
: Allow using same trigger name in multiple declarations
#296
Comments
Indeed, that is an error in the spec. At present, we consider it an error whose detection is delegated on the C compiler. If you consider the process of compilation as indivisible (Haskell -> running -> GCC), then the error is being caught. What happens is that it is not caught in the first stage, it is caught in the third (when you try to compile the C code). |
I take that back. In principle, it should be an error only if the arguments were different, but not if they are the same. |
I took a quick stab at this. Avoiding multiple declarations of the handler functions if they have the same arguments is easy to do. Avoiding multiple declarations of the arguments or argument generation functions is a bit trickier. There are two potentially orthogonal improvements to add to Copilot: 1) avoid multiple declarations of the same generation functions (this connects to #297), and 2) use different names for arguments to the same handling function when they come from different triggers with the same handling function name. |
I tried this again and I have a crude implementation that seems to work. There's an architecturally cleaner way of structuring the code (that's way I mean by crude). I don't want to not rush putting this in the Jan 7, 2024 release; I'd rather discuss it well before it's merged. We'll talk about it next week during our next planning meeting. If we can, we'll add this to Copilot 3.19, to be released on March 7, 2024. I'll keep you updated. |
We just had our planning meeting and this issue is likely to be included in the next release. You should see an update on this in a few days. |
Description The current implementation of Copilot does not allow using the same trigger handler name multiple times, since the C99 backend produces multiple repeated declarations, which is invalid. So long as the types do not change, or so long as the target language allows for method/function overloading, then the Copilot spec should accept them. Type
Additional context None. Requester
Method to check presence of bug Not applicable (not a bug). Expected result Copilot accepts specs where there are two triggers with the same name, so long as the types of the arguments (and their arity) is the same. Desired result Copilot accepts specs where there are two triggers with the same name, so long as the types of the arguments (and their arity) is the same. Proposed solution Modify Further notes None. |
copilot-c99
: Allow using same trigger name in multiple declarations
Supporting multiple calls to the same trigger has (in my opinion) one major drawback. In Copilot we basically consider triggers to be the output of a program. Having multiple triggers call the same function means that we have a single output referred from multiple places. This can make the code less readable, and is up to the user to structure it a nice way. On the other hand, I am pretty sure that allowing multiple definitions do not change the semantics of Copilot anyway (under the limitation that we only allow reuse of the trigger with same arity and argument types). For example: (type annotations omitted for brevity) trigger "f" (a > 1) [arg 123]
trigger "f' (b > 10) [arg 456] could be written in the current version of Copilot as: cond0 = a > 1
cond1 = b > 10
guard = cond0 || cond1
argVal = if cond0 then 123 else 456
trigger "f" guard [arg argVal] Now, I think we can all agree that this approach is much more error-prone, so it might not be a bad idea to support multiple triggers. I think it is very reasonable to only support multiple triggers if the arity and argument types match exactly. C for example disallows / does not support overloading functions (for good reason, in my opinion). If we disallow it, I think it would be nice to have Copilot check this, instead of relying on the backend to do this. We can make our error message a lot more informative, especially because I expect it is fairly easy for the user to make a mistake/typo where the types do not match. |
Agreed. I think we can proceed with this. |
Change Manager: Confirmed that the issue exists. |
Technical Lead: Confirmed that the issue should be addressed. |
Technical Lead: Issue scheduled for fixing in Copilot 4.2. Fix assigned to: @fdedden . |
…uage#296. A backend specific representation of triggers allows us to keep track of the internal name for a trigger.
…age#296. Updates the generation of the `step` function to use unique names for the trigger related code.
…lot-Language#296. Generate the trigger guard and argument functions using the unique names.
…opilot-Language#296. The .h file should not list the same trigger multiple times, this commit removes the duplicates.
…anguage#296. Multiple triggers sharing the same name should have the exact same argument types as well, as C99 does not allow multiple function definitions.
Implementor: Solution implemented, review requested. |
…uage#296. The current implementation of Copilot does not allow using the same trigger handler name multiple times, since the C99 backend produces multiple repeated declarations, which is invalid. Consequently, the code generator assumes that trigger names are unique. To allow for multiple triggers that trigger the same handler, we need to introduce a separate construct in triggers that acts as a unique identifier. This commit introduces an internal datatype to represent a `Trigger` with a unique name that is different from that of the function called when triggered.
…uage#296. The current implementation of Copilot does not allow using the same trigger handler name multiple times, since the C99 backend produces multiple repeated declarations, which is invalid. A prior commit has introduced a representation of triggers with unique IDs, allowing us to distinguish between a monitor for one condition within a Copilot spec vs the external C function being called when the condition becomes true. This commit updates the generation of the `step` function to use unique names for the triggers.
…gers. Refs Copilot-Language#296. The current implementation of Copilot does not allow using the same trigger handler name multiple times, since the C99 backend produces multiple repeated declarations, which is invalid. Prior commits have introduced a representation of triggers with unique IDs (allowing us to distinguish between a monitor for one condition within a Copilot spec vs the external C function being called when the condition becomes true), and have adapted low-level functions accordingly. This commit adapts the top-level compilation functions in the same way, by generating trigger guards and argument functions using the unique names.
…opilot-Language#296. The current implementation of Copilot's C99 backend produces multiple repeated declarations when the same trigger is used multiple times, which is invalid C code. This commit modifies the code that generates the header file to prevent the same trigger from being declared multiple times.
…anguage#296. The current implementation of Copilot does not allow using the same trigger handler name multiple times, since the C99 backend produces multiple repeated declarations, which is invalid. Prior commits have modified the C99 backend to now allow for multiple triggers with the same handler. However, the resulting code is only valid in C if the triggers always have the same type signatures, since C does not support polymorphism. This commit adds a check to the compilation step to ensure that triggers used multiple times are always used with the same types (and, consequently, the same arity).
…uage#296. The current implementation of Copilot does not allow using the same trigger handler name multiple times, since the C99 backend produces multiple repeated declarations, which is invalid. Consequently, the code generator assumes that trigger names are unique. To allow for multiple triggers that trigger the same handler, we need to introduce a separate construct in triggers that acts as a unique identifier. This commit introduces an internal datatype to represent a `Trigger` with a unique name that is different from that of the function called when triggered.
…uage#296. The current implementation of Copilot does not allow using the same trigger handler name multiple times, since the C99 backend produces multiple repeated declarations, which is invalid. A prior commit has introduced a representation of triggers with unique IDs, allowing us to distinguish between a monitor for one condition within a Copilot spec vs the external C function being called when the condition becomes true. This commit updates the generation of the `step` function to use unique names for the triggers.
…gers. Refs Copilot-Language#296. The current implementation of Copilot does not allow using the same trigger handler name multiple times, since the C99 backend produces multiple repeated declarations, which is invalid. Prior commits have introduced a representation of triggers with unique IDs (allowing us to distinguish between a monitor for one condition within a Copilot spec vs the external C function being called when the condition becomes true), and have adapted low-level functions accordingly. This commit adapts the top-level compilation functions in the same way, by generating trigger guards and argument functions using the unique names.
…opilot-Language#296. The current implementation of Copilot's C99 backend produces multiple repeated declarations when the same trigger is used multiple times, which is invalid C code. This commit modifies the code that generates the header file to prevent the same trigger from being declared multiple times.
…anguage#296. The current implementation of Copilot does not allow using the same trigger handler name multiple times, since the C99 backend produces multiple repeated declarations, which is invalid. Prior commits have modified the C99 backend to now allow for multiple triggers with the same handler. However, the resulting code is only valid in C if the triggers always have the same type signatures, since C does not support polymorphism. This commit adds a check to the compilation step to ensure that triggers used multiple times are always used with the same types (and, consequently, the same arity).
Change Manager: Verified that:
|
Change Manager: Implementation ready to be merged. |
If we have a Copilot specification where we have multiple conditions for triggering the same function (but perhaps we are providing different arguments), then in generated C code we would have multiple declarations of trigger functions and multiple definitions of helper functions and the generated code could not be compiled without modifications.
Example
Suppose we would like to trigger the
switchOffPower(..)
function if the current of one of the components is too large. We would also like to pass the value of the signal and the index of the component to theswitchOffPower(..)
.Then the
repeated_declarations_example.h
declaresswitchOffPower(..)
twice:And
repeated_declarations_example.c
contains multiple definitions ofbool switchOffPower_guard(void)
,float switchOffPower_arg0(void)
,uint8_t switchOffPower_arg1(void)
.The text was updated successfully, but these errors were encountered: