Re: [svn:parrot-pdd] r30622 - trunk/docs/pdds/draft
Bob Rogers wrote: Allison Randal wrote: +Monkeypatching is certainly possible, but not encouraged. Cool; a new term in Allison-speak! ;-} As much as linguists love creating new words, I can't claim credit for this one: http://en.wikipedia.org/wiki/Monkey_patch More later, Allison
Re: [svn:parrot-pdd] r30622 - trunk/docs/pdds/draft
From: Allison Randal [EMAIL PROTECTED] Date: Mon, 01 Sep 2008 20:31:18 +0200 Bob Rogers wrote: Allison Randal wrote: +Monkeypatching is certainly possible, but not encouraged. Cool; a new term in Allison-speak! ;-} As much as linguists love creating new words, I can't claim credit for this one: http://en.wikipedia.org/wiki/Monkey_patch I didn't mean to imply that you had invented it, merely that you had incorporated it into your own working vocabulary. -- Bob
Re: [svn:parrot-pdd] r30622 - trunk/docs/pdds/draft
Bob Rogers wrote: +{{ There seems to be an implied basic assumption here that language +interoperability is the responsibility of the language +implementor. It is not. We cannot require that language +implementors design and implement their languages according to some +global specification. If you are not happy with that assumption, then I'm surprised you bothered to commit this draft at all, even as a starting point. Design is a process. If you don't understand what I'm getting at, then it means I haven't explained it well enough yet. And, revising the draft to help you understand also produces a design document, so it's doubly useful. Even then, surely, it must *still* be the responsibility of the language implementor not to introduce gratuitous barriers to interoperability? As a case in point, consider keyword (named) parameters in Lisp. Kea-CL does not use Parrot named parameters to implement key, partly for ANSI compliance and partly for efficiency. This currently makes it problematic (though not impossible) for other languages to call Lisp functions that accept keywords. You can either say I'm a bad boy for not fully using Parrot features and require me to design and implement ... according to some global specification, forcing me to solve the performance vs. compliance vs. interoperability tradeoff in each sub, or allow me to do my own thing internally and accept the need for glue around the edges (which in turn requires compliance with another specification). Well, my main question from that is what it is about Parrot named parameters that don't work for Kea-CL. (It may be something we can fix.) But, what I expect from Kea-CL with a unique parameter-passing style is that your libraries clearly document how to call the subroutines. That's all. If people find libraries written in your language too obtuse to bother with, then they simply won't use them. There are an awful lot of musts in the draft, where there should be only free will. Another example is object system metamodel compatibility. I am not an expert on metamodels, but all the ones I *think* I know make it very hard for me to imagine inheritance across language boundaries without some very careful design and coding on the part of language implementors on both sides of the boundary. (Who will no doubt be grateful for some global specification to help them in that work. ;-) The interoperability infrastructure is the vtable functions. You can have absolutely any metamodel you want, just provide a minimal set of functionality so Parrot can instantiate objects from your class, invoke methods, and get and set attribute values. Inheritance across language boundaries works by proxying and delegation. It's true that a class in one language won't know how to, for example, look up a method in a parent class from another language. So, it can't poke directly into the parent and do the lookup, but it can ask the parent to do the lookup. Poking directly into the parent breaks encapsulation anyway, generally a bad idea. Do you really think that Parrot can subsume all object system metamodels well enough to provide all the infrastructure? Just the CLOS and Perl 6 MOPs are each complicated enough on their own; I'm tempted to advocate $n^2$ metamodel interfaces in order to break the problem down into manageable chunks. (And, not incidentally, push the problems onto the people who understand them.) If you mean Do you think Parrot can build an enormous and complex interoperability infrastructure that handles all possible language semantics now and in the future?, the answer is absolutely not, and let's avoid that like the plague. The point is to keep it as barebones as possible, and leave each language to implement whatever custom behavior they need behind the vtable function interface. +{{ It's not possible to define a sub that can't be called externally --allison }} Not now, true. Except that we currently support .sub foo :anon ... for compilation-unit scoping. Are you saying you object to language scoping of subs? Sure, but if that scoped sub was returned as a subroutine object to another language, it could be invoked as a subroutine by that language. +{{ Exporting is very much a Perl idea, not much applicability for exporting +outside of Perl. --allison}} Eh? I think we are having another terminology issue. By export I meant make public. Perl is not the only language to use this term; just off the top of my head I can think of CL and Erlang. Ah, by export I mean inject into the caller's namespace (Perl terminology). Any subroutines stored in a namespace are already public, so I'm not sure what you meant. I *could* represent CL strings explicitly as vectors of characters instead of using the String type. But that would mean that I couldn't use the wealth of Parrot string ops, and would be inviting more interoperability problems to boot. Ditto
Re: [svn:parrot-pdd] r30622 - trunk/docs/pdds/draft
From: Allison Randal [EMAIL PROTECTED] Date: Tue, 02 Sep 2008 01:15:18 +0200 Thank you for responding so promptly; I doubt I will be able to return fire on your schedule. Bob Rogers wrote: As a case in point, consider keyword (named) parameters in Lisp. Kea-CL does not use Parrot named parameters to implement key . . . Well, my main question from that is what it is about Parrot named parameters that don't work for Kea-CL. (It may be something we can fix.) I will answer this now, since you ask, and because I had written it up for the previous post and then decided that it was too much detail. Please see below. But, what I expect from Kea-CL with a unique parameter-passing style is that your libraries clearly document how to call the subroutines. That's all. If people find libraries written in your language too obtuse to bother with, then they simply won't use them. Yes. If I do nothing else, then this corresponds to option c below, which meets my criteria for too obtuse. There are an awful lot of musts in the draft, where there should be only free will. Guilty as charged. My intent is usually must do X in order to maximimize interoperability, but that is not clear. Should is much better. And the rest will have to wait until I have more time. -- Bob To explain why I think it is inevitable that language implementors will have to shoulder at least some of the burden, let me describe an interoperability problem that affects Kea-CL (and ANSI-compliant Common Lisp implementations in general). The ANSI spec says two things about keyword parameters [1] that constrain how they can be implemented in Parrot: 1. Keyword parameters are typically named by symbols in the KEYWORD package, but are permitted to be named by any object; such objects are tested for identity when binding keyword parameters. Therefore, the symbols :foo and frobboz::foo are distinct as keyword parameter names, even though they might stringify the same [2]. 2. At the point of call, there is no distinction between different kinds of parameters. For example, in the call (test-function foo bar :start1 17) the last two arguments could supply values to a single keyword parameter named :start1, or to the third and fourth positional parameters. Or the whole thing could be a single rest (slurpy) parameter; the compiler is not allowed to guess here [3]. Because Parrot named parameters are handled as a separate class of parameter, and are always named by strings, that presents a severe problem. An implementation can choose to: a. Punt on ANSI compliance, mapping Lisp keywords onto Parrot named parameters. I don't think this possible, since there's no way to tell at the point of call. b. Adopt a hybrid approach and declare keyword parameters as Parrot named parameters, adding some extra processing logic to handle conversion; i.e. all functions support both protocols. If the named parameters are filled by a non-Lisp call, add them to any rest list; if an rest list has keyword values that are not yet supplied, stuff the values in the named parameters. This ought to work (I haven't tried it), but entails a certain amount of extra overhead, even for the Lisp-to-Lisp case. c. Use the straightforward Lispy implementation (i.e. by ignoring Parrot named parameters altogether) and insist that the caller supply key arguments using Lisp symbols as positional parameters. Any caller would have to do the equivalent of (intern FOO (find-package KEYWORD)) just to look up the parameter name for :foo. (This is the current unsatisfactory state of affairs). d. Use the straightforward Lispy implementation (i.e. by ignoring Parrot named parameters altogether) and plan to provide a wrapper for each API function that has keywords for foreign calling. My proposal is about option d, because I think that is the best option for Lisp, and I think it should work well for other languages, too. [1] http://www.lispworks.com/documentation/HyperSpec/Body/03_dad.htm [2] But stringification is not a CL concept anyway. Coercion to string is usually tied up with printing, but printing yields different results depending on context. [3] Some compilers optimize based on prior knowledge of the definition being called, but that is not strictly legal, and always requires a non-default level of optimization.
[svn:parrot-pdd] r30622 - trunk/docs/pdds/draft
From: [EMAIL PROTECTED] Date: Thu, 28 Aug 2008 12:43:20 -0700 (PDT) Author: allison Date: Thu Aug 28 12:43:19 2008 New Revision: 30622 I've not responded to all your comments, just some of the key ones that I hope will promote understanding. I won't commit any changes until after I hear what you have to say. (Some of the hunks have been reformatted for readability.) @@ -41,6 +41,13 @@ case, some translation may be required by both the calling language and the called language: +{{ There seems to be an implied basic assumption here that language +interoperability is the responsibility of the language +implementor. It is not. We cannot require that language +implementors design and implement their languages according to some +global specification. If you are not happy with that assumption, then I'm surprised you bothered to commit this draft at all, even as a starting point. Even then, surely, it must *still* be the responsibility of the language implementor not to introduce gratuitous barriers to interoperability? As a case in point, consider keyword (named) parameters in Lisp. Kea-CL does not use Parrot named parameters to implement key, partly for ANSI compliance and partly for efficiency. This currently makes it problematic (though not impossible) for other languages to call Lisp functions that accept keywords. You can either say I'm a bad boy for not fully using Parrot features and require me to design and implement ... according to some global specification, forcing me to solve the performance vs. compliance vs. interoperability tradeoff in each sub, or allow me to do my own thing internally and accept the need for glue around the edges (which in turn requires compliance with another specification). Another example is object system metamodel compatibility. I am not an expert on metamodels, but all the ones I *think* I know make it very hard for me to imagine inheritance across language boundaries without some very careful design and coding on the part of language implementors on both sides of the boundary. (Who will no doubt be grateful for some global specification to help them in that work. ;-) +Any interoperability +infrastructure must be provide by Parrot, and must work for all languages. +--allison }} Do you really think that Parrot can subsume all object system metamodels well enough to provide all the infrastructure? Just the CLOS and Perl 6 MOPs are each complicated enough on their own; I'm tempted to advocate $n^2$ metamodel interfaces in order to break the problem down into manageable chunks. (And, not incidentally, push the problems onto the people who understand them.) @@ -117,6 +132,8 @@ call intra-language subs, they should be very sure they understand that language's calling conventions. +{{ It's not possible to define a sub that can't be called externally --allison }} Not now, true. Except that we currently support .sub foo :anon ... for compilation-unit scoping. Are you saying you object to language scoping of subs? @@ -139,13 +156,22 @@ access the module API (though it may need additional hints). Of course, that also requires a PIR API for accessing this metainformation . . . +{{ Exporting is very much a Perl idea, not much applicability for exporting +outside of Perl. --allison}} Eh? I think we are having another terminology issue. By export I meant make public. Perl is not the only language to use this term; just off the top of my head I can think of CL and Erlang. @@ -175,6 +201,10 @@ functions, i.e. a method defined for CVECTOR must be considered when passed a string as a parameter. +{{ Common Lisp (for example) will have its own set of type relationships, +because it will have its own set of types . . . I *could* represent CL strings explicitly as vectors of characters instead of using the String type. But that would mean that I couldn't use the wealth of Parrot string ops, and would be inviting more interoperability problems to boot. Ditto for Integer and Float, which are exactly what I need in terms of representation. CL does not need new types for these. And that is a good thing. @@ -235,6 +275,12 @@ floating-point result from Common Lisp code that happens to get two integers from Perl or Lua (or both!). +{{ Not a bug, it's the expected result. Divide operations are multi-dispatched. +If you pass two Common Lisp integers into a divide operation in Perl 5, it'll +search for the best matching multi, and if it finds one for Common Lisp +integers (an exact match), it'll run that and return a Common Lisp ratio. +--allison }} We are at an impasse, then. But I suppose it doesn't matter. If language implementers believe that is OK, then they can accept whatever the builtin returns. If not, they can use MMD to define any exceptions they require. @@ -242,6 +288,10 @@ inputs to these operations
[svn:parrot-pdd] r30622 - trunk/docs/pdds/draft
Author: allison Date: Thu Aug 28 12:43:19 2008 New Revision: 30622 Modified: trunk/docs/pdds/draft/pdd31_hll_interop.pod Log: [pdd] Adding a series of architectural comments to the HLL Interop PDD. Modified: trunk/docs/pdds/draft/pdd31_hll_interop.pod == --- trunk/docs/pdds/draft/pdd31_hll_interop.pod (original) +++ trunk/docs/pdds/draft/pdd31_hll_interop.pod Thu Aug 28 12:43:19 2008 @@ -41,6 +41,13 @@ case, some translation may be required by both the calling language and the called language: +{{ There seems to be an implied basic assumption here that language +interoperability is the responsibility of the language implementor. It is not. +We cannot require that language implementors design and implement their +languages according to some global specification. Any interoperability +infrastructure must be provide by Parrot, and must work for all languages. +--allison }} + | | |Calling sub @@ -70,7 +77,13 @@ {{ Of course, stub is really too close to sub, so we should find a better word. Doesn't the C community call these bounce routines? Or something? --- rgr, 31-Jul-08. }} +-- rgr, 31-Jul-08. + +The language will never provide a wrapper for its subs. For the most part, +wrappers will be unnecessary. Where a wrapper is desired to make a library from +some other language act more like a native library, the person who desires +the native behavior can implement the wrapper and make it publically available. +--allison }} {{ I am discovering that there are five different viewpoints here, corresponding to the five layers (including plain Parrot) of the diagram @@ -109,6 +122,8 @@ are provided by a bare Parrot (i.e. one without any HLL runtime code), then it should be possible to use this API from any other language. +{{ This is unnecessarily restrictive --allison }} + =item * It is acceptable for languages to define subs for internal calling that are @@ -117,6 +132,8 @@ call intra-language subs, they should be very sure they understand that language's calling conventions. +{{ It's not possible to define a sub that can't be called externally --allison }} + =back =head1 HALF-BAKED IDEAS @@ -139,13 +156,22 @@ access the module API (though it may need additional hints). Of course, that also requires a PIR API for accessing this metainformation . . . +{{ Exporting is very much a Perl idea, not much applicability for exporting +outside of Perl. --allison}} + Crazy idea: This is more or less the same information (typing) required for multimethods. If we encourage the export of multisubs, then the exporting language could provide multiple interfaces, and the calling compiler could query the set of methods for the one most suitable. +{{ Proposal rejected, because we aren't going with external and internal +subroutine variants, so it's not needed. --allison }} + =head2 More namespace complexity? +{{ Proposal rejected, because we aren't going with external and internal +subroutine variants, so it's not needed. --allison }} + It might be good to have some way for HLLs to define a separate external definition for a given sub (i.e. one that provides the wrapper) that can be done without too much namespace hair. I.e. @@ -175,6 +201,10 @@ functions, i.e. a method defined for CVECTOR must be considered when passed a string as a parameter. +{{ Common Lisp (for example) will have its own set of type relationships, +because it will have its own set of types. There will be no remapping of core +types --allison }} + The language that owns the multisub gets to define the type hierarchy and dispatch rules used when it gets called. In order to handle objects from foreign languages, the owning language must decide where to graft the @@ -184,10 +214,16 @@ only have to include CObject in order to incorporate objects from all other conforming languages. -- rgr, 26-Aug-08. }} +{{ The language that owns the multisub does get to define the dispatch rules +for the multisub. But, it doesn't get to alter the type hierarchy of objects +from other languages. --allison }} + Note that common Parrot classes will in general appear in different places in different languages' dispatch hierarchies, so it is important to bear in mind which language owns the dispatch. +{{ Absolutely not true. --allison }} + =head1 DEFINITIONS {{ Collect definitions of new jargon words here, once we figure out what they @@ -220,6 +256,10 @@ the particular case of integer division, which differs significantly between languages. +{{ No, this is completely backwards. Languages are heartily encouraged to +create their own PMCs for any and all common variable types found in the +language. --allison }} + In Tcl, the integer three divided by the integer five produces the integer value 0. @@ -235,6 +275,12 @@ floating-point result from Common Lisp code that happens to