From -7024588585842516371
X-Google-Language: ENGLISH,ASCII-7-bit
X-Google-Thread: f78e5,cdcc6975eda99c6,start
X-Google-Attributes: gidf78e5,public
X-Google-ArrivalTime: 1993-10-11 11:04:09 PST
Newsgroups: comp.std.c++
Path: gmd.de!newsserver.jvnc.net!howland.reston.ans.net!pipex!uunet!munnari.oz.au!metro!news
From: maxtal@physics.su.OZ.AU (John Max Skaller)
Subject: Order of Initialisation
Message-ID: <CEqtq3.MqI@ucc.su.OZ.AU>
Sender: news@ucc.su.OZ.AU
Nntp-Posting-Host: physics.su.oz.au
Organization: School of Physics, University of Sydney, Australia
Date: Mon, 11 Oct 1993 17:25:14 GMT
Lines: 173

In my opinion, the order of initialisation problem is one that
needs to be solved: it will become particularly important
with multiple large class libraries supported by namespaces,
especially ones with lots of complex templates.

Ideally, the linker/compiler can do a complete dependency
analysis on individual initialisations, but I think
that  a REQUIREMENT for that in the Standard may create
two problems:

	1) Its hard to do, I'm not sure its even possible
	   due to aliasing problems.
	   So many compilers will get it wrong.

	2) Its likely to be VERY slow even if its possible.

On the other hand, I am not sure that leaving the order of
initialisation unspecified is acceptable either,
and the de-facto specification: within a translation unit
in order, between translation units no order: is not
good enough either. 

I think. Do you agree?

I have a possible, somewhat hacked, and non perfect, solution. 
I dont claim its ideal or solves all problems. It definitely
solves *some* problems. It also requires an extension,
and if its not considered soon we may be stuck either
with no solution, or delays in acceptance of the Standard
while a solution is retrofitted. 

Here is an outline of my idea:

1) You can write:

	module fred { .. }
	module joe depends on fred { .. }

in a file. After pre-processing, each module is treated
exactly as a separate translation unit. 
(Sorry, these are NOT real modules, MODULA or Ada style)

The names of the modules are not visible to the program.
(Well, they could be accessed by a __MODULE__ macro I suppose).
In particular, a module is NOT a namespace.

	module max {
		int i;
		max::i++; // error, max not known
	}
	module tal depends on max {
		extern int i;
		i++; // fine, refers to 'i' in module max
	}

The module names must be unique per program. They correspond
to the module names in a DOS object code library file,
and represent the smallest loadable unit.

An immediate advantage is you can create a library with
100 separately loadable functions in it, from a single
source file. 

Wrapping module statements around things acts as an
impenetrable barrier, guarranteeing isolation
from context. Use of modules helps deprecate use
of the preprocessor and the file system, and provides
a mechanism in the C++ language proper to deal
with 'translation units'.

The 'depends on ' clause indicates an initialisation dependency.

Separate statements can be written:

	module A depends on B, C;
	module X depends on B, Y;

and I envisage a file of these per program to resolve
order not intrinsic to the modules themselves.

To make this work for templates, we need to force
them to be instantiated somewhere. There is a separate
proposal for this in its second revision already,
basically:

	template list<complex>;

forces instantiation 'here'. These forced instantiations
do not affect overloading. I imagine them in modules
in the same file (or same sort of file)
as the 'extra' module dependencies.

Some extra issues: code not in explicit modules
is wrapped in a module with a compiler generated unique
name. (The file name would be a good place to start :-)

Modules can be nested, but this is mainly because
a file is a module, and an explicit module defined
in a file is thereby automatically nested,
so it has to be allowed. A nested module is exactly
like a non-nested one, the compiler can move a nested
module around (after preprocessing) because of
the isolation guarrantee.

	// file FRED.CC
	int i;
	module bertha {
		extern int i; // refers to i in module 'FRED'
		module nested {
			i++; // error: i not declared
		}
	}

Circular dependencies should cause link-time diagnostics
to be issued.

The module idea  gives the programmer some control over
granularity, and, by making the dependencies
explicit and the modules fairly big (compared to
individual initialisations) should allow fast,
reliable, mechanical solution to the order of
initialisation problem --- with the bulk
of the responsibility on the programmers shoulders.

Of course, I hate giving programmers responsibility.
But in this case it might be an advantage compared
with denying them a sensible mechanism to take control
of at least some problems.

That is, I'd rather be responsible than helpless.

Disadvantages
-------------

It doesnt solve all problems.

Module name pollution. (There are a number of possible solutions
to this)

Confusion with namespaces.

Its yet another extension.

Comment
-------

The code above is  probably already well formed:
no one said a 'translation unit' had to be equal to the
native operating systems concept of a file,
and no one said that you cant control the linker
with some statements: these things are implementation
defined now, and I just gave an example implementation.

There is a possible advantage to portability, however,
in Standardising this, or some, mechanism.

There is also the potential *disadvantage* that it restricts
future solutions and restricts implementors.

Of course, thats exactly the point: the lack of constraints
on order of initialisation is exactly the problem.

In effect, what I've defined could be done with pre-processing
statements, except they affect the front, rather than the
back, end of the system.  I'd rather not extend the pre-processor
when effort has been put into deprecating it (eg #define).


--
        JOHN (MAX) SKALLER,         INTERNET:maxtal@suphys.physics.su.oz.au
	Maxtal Pty Ltd,		    CSERVE:10236.1703 
        6 MacKay St ASHFIELD,	    Mem: SA IT/9/22,SC22/WG21 
        NSW 2131, AUSTRALIA	    


