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

Naive state #235

Merged
merged 17 commits into from
Jul 26, 2023
Merged

Naive state #235

merged 17 commits into from
Jul 26, 2023

Conversation

b-studios
Copy link
Collaborator

Here I am experimenting with a different representation of state that is easier to monomorphize.

@b-studios
Copy link
Collaborator Author

b-studios commented Feb 24, 2023

The PR is starting to look solid. I implemented the new local state for all backends, except LLVM (and machine for that matter).

It would be very valuable to get feedback from @marzipankaiser, @serkm, and @phischu on how to proceed with machine. You don't have to look at the whole PR, the essential change is this in lifted.Tree:

-  case State(id: Id, init: Expr, region: Symbol, ev: Evidence, body: Stmt)
+  // allocates into a (type-monomorphic?) region.
+  // e.g. var x in r = init; body
+  case Alloc(id: Id, init: Expr, region: Id, ev: Evidence, body: Stmt)
+
+  // creates a fresh state handler to model local (backtrackable) state.
+  // e.g. state(init) { (ev){x: Ref} => ... }
+  case Var(init: Expr, body: Block.BlockLit)

https://github.com/effekt-lang/effekt/pull/235/files#diff-0555635c10275b9368035de048ce1782d57df07d499fc1671fb799d45586aa0bR125-R132

For now, I changed the test files to use an explicit region instead of local mutable state.

-def main() = {
-    var n = 0
+def main() = region r {
+    var n in r = 0

https://github.com/effekt-lang/effekt/pull/235/files#diff-52c3c58f95cb33c9fbda0911bef989780e255f229c04410a7f5e94d98320429cL18-L19

but this is only a temporary fix, since I do not translate local mutable state to machine:

https://github.com/effekt-lang/effekt/pull/235/files#diff-2bc35700065c09eb82c800736c2625a2516ddb669bb20acbfce3d9af8dbca683R256-R258

Any feedback on how to proceed with machine is very welcome! You can also look at how the other backends implement it, of course.

@b-studios b-studios marked this pull request as ready for review February 24, 2023 10:59
@phischu
Copy link
Collaborator

phischu commented Apr 6, 2023

@serkm I have yet another idea for the implementation of local mutable state.

It crucially relies on going back to the "copy-on-share" strategy. This means that shareStack immediately deep-copies the stack instead of bumping the reference count. This way every reference is to a stack indeed is always unique. I don't remember why we changed that but there was a reason. Note that this only ever happens when the user mentions the resumption twice.

Now when we want to create a local mutable reference we push a frame that contains the value. References are offsets from the bottom of the stack. Getting the content of a reference means finding the correct stack using evidence and then reading the value at the offset. Setting the content of a reference finds the location in the same way and directly writes to it on the stack.

For arenas we could do the same except that the frame contains a reference to the arena and erase and share and return do the correct thing with it.

A corner case is allocating into the global region which would create a reference on the heap.

This could also fix #244.

@b-studios b-studios merged commit 7f3626f into master Jul 26, 2023
@b-studios b-studios deleted the naive-state branch January 28, 2024 11:53
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.

None yet

2 participants