guile-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

RE: The Guile junk drawer and a C plea (was: [PATCH] Addnondestructive d


From: Maxime Devos
Subject: RE: The Guile junk drawer and a C plea (was: [PATCH] Addnondestructive delq1, delv1, and delete1.)
Date: Sat, 29 Jun 2024 12:41:27 +0200

 

>Regarding the junk, I very much agree. I also look forward to getting rid of ice-9 :). As has been spoken about here previously, I suggest that we design a new module hierarchy, introduce aliases for module bindings, and still supply the old module hierarchy during a few years for backward compatibility.

 

On this, and on responses on potential harm introduces by incompatible changes:

 

It’s not like Python where semantics were changed in some changes, this is about simply renaming stuff. We can keep the (ice-9 ...) modules/bindings forever – if not in Guile, then in a separate Scheme library (so out-of-date Scheme libraries can still be used after installing this compatibility library with whatever is the local package manager).

 

The default environment is irrelevant to most Scheme libraries, since it is irrelevant to any library defining modules with ‘define-module’, ‘define-library’ or ‘library’ forms (which is pretty much the only reasonable way to define modules unless you are making your own system). This already reduces a lot of compatibility concerns. An important exception is anyone doing ‘eval’ or compiling expressions (think anyone doing the equivalent of “guile -l script.scm”.

 

Now let’s look at ‘eval’ and the like, in particular where it uses the default environment.

 

From the manual:

 

Scheme Procedure: eval exp module_or_state

C Function: scm_eval (exp, module_or_state)

Evaluate exp, a list representing a Scheme _expression_, in the top-level environment specified by module_or_state. While exp is evaluated (using primitive-eval), module_or_state is made the current module. The current module is reset to its previous value when eval returns. XXX - dynamic states. Example: (eval ’(+ 1 2) (interaction-environment))

 

Note that ‘eval’ does not even have a default environment, you need to specify an environment (in this case, a module) to evaluate the _expression_ in! So, an option here is to let (guile) be the current messy (not recommended) environment, let (guile interaction-environment-2) (*) be a cleaned-up version, if at some point in time it is decided this cleaned-up version is not clean enough or that some bindings should be added, a new module (guile interaction-environment-3) could be defined, etc..

 

(Important point: never change the contents of one of these interaction environment modules, to ensure compatibility!)  (If at some point there are too many of these interaction environment, the old ones can be moved to separate libraries to be installed with the local package manager – this might even include (guile).)

 

This way, any user of ‘eval’ or the like can (and in case of ‘eval’, needs to) specify _which_ environment they want.

 

Next, we have the thunk ‘interaction-environment’:

 

>Scheme Procedure: interaction-environment

>C Function: scm_interaction_environment ()

>Return a specifier for the environment that contains implementation–defined bindings, typically a superset of those listed in the report. The intent is that this procedure will return the environment in which the implementation would evaluate expressions dynamically typed by the user.

 

For compatibility, this would need to be the messy (guile) module. It would also need to deprecated (but not actually removed) – best let users specify _which_ version they want, so compatibility is preserved.

 

Next there is ‘eval-string’ and ‘primitive-eval’, which evaluates in the current module (and hence doesn’t care about what is the interaction environment).

 

There is also “guile -l [...]” and the like, but I don’t think Lilypond and the like really care about what “guile -l [...]” uses as default environment, as long as there is a way of overriding the choice.

 

Also, on deprecation and removal: just because you deprecate something, doesn’t mean it has to be removed. And just because something deprecated will be removed or because something is volatile, doesn’t mean it has to be an incompatible change!

 

We can do something similar to what Coq does – Coq sometimes does incompatible changes, but at the same time, when it does so, it also verifies that there are no impacted libraries, and if there are impacted libraries, the impacted libraries are first modified – by people making changes to Coq itself(*) – to update it according to the changes.  (It’s not done for _all_ libraries of course, but still a nice selection.)

 

(*) Actually I’m not sure if this about Coq itself or a selection of Coq libraries, but the point stands either way.

 

Also, in RnRS modules can have version modules. There isn’t currently support for defining multiple versions of modules in Guile, but there could be.

 

Best regards,

Maxime Devos.


reply via email to

[Prev in Thread] Current Thread [Next in Thread]