The Core Language of Aldwych Matthew Huntbach Department of Computer Science Queen Mary, University...

Preview:

Citation preview

The Core Language of Aldwych

Matthew Huntbach

Department of Computer Science

Queen Mary, University of London

Origin

• Aldwych was originally a pre-processor for a concurrent (committed choice) logic programming language:

“Aldwych turns into Strand”

• Strand 1989 BCS IT Award winning system

What’s Wrong with Concurrent Logic Programming?

• Too many competing systems• Looks like Prolog but doesn’t behave like

Prolog• Lack of structure - really very low level• Producer-consumer relationship on

variables crucial to understanding but not a syntactic issue

• Pulled down by 5th Generation failed hype

What’s Right with Concurrent Logic Programming?

• Naturally concurrent• Declarative with simple (?) operational

semantics• Handles interaction with ease• Strongly influential on development of

Erlang - now marketed as the most successful commercial functional language

Stream AND-parallel Programming

• Computations communicate through shared variables

• A variable becomes bound to a tuple containing 0 or more further variables

• Once a variable is bound, its binding never changes (no mutability, no backtracking)

• Variables in a tuple may be bound later than the variable bound to the tuple

Concurrent Computation

• A procedure is a named model set of rewrite rules• A computation is described by a set of rewrite

rules, with fresh variables for each instance• A computation suspends until its arguments are

bound sufficient for full pattern–matching on at least one rule

• There are no other restrictions on concurrent processing

Rewrites

• A computation rewrites to further computations and/or assignments

• Assignments may be to variables given as arguments, to variables which are part of argument tuples, and to local variables

• Local variables made part of global environment on rewrite

• Assignments may spark more rewrites

Aldwych Core Language

• Introduces less verbose syntax

• Syntax enforces exactly one writer per variable

• Syntax makes clear where writer is

• Language is subset of full Aldwych

• Full Aldwych transforms to Core Aldwych through defined transformation rules

Core Language Syntax and Operational Semantics

• This paper gives a complete set of rules which describe a correct Core Language program

• It gives a complete set of reduction rules which describe the operational behaviour of a program

• The operational rules are indeterminate in order of application, they could give lazy, eager or parallel reduction

Reduction Rules

• Break down pattern matching into individual variable tests and variable to variable assignments

• If a variable test matches an external variable assignment, knock it off

• If all tests knocked off, commit to rule• If a variable test does not match an external

assignment, discard rule

Interaction

The boundary between an Aldwych program and the outside world is indeterminate. A computation interacts with the rest of the world only through its input variables, over which whose contents it has no control, and its output variables over which whose content it has full control. There is no necessity these variables connect only to Aldwych computations.

Why Core Aldwych is Not Functional Programming

• There is a distinction between data and program, variables may only be bound to tuples, function are not first-class citizens

• There is the possibility that a computation may rewrite using more than one rule, the operational semantics impose no ordering on which rule to choose (“don’t care” non-determinacy)

• Aldwych has “back-communication”

Futures and Back-communication

• If a computation binds a variable to a tuple with further variables, and computations it rewrites to write to those variables, a reader of the top-level variable may use its component variables as “futures”

• Aldwych allows a computation to bind a variable to a tuple whose reader becomes the writer to (some of) its component variables

Linearity

• If the reader of a variable becomes the writer of some of the variables in the tuple to which it is bound, it must be the sole writer, to preserve the single-assignment property.

• So only a variable known to be linear (exactly one reader) may be bound to a tuple with back-communication variables

Aldwych Processes

An Aldwych computation is transient: it rewrites to further computations and assignments which do not retain any common identity. However, a recursive call can be considered a continuation of a process, with changes in corresponding arguments representing changes in state. Full Aldwych has syntax which reflects this.

Aldwych Channels

If a variable is bound to a tuple containing a message and a further variable, and this further variable takes the place of the original in a recursive call, it can be considered a representation of a process sending the message to the original variable’s reader on a continuing channel. Similarly the reader replaces the original variable by the further variable in a recursive call.

Replying to messages

If the channel is represented by a linear variable, the message sent on it may itself be a tuple containing a back communication variable. This variable is then incorporated into the recursive call, or into a computation feeding into the recursive call, representing a process sending a message and receiving a reply.

Aldwych Objects

• The output of a stream of messages (possibly with reply variables) represents the input of an object, and vice-versa

• Multiple streams of messages may be merged while retaining the linearity property. This can be used to represent references to an object being duplicated.

Object with two references

client1(…)->(…,Alias1,…),

client2(…)->(…,Alias2,…),

merge(Alias1,Alias2)->Object,

server(…,Object,…)

Merge code#merge(In1,In2)->Out{ In1=cons(Mess,In11) ||

Out=cons(Mess,Out1),merge(In2,In11)->Out1;

In2=cons(Mess,In21) || Out=cons(Mess,Out1),merge(In21,In1)->Out1;

In1=empty || Out<-In2; In2=empty || Out<-In1}

Stream merger (full Aldwych)

#merge(in1,in2)<

{

{in1,in2}?m | ^m;

in1=[] ||> in2;

in2=[] ||> in1

}

Bank Account Object

#account(bal,Chan){ Chan=cons(deposit(amount),Chan1) || bal1<-bal+amount, account(bal1,Chan1);

Chan=cons(withdraw(amount),Chan1) || bal1<-bal-amount, account(bal1,Chan1);

Chan=cons(balance->reply,Chan1) || reply<-bal, account(bal,Chan1); Chan=empty ||}

Bank Account Full Aldwych

#account(bal<-0)~{ deposit(amount) | bal<-bal+amount; withdraw(amount)- [ amount>bal |>=false; : |>=true, bal<-bal-amount ] balance-|>bal;}

Factorial Full Aldwych

#fact(n)<

<(acc<-1)

{

n>1 | acc<-acc*n, n<-n-1;

: ||> acc

}

Functional Programming in Full Aldwych

• A function is an immutable object with one method - apply

• Juxtaposition F N is taken to mean F.apply(N)

• Curried functions are object factoriesA little more syntactic sugar makes pure

functional programming a subset of Aldwych

Factorial using Fold#fold [F n xs]<{ xs?x |>F x <; : ||>n;}

#fact(n) <==> fold() ($[x y]<==>x*y) 1 ints(n);

#ints(n)<{ n=0 ||>[]; : | ^n,n-=1}

Interaction with World

What’s inside an object doesn’t have to be Aldwych so long as it presents an Aldwych interface. So Aldwych objects may be:

• Mutable arrays

• Input/output

• GUI components

Erlangrpc(Pid, Query) ->

Pid! {self(), Query),receive

{Pid, Reply} ->Reply

end.

areas() ->receive

{From, {rectangle, Width, Ht}} ->From ! {self(), Width*Ht},areas();

{From, {circle, R}} ->From ! {self(), 3.14159*R*R),areas()

end.

% Pid = spawn(fun area_server2:areas/0).% a = area_server2:rpc(Pid, {circle, 5}).

Aldwych

#areas~{ rectangle(width,ht)-|>width*ht; circle(r)-|>3.14159*r*r;}

% Pid<-areas(), a<-Pid.circle(5);

Achievement 1

Type system of full modes and linearity added to committed choice concurrent logic programming. Enables it to be fully described operationally by simple reduction rules, and also efficiently implemented, aids partial evaluation, gives better syntax.

Achievement 2

Features of imperative, object-oriented, communicating process, functional languages easily described via transformation rules into the underlying core language

Achievement 3

Some tricky programming language issues resolved:

• Naturally concurrent and interactive

• Dynamic communications topology

• Efficient mutable arrays incorporated into functional framework

The Next 700 Concurrent Programming Languages?

• In 1966 Landin described a “family of languages” called ISWIM which translated to underlying applicative expressions:“Most programming languages are partly a way of expressing things in terms of other things and partly a basic set of given things. The ISWIM system is a byproduct of an attempt to disentangle these two aspects in some current languages.”

• Aldwych does this for concurrent languages

Recommended