[llvm-dev] Questions on Clang's documentation of Modules

Richard Smith via llvm-dev llvm-dev at lists.llvm.org
Thu May 12 13:32:10 PDT 2016

On Wed, May 11, 2016 at 11:40 PM, Dan Liew <dan at su-root.co.uk> wrote:

> Hi,
> I was reading Clang's documentation [1] on Modules and there are
> several aspects that confused me that I was wondering if someone could
> clarify some parts. I'm CC'ing a few people who git blame shows
> contributed to the documentation. Hopefully answers can be used to
> help me write a patch to improve the documentation here.
> # Modules Semantics
> The following is stated
> ```
> If any submodule of a module is imported into any part of a program,
> the entire top-level module is considered to be part of the program.
> As a consequence of this, Clang may diagnose conflicts between an
> entity declared in an unimported submodule and an entity declared in
> the current translation unit, and Clang may inline or devirtualize
> based on knowledge from unimported submodules.
> ```
> What does considered "part of the program" mean here? Initially I
> thought that meant just import the parent module (i.e. writing
> ``import std.io`` is the same as ``import std``) but thinking about it
> some more that doesn't make sense because there wouldn't be any point
> in having submodules because they couldn't be used independently from
> other submodules.
> Perhaps what was meant here is that because ``std`` corresponds to one
> or more libraries we can have Clang check for problems that might
> occur if the program did do ``import std`` (i.e. we used more of the
> library that we are linking against) even though it isn't. Is that
> correct?

Yes. The rest of the module is part of the program in the same way that
other .o files that are linked to the current one are part of the program.
But the import only makes the nominated submodule visible.

Put another way: top-level modules are the units of granularity for
linking, and submodules are the units of granularity for visibility within
a particular translation unit. But because the compiler knows that the
entire top-level module will be part of the program when a submodule is
imported, it's able to diagnose more problems / conflicts.

# Use declaration
> I don't understand this part at all.
> What does ``the current top-level module`` mean here? In other places
> the docs say "enclosing module" for other declarations inside a module
> declaration. Are these supposed to be the same? They do not sound the
> same.

A top-level module is one that's not a submodule of another module.  We can
easily add a definition if that's not obvious.


module A {
  module B {
    module C {
      // Here, A is the top-level module, but A.B.C is the (immediately)
enclosing module.

In any case, I think the documentation is a little unclear here: we should
probably phrase this as "A use-declaration specifies another module that
the enclosing module (that is required to be a top-level module) intends to
use." or similar.

The example given further confuses me because
> - I don't know what the "current top-level module" is here
> - I don't understand why the compiler would complain about anything
> here. There's nothing here that indicates that "c.h" depends on "a.h"
> so why would the compiler complain about module C not declaring a
> dependency on module A.

It says that "use of A from C" would trigger a warning, that is, if C
included one of A's headers, a warning would be triggered. This would be a
lot more obvious if we gave example contents for c.h.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/llvm-dev/attachments/20160512/b16449d7/attachment.html>

More information about the llvm-dev mailing list