Skip to content
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

Add support for ADTs in Viper #574

Merged
merged 56 commits into from
May 18, 2022
Merged

Conversation

amaissen
Copy link
Contributor

This PR adds support for basic use of ADTs in Viper via a Viper plugin.

amaissen added 30 commits March 11, 2022 10:45
-Added a node for the declaration
-Added a node for the constructors in the declarations body
-Both nodes have high resemblance with the definitions for Domains
-Added an AST node for the declaration
-Added an AST node for the constructors in the declarations body
-Both nodes have high resemblance with the definitions for Domains
…Nodes

-Note the ADT top-level declaration might be translated before its constructors, since we might need that information. We will handle this in a later step
-As for the PDomainType we specify different kind of type. Namely Unresolved, Adt and Undeclared, which we need for resolving
-Most of the implementation is borrowed from PDomainType, since they are similar
-As for PDomainFunction we have to make some adaptions to the method withChildren such that it can properly be used. (e.g needed if we use some StrategyBuilder)
-Basically we have to make sure that 'adtName' is handled correctly
-Currently, the only way it works, is with the Reflection approach. A simplified implementation is desired and provided in a later step
-Since the syntax of domain types is identical to the syntax of adt types they can not be distinguished, hence we translate each PDomainType to an PAdtDomain type if a corresponding ADT declaration exists
-Currently we do this for occurences in signatures of functions, adt constructors and method. In later step we also need to do this for variable declarations, built-in type declarations, etc.
… types

-For ADT types we have to check if there is a corresponding declaration (this is currently redundant because we transform PDomainTypes to PAdtTypes only if there is a corresponding declaration, anyway this might change)
-For ADT constructors we have to type check all its arguments
-For ADT declarations we have to type check all its constructors
-Create a class for the ADT type that hold the necessary information we need in a later step to encode the ADT type as a domain type
-Handle ExtensionMember in showMember
-Handle ExtensionType in showType
-This enhancement allows the plugin developer to implement an own prettyPrint also for ExtensionMember and ExtensionType. Previusoly this was only possible for ExtensionStmt and ExtensionExp
-Observe that we need to translate the domain signatures first, since other members like domain functions, methods and ordinary functions might depend on the domain signatures
-Signatures of extensions need to be treated similarly as domain signatures, as they might introduce a new top-level declaration that behaves similar as domains (e.g ADTs). Accordingly, their signatures must be translated before signatures of domain functions, methods, functions, etc.
-Note that we translate extensions signatures after domain signatures since there might be extensions that work like methods and functions, and hence might need the domain signatures.
-Implement the translation for PAdtType to AdtType
-Adjust translation flow to respect changes of the plugin infrastructure
-Implement a much simpler solution for withChildren
-Since both classes have a special second argument list, we need to handle them correctly
-Despite handling the case when node is a Map, the rewriting of Maps does not work correctly. This is because Tuple's are not handled, which stops the recursion and prevents rewriting.
-Added a case for Tuple, that solves the described issue.
-Make use of the fact that all nodes are Rewritable's, so we can traverse the entire tree using a StrategyBuilder
-Add functionality to encode ADT declarations, constructors and types
-Use the AdtEncoder to encode ADT related AST nodes to normal AST nodes before the AST is passed to the verifier
-Implement first version of type checking for ADT operation applications
-Additionally we add a companion object s.t the return type is set correctly
-Additionally, missing methods of AdtType are implemented
- Contains utility to avoid name conflicts when adding tag function declarations and destructor function declarations.
-This includes adding injectivity and exclusivity axioms, adding an encoding for destructors and a tag function for discrimination
-Disallow duplicate argument identifiers of constructors, otherwise we destructors can not be distinguished with the current design of ADT's
…t-extension

# Conflicts:
#	src/main/scala/viper/silver/parser/Translator.scala
# Conflicts:
#	src/main/scala/viper/silver/ast/utility/rewriter/Strategy.scala
amaissen added 24 commits March 16, 2022 10:43
-Refactor PConstructorCall for potential code reuse
-Additionally provide companion object to correctly set the destructor application given the name and the corresponding ADT.
-Since the syntax of field accesses and destructor applications can not be distinguished, we need to transform PFieldAccess's to PDestructorCall's if there is such a destructor
-Additionally add a getTag function that maps adt constructor's to its tag identifier
-Implement the type-checking for discriminator calls
-Implement the translation to an AST node for discriminator calls
-Note that (true or A or B ) is not the same as (A or B)
-But (false or A or B ) is the same as (A or B)
-There was a bug that a new mapping for a name is added, despite already having a mapping for that name
-There might happen that 'name' corresponds to an identifier of a method, function, etc. which caused an exception.
-Only allow PFormalArgDecl's as PAdtConstructor arguments
-Only allow LocalVarDecl's as AdtConstructor arguments
-Add the possibility to disable ADT plugin
-In commit f55e455dac752fb47ddfa98504ae91bdc199e1e thee ADT plugin was added to the default plugins, hence the number of defualt plugins is now 3.
Copy link
Member

@Aurel300 Aurel300 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Whitespace and formatting is inconsistent (in small ways) in many places. Other than that I wonder about the adt syntax: what about domain adt ...? Is adt now a keyword? Similarly I found the deriving syntax a bit strange.

@@ -111,6 +111,13 @@ abstract class SilFrontendConfig(args: Seq[String], private var projectName: Str
hidden = true
)

val adtPlugin = opt[Boolean]("disableAdtPlugin",
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I know this is the same as the termination plugin above, but shouldn't this rather be enableAdtPlugin, true by default?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@Aurel300 I don't have a strong opinion here. If you have, please bring it up in a Viper meeting. Or simply change the implementation when nobody is looking ;-)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Imo, the bigger issue with disabling default plugins is that they are actually still loaded. Disabling of the plugin's functionality happens by returning from the hooks without doing anything. I adopted this from the termination plugin, personally I don't like this solution. :)

Comment on lines +278 to +281
override def verifyExtExp(): VerificationResult = {
assert(assertion = false, "AdtDiscriminatorApp: verifyExtExp has not been implemented.")
Failure(Seq(ConsistencyError("AdtDiscriminatorApp: verifyExtExp has not been implemented.", pos)))
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this an open TODO?

Copy link
Contributor Author

@amaissen amaissen Apr 26, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No, verifyExtExp() is a method provided by the plugin infrastructure, but actually never used anywhere. If, this method will be used/called in future, the error should happen, since it should not be necessary to call it for new expression added with the ADT plugin.

@mschwerhoff
Copy link
Contributor

Whitespace and formatting is inconsistent (in small ways) in many places.

@amaissen Please fix, if still possible.

Other than that I wonder about the adt syntax: what about domain adt ...? Is adt now a keyword?

@Aurel300 Yes, when the plugin is in use. The syntax has been ran by Peter.

Similarly I found the deriving syntax a bit strange.

@Aurel300 The deriving system is a proof of concept, and likely to change.

@mschwerhoff mschwerhoff merged commit 73ce0e7 into viperproject:master May 18, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants