HN user

jpolitz

451 karma

https://jpolitz.github.io

Posts1
Comments110
View on HN

As far as I remember (maybe Arnar or Úlfar or another of the authors would have a different memory, though) we just wanted a “cool cookie” name. We knew about the -oon/-on distinction and liked the sound of -oon.

I view it as a mild plus that the confusion around the name has educated so many about confectionery taxonomies.

Various flavors of a course based on "An Incremental Approach to Compiler Construction" [1] have most or all materials free online, some with excellent notes. Taught at UCSD, Northeastern, Swarthmore College:

https://ucsd-cse131-s18.github.io https://course.ccs.neu.edu/cs4410/lec_let-and-stack_notes.ht... https://ucsd-progsys.github.io/131-web/lectures/05-cobra.htm...

(I designed the original version, though it's improved a lot in the past few years)

[1] http://scheme2006.cs.uchicago.edu/11-ghuloum.pdf

It's worth noting that Stopify itself isn't an editor or IDE as the title suggests.

Stopify is a JavaScript -> JavaScript compiler, implemented as a Babel transform, that enables pausing and restarting control operators for JavaScript programs.

A lot of the comments note the rich history of systems for debugging and execution control. Stopify's goal is to enable those kinds of systems, efficiently, while constrained by the browser's execution model.

Infinite Loops 9 years ago

Nice! Something like this is super-important for user experience.

This is a problem we've thought a lot about with Pyret, and have different concrete solutions. Rather than use heuristics that turn long-running computations into errors, we capture continuations and yield to the browser periodically. This allows long-running computations to eventually complete, while allowing the user to fully interact with buttons and the page while it's happening. This generalizes to nice abstractions for functional event loops and ways to manage asynchronous APIs for novices.

The Doppio JVM and the Whalesong compiler for Racket have similar underlying approaches.

It's quite a bit of effort to work around this inherent limitation of the browser's evaluation model for web-based IDEs!

There is the Canine Good Citizen test (http://www.akc.org/dog-owners/training/canine-good-citizen/), and the more stringent Community Canine Good Citizen Test (http://www.akc.org/dog-owners/training/akc-community-canine/).

I've used this informally as justification before when renting housing and bringing my dog to work (she's a plain CGC).

I think there's value in having these be more recognized. I especially wish they were by airlines.

Note that this isn't the same thing as the issue with service animals, where credentials are at a totally different standard, and more important than where I can bring my pet.

It's worth mentioning that Pyret followed this path. It was originally a Racket #lang. Once we got the design off the ground and decided to primarily target the browser, we wrote a new implementation in JavaScript and Pyret. The tools in Racket (including ragg [http://docs.racket-lang.org/ragg/]) were invaluable in getting started quickly.

This archives the state of the system when we made the switch:

https://github.com/brownplt/pyret-lang/releases/tag/pyret-20...

Some things, like the grammar (https://github.com/brownplt/pyret-lang/blob/5f22ec7c8affde15...) have survived largely intact from that prototype for years.

Cool to see Whalesong up here; it's worth pointing out the incredible effort put into making this really work for Racket, _including_ support for continuations. That is, you can compile a Racket program that uses call/cc and friends to JavaScript.

This is huge because with powerful control operators like call/cc, you can simulate pre-emptive multithreading within a browser tab. This gives the runtime:

- The ability to simulate synchronous functions backed by asynchronous library calls (e.g. apparently make a synchronous request to a URL from the program's point of view, but have it backed by an AJAX request) - The ability to add a pause and/or stop button to an IDE within a browser tab, even if the program goes into an infinite loop

In fact, work on Whalesong (and a few earlier prototypes) more or less run the Racket-using parts of www.wescheme.org which 10s of thousands of students use each year.

Most x-to-JS implementations don't have this level of feature richness; Doppio and GopherJS are two that have similar levels of execution control.

I worked in the same office as dyoo while he was implementing Whalesong about 5 years ago, and learned a ton from him and from the system. Pyret and code.pyret.org directly built on some of the code for the "framework to program the web in functional event-driven style" in reactors (https://www.pyret.org/docs/latest/reactors.html). Whalesong's APIs for programmatically saving and restoring the stack inspired the ones we use in Pyret, as well.

My compilers course has all the lectures recorded, and has starter code for all the assignments provided. It provides all the parsers, and focuses on the backend, including memory management and various details of value representations.

This is just my materials, I don't have an associated platform with verification/certification. However, some folks from HN have previously done the course and emailed me after, and seem to have gotten some value out of it.

https://cseweb.ucsd.edu/classes/sp17/cse131-a/

https://podcast.ucsd.edu/podcasts/default.aspx?PodcastId=401...

https://github.com/ucsd-cse131-sp17

Earlier offering:

https://www.cs.swarthmore.edu/~jpolitz/cs75/s16/

I think this has lots of potential. I have thought before that if I could make two changes to Slack (which I already think is pretty great), they would be:

1. Hitting "Enter" doesn't send the message. This encourages writing actual paragraphs in response, rather than sending fragments of sentences

that can be interrupted across multiple lines

because you're not really sure if you've finished your sentence just yet

oh and you thought of one more thing so everyone else please take this line into consideration as well

Of course, you might say "train your team to not do that." Sure. But I'd rather use a tool that doesn't require breaking (perhaps reasonable) habits. And if communication shouldn't be through short bursty chunks by default, why make that the easiest thing to do?

2. Make threads more of a default way to respond, and make thread comments first-class citizens. Presented with the UX of Slack, it's really hard to move yourself towards using threads because the easiest way to respond to things is to type and hit enter. Also, threads live in their own "All threads" space, not organized by channel. Thread comments aren't first-class citizens like regular chat is because they can't have files attached, be posts or snippets, etc, so sometimes it feels like I actually _lose_ functionality by starting a thread.

Twist looks like it has what I love about Slack – good for newbies to join in and see organized, curated history (I can't show new folks _my_ inbox labels and organization, or spin up a new channel on a mailing list for each topic we want to discuss), good for lurking on projects that aren't your own but are related, and has emoji responses for celebration, quick feedback, and commiseration.

Is there a particular piece of insight from that paper that indicates a mistake in the design of Viper? I love erights' work and don't doubt that there is a lot to be learned from it in this context, but some guidance on how to apply it here would help.

I'm basing my course this quarter on one from Northeastern, where Ben Lerner has written a pretty impressive set of notes, the latter half of which are data structures content:

http://www.ccs.neu.edu/course/cs2510/Lectures.html

The NEU course assumes that students have taken How to Design Programs in Racket, so the early notes refer to Racket syntax. I'm working on notes for a Racket-less introduction that uses the same tools for my course right now:

https://cseweb.ucsd.edu/classes/sp17/cse11-a/Lectures.html

These notes also rely on a particularly good testing library that is capable of doing things like comparing objects for structural equality without requiring that students define a .equals() method first, which can be incredibly helpful for getting off the ground.

Consider Bootstrap:

http://www.bootstrapworld.org/

Bootstrap 1 is computing tied to algebra concepts, targeted at the middle school age group (US grade 6-8). Students learn things like order of operations and what a function is while building up their own game. The curriculum has lots of activities that show students how to use code to generate images early on, which gives something immediately interesting and tangible to work with.

It runs in a stock browser (lots of students do Bootstrap on inexpensive Chromebook models), has a great support mailing list, and is used in schools across the US already. It also explicitly helps with math skills, which can be doubly useful in preparing for other STEM topics in the future.

how it can turn recursive structures like expressions and statement blocks into linear sequences of instructions

I think this is one of the key concepts in a compiler, yet I don't think it has much to do with parsing.

Parsing (in a compiler) is the act of taking a linear sequence of characters or tokens, and turning them into a rich AST structure.

The back end of the compiler is what takes this recursive structure and flattens it out into a linear sequence of instructions that "mean" the same thing as the tree.

Parsing is critical, of course, for building a working compiler. But I think not focusing on surface syntax gets to the key recursive-to-linear insight you mention more directly!

Thanks, this a terrific reference that I hadn't seen!

I see a few interesting contrasts with the my course off the bat:

- I skipped forcing students to implement uniquifying variables early on. I wanted to get from source to assembly as quickly as possible, but this may have been a worthwhile step to force, since it teaches some valuable lessons.

- I had them implement ANF (AKA flatten in those notes) in a different style, because I was used to it. The style in that textbook is better (Ranjit Jhala at UC San Diego also pointed this out when he taught a version of the course), where an expression is turned into a list of bindings and a final expression, rather than using a continuation-passing ANF algorithm as I did.

- The linked book has instruction selection with semi-abstract addresses followed by a "patching" phase, to avoid instructions that, say, move from stack location to stack location. This is cool, but is a few more steps than I wanted to get into for the simplest compilers. I didn't pursue as structured an approach, and instead gave a simple description to the first few "compile" functions we wrote:

    Generate a list of instructions that gets the "answer"
    for this expression into EAX
This avoided detailed discussion of instruction selection, abstract vs. concrete addresses, etc, in the beginning, and just made students generate some instructions that work. We quite quickly after that needed to start talking about issues of clobbering other expressions' state, and finding unique locations for variables, but then those just became constraints on "getting the answer into EAX" correctly. In fact, I found that repeating the mantra "get the answer into EAX" was a nicely actionable way to go about generating instructions, and letting students get started when we introduced a new feature (to compile it, we need to get the answer into EAX!)

After we'd done this a few times, we had the shared vocabulary to realize that answers don't _always_ have to go to EAX (the compiler can be parameterized over where the current answer should go), and not every constant's value needs to flow through EAX in order to get to its variable's home, etc. But these were refinements on top of our dead simple strategy.

Just some thoughts I had while perusing the first few chapters here. Thanks again for sharing!

I love this paper! I built my compilers course out of the ideas in it:

https://www.cs.swarthmore.edu/~jpolitz/cs75/s16/index.html

I think the incremental approach is terrific, because it allows you to get to a program the emits assembly and builds a working binary in week one. The first thing this does is give a concrete example of what "a compiler" is. The second is to provide a great foundation for discussing static vs. dynamic and what decisions are made at compilation time vs. runtime, without needing a full implementation. These concepts are not obvious (e.g. when can and should a check for unbound ids happen? What about divide by zero, or overflow, or type mismatch?), and deserve to be carefully taught and considered.

This lets the course build up a new feature, from front-to-back, each week or two, and consider its implications on the whole pipeline each time.