bugKawa - Bugs: bug #43285, Require vs. load

 
 

bug #43285: Require vs. load

Submitter:  Helmut Eller <ellerh>
Submitted:  Tue 23 Sep 2014 05:49:29 PM UTC
   
 
Category:  None Severity:  3 - Normal
Item Group:  None Status:  Invalid
Privacy:  Public Assigned to:  bothner
Open/Closed:  Closed
* Mandatory Fields

Add a New Comment Rich Markup
   

Tue 23 Sep 2014 07:20:21 PM UTC, comment #4: 

By "lexical scope of x.scm" I mean file-level or module-level scope, similar to a r7rs library.  If you read the r7rs specification section 5.6.1 page 28 you see "After all cond-expand library declarations are expanded, a new environment is constructed for the library consisting of all imported bindings."  The module-level scope is equivalent to this environment.  Note since this environment is local to the module/library, it can be treated as a purely lexical scope.  Think of it as an implicit file-level letrec*, but with the option of exporting a subset of the bindings to another module. This scope is "inside" the traditional top-level scope.

"I would say that foo is defined in the top-level scope (as it's neither inside a module nor inside a lambda)."

It's defined in the module/library scope of y.scm.  When you (require "y.scm") (or equivalently use R7RS import) the file y.scm is treated as an implicit module/library.

("module" == "library" in this case.  The former is Kawa/R6RS terminology, the latter is R7RS terminology.)

Per Bothner <bothner>
Group administrator
Tue 23 Sep 2014 06:42:14 PM UTC, comment #3: 

I only understand half of your terminology.  What is the "lexical scope of x.scm"?  I would say that foo is defined in the top-level scope (as it's neither inside a module nor inside a lambda).

Helmut Eller <ellerh>
Tue 23 Sep 2014 06:28:32 PM UTC, comment #2: 

"It might be possible to add the exported bindings to the dynamic environment before evaluating the module body"

Note that wouldn't help in this case, since x.scm doesn't re-export the imported binding foo - you'd have to explicitly export it.

Per Bothner <bothner>
Group administrator
Tue 23 Sep 2014 06:16:49 PM UTC, comment #1: 

It's not a bug, as I see it.

When you evaluate x.scm (without using -f or the load function) it is parsed in module-at-a-time mode.  The entire file is compiled into a module, which is then loaded.  When x.scm requires y.scm, the definition of foo is added to the lexical scope of x.scm, not the dynamic environment.  When x.scm is evaluated, it loads z.scm, which looks for foo in the dynamic environment, where it is not.

There is a special hack for the interactive top-level: After evaluating a require, all the of exported bindings are added to the dynamic environment.

It might be possible to add the exported bindings to the dynamic environment before evaluating the module body, though maybe not in all cases, and it's a bit tricky.  (See the code in ModuleExp.evalModule2.)

Note if you run x.scm in line-at-a-time mode (e.g by using the -f flag) things work as expected.

Per Bothner <bothner>
Group administrator
Tue 23 Sep 2014 05:49:29 PM UTC, original submission:  

Not sure if this is a bug, but I find this situation surprising.

Suppose we have three files x.scm, y.scm, z.scm with the following
content:

shell> cat x.scm
(require "y.scm")
(load "z.scm")

shell> cat y.scm
(define (foo) 123)

shell> cat z.scm
(foo)


i.e. the file y.scm defines a function foo which is used in file
z.scm; x.scm loads the other two files.

Then Kawa (version 1.14.1 (revision 7749:8062M)) runs into this
problem:

shell> kawa x.scm
z.scm:1:1: warning - no declaration seen for foo
z.scm:1:1: unbound location: foo
        at gnu.mapping.SharedLocation.get(SharedLocation.java:22)
        at gnu.mapping.DynamicLocation.get(DynamicLocation.java:28)
        at atInteractiveLevel$1.run(z.scm:1)
        at gnu.expr.ModuleExp.evalModule2(ModuleExp.java:316)
        at gnu.expr.ModuleExp.evalModule(ModuleExp.java:217)
        at kawa.Shell.run(Shell.java:290)
        at kawa.Shell.runFile(Shell.java:522)
        at kawa.standard.load.apply2(load.java:67)
        at kawa.standard.load.apply1(load.java:27)
        at gnu.mapping.Procedure.apply(Procedure.java:135)
        at gnu.mapping.Procedure.apply(Procedure.java:118)
        at gnu.mapping.CallContext.runUntilDone(CallContext.java:234)
        at x.run(x.scm:2)
        at gnu.expr.ModuleExp.evalModule2(ModuleExp.java:316)
        at gnu.expr.CompiledModule.evalModule(CompiledModule.java:42)
        at gnu.expr.CompiledModule.evalModule(CompiledModule.java:61)
        at kawa.Shell.runFile(Shell.java:536)
        at kawa.Shell.runFileOrClass(Shell.java:445)
        at kawa.repl.main(repl.java:881)


Helmut Eller <ellerh>

 

(Note: upload size limit is set to 16384 kB, after insertion of the required escape characters.)

Attach Files:
   
   
Comment:
   

No files currently attached

 

Depends on the following items: None found

Items that depend on this one: None found

 

Carbon-Copy List
  • -email is unavailable- added by bothner (Posted a comment)
  • -email is unavailable- added by ellerh (Submitted the item)
  •  

    There are 0 votes so far. Votes easily highlight which items people would like to see resolved in priority, independently of the priority of the item set by tracker managers.

    Only logged-in users can vote.

     

    Follow 3 latest changes.

    Date Changed by Updated Field Previous Value => Replaced by
    2016-04-08 bothner Open/ClosedOpen Closed
    2014-09-23 bothner StatusNone Invalid
        Assigned toNone bothner

    Back to the top

    Powered by Savane 3.13-3230.
    Corresponding source code