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

Simplify BindingsMap by instead relying on StaticModuleScope for atom type resolution #11955

Conversation

radeusgd
Copy link
Member

@radeusgd radeusgd commented Dec 31, 2024

Pull Request Description

  • Removing AtomTypeInterface - it was a useful temporary hack, but in the longer term it seemed to not really solve the problem we had.
  • Now storing the types of atom constructor arguments in StaticModuleScope, so I can remove the Expression from BindingsMap. I think that storing IR inside of metadata attached to said IR (which was the reason for introducing cycles) was a bad idea after all.
  • Thus, the TypeRepresentation is greatly simplified - it no longer refences complicated objects like AtomTypeInterface (which had a nice API but ugly internals, and the internals were affecting serialization). Now TypeRepresentation becomes just plain data, a much simpler representation and I think it is closer to what it was supposed to be from the beginning.

Important Notes

Checklist

Please ensure that the following checklist has been satisfied before submitting the PR:

  • The documentation has been updated, if necessary.
  • Screenshots/screencasts have been attached, if there are any visual changes. For interactive or animated visual changes, a screencast is preferred.
  • All code follows the
    Scala,
    Java,
    TypeScript,
    and
    Rust
    style guides. In case you are using a language not listed above, follow the Rust style guide.
  • Unit tests have been written where possible.
  • If meaningful changes were made to logic or tests affecting Enso Cloud integration in the libraries,
    or the Snowflake database integration, a run of the Extra Tests has been scheduled.
    • If applicable, it is suggested to paste a link to a successful run of the Extra Tests.

@radeusgd radeusgd force-pushed the wip/radeusgd/type-checker-atom-type-in-static-module-scope branch from 31934b9 to 919086a Compare January 2, 2025 18:05
Comment on lines -598 to -606
case class Argument(
name: String,
hasDefaultValue: Boolean,
typReference: Reference[Expression]
) {
def typ(): Option[Expression] = Option(
typReference.get(classOf[Expression])
)
}
Copy link
Member Author

Choose a reason for hiding this comment

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

This removes the infamous cycle from the IR - the Expression holding the type of the constructor is no longer needed.

That's because we process this type Expression in StaticModuleScopeAnalysis and save it in StaticModuleScope metadata as an already processed TypeRepresentation - so it is no longer IR that is stored inside of metadata, but a simpler data structure representing our types.

Copy link
Member

Choose a reason for hiding this comment

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

This is a minimal change to the BindingsMap. It removes typ() which wasn't used by regular execution at all - e.g. everything shall keep functioning...

Copy link
Member Author

Choose a reason for hiding this comment

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

Yep, typ() was only added for the type inference and now it is obsolete thanks to StaticModuleScope, so it can be removed. In a way - I revert BindingsMap to be like before my earlier changes.

registerFieldGetters(scopeBuilder, atomTypeScope, typ);
}

private TypeRepresentation buildAtomConstructorType(
Copy link
Member Author

Choose a reason for hiding this comment

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

This is mostly moved from the TypeResolver.

@@ -51,8 +51,7 @@ public QualifiedName getAssociatedType() {
* <p>Instances that are assigned this type are built with one of the available constructors, but
* statically we do not necessarily know which one.
*/
record AtomType(QualifiedName fqn, AtomTypeInterface typeInterface)
implements TypeRepresentation {
record AtomType(QualifiedName fqn) implements TypeRepresentation {
Copy link
Member Author

Choose a reason for hiding this comment

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

Our type representation is no longer holding references to some complex AtomTypeInterface structure which internally was holding references to BindingsMap and was overall ugly.

Now the TypeRepresentation is a plain data type. The information about Atom type interface is instead encoded in the StaticModuleScope, like information about method already has been.

@radeusgd radeusgd self-assigned this Jan 2, 2025
@radeusgd radeusgd added the CI: No changelog needed Do not require a changelog entry for this PR. label Jan 2, 2025
@radeusgd radeusgd marked this pull request as ready for review January 2, 2025 19:05
@radeusgd radeusgd changed the title [Draft] Simplify BindingsMap by instead relying on StaticModuleScope for atom type resolution Simplify BindingsMap by instead relying on StaticModuleScope for atom type resolution Jan 2, 2025
@radeusgd
Copy link
Member Author

radeusgd commented Jan 2, 2025

@JaroslavTulach shall we maybe disable the support for cycles in IR persistence now?

I think we are no longer relying on it and there were issues with it from time to time so maybe we should change the code to fail on cycles and keep an eye on us accidentally re-introducing these problematic cycles?

btw. I think the cycles could have been also why @Akirathan could not use equality for comparing IR and had to resort to identity. I'm not sure if we had any other cycles than this one? If not, maybe we could try to come back to equality over identity then.

Copy link
Member

@JaroslavTulach JaroslavTulach left a comment

Choose a reason for hiding this comment

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

I don't see any problem with the changes into BindingsMap.

Comment on lines -598 to -606
case class Argument(
name: String,
hasDefaultValue: Boolean,
typReference: Reference[Expression]
) {
def typ(): Option[Expression] = Option(
typReference.get(classOf[Expression])
)
}
Copy link
Member

Choose a reason for hiding this comment

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

This is a minimal change to the BindingsMap. It removes typ() which wasn't used by regular execution at all - e.g. everything shall keep functioning...

@radeusgd radeusgd force-pushed the wip/radeusgd/type-checker-atom-type-in-static-module-scope branch from 4e6cd00 to 5f515ff Compare January 7, 2025 17:59
@radeusgd radeusgd merged commit 6b0ce25 into wip/radeusgd/9812-infer-method-calls Jan 7, 2025
29 of 31 checks passed
@radeusgd radeusgd deleted the wip/radeusgd/type-checker-atom-type-in-static-module-scope branch January 7, 2025 18:14
@JaroslavTulach
Copy link
Member

btw. I think the cycles could have been also why @Akirathan could not use equality for comparing IR and had to resort to identity. I'm not sure if we had any other cycles than this one? If not, maybe we could try to come back to equality over identity then.

change the code to fail on cycles

It doesn't cause us much problems/slowdown on read, especially when cycles aren't present. So it doesn't have any priority. I'd like to avoid an issue laying around in new/backlog that would need to be ignored every planning meeting.

mergify bot pushed a commit that referenced this pull request Jan 8, 2025
…11399)

- Implements #9812
- Allows us to propagate type inference through method calls, at least in a basic way.
- Adds a 'lint warning': when calling a method on an object of a known specific (non-`Any`) type that does not exist on that type, a warning is reported, because such a call would always result in `No_Such_Method` error at runtime.
- `Any` has special behaviour - if `x : Any` we don't know what `x` might be, so we allow all methods on it and defer to the runtime to see if they will be valid or not.
- This check is not proving correctness, but instead it's only triggering for 'provably wrong' situations.
- Includes changes from #11955:
- removing obsolete `AtomTypeInterface`,
- simplifying `TypeRepresentation` to be a plain data structure,
- and removing a cycle from IR in `BindingsMap` in favour of relying on `StaticModuleScope`.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
CI: No changelog needed Do not require a changelog entry for this PR.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants