2

I am writing a parser for a metalanguage to be run in the browser. The metalanguage is blocking, but needs to be converted to nonblocking in the interpreter due to the limitations of javascript.

For example, the metalanguage code might look something like

1. dosomething(4)
2. dosomethingelse(1)
3. dosomething(7)
4. goto 2

with the functions implemented in javascript as

function dosomething(n, callback) {
  ... // do something with n
  setTimeout(callback, 1000);
}

function dosomethingelse(n, callback) {
  ... // do something else with n
  setTimeout(callback, 1000);
}

Without the goto statements, this would be easy to compile to javascript and then eval. However, I have no clue how to implement the gotos. Any help is appreciated.

8
  • unconditional goto is just a while loop Commented Dec 28, 2014 at 3:55
  • how do you interpret a blocking while loop in a nonblocking language? Commented Dec 28, 2014 at 3:56
  • I do not understand this question. Commented Dec 28, 2014 at 3:57
  • do you want to wait for all your asynchronous dosomething calls to complete and then do a goto? Commented Dec 28, 2014 at 3:59
  • 1
    I usually do it using promises. Like github.com/kriskowal/q Commented Dec 28, 2014 at 4:00

2 Answers 2

2

As others have said, check out Promises. This tutorial really helped me out for getting started with them, hopefully it helps you too. https://spring.io/understanding/javascript-promises

Sign up to request clarification or add additional context in comments.

Comments

1

Use yield to make functions you can pause and then regenerator to run it in older browsers:

First, we convert dosomething(4) in your language into:

function doSomething(n, callback){
    setTimeout(function(){ callback(null,true); }, n);
}

Note the node err-back convention - callbacks take two arguments - the first is an error and the second is the return value.

Then - you can convert them to promises easily:

var doSomething = Promise.promisify(doSomething); // using bluebird.

Now, when they return promises- you can wrap lines with yields:

Promise.coroutine(function*(){ 
    yield dosomething(4);
    yield dosomethingelse(1);
    yield dosomething(7);
});

You will need to call addYieldHandler in order to deal with yielded non-promise values. This will execute them "synchronously" waiting for each promise to resolve before starting the next. Finally use regenerator to convert your code into something ES5 browsers can run (Since yield only works in FF and in Chrome under a flag atm).

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.