home *** CD-ROM | disk | FTP | other *** search
/ NetNews Usenet Archive 1992 #31 / NN_1992_31.iso / spool / comp / lang / cplus / 18601 < prev    next >
Encoding:
Text File  |  1992-12-31  |  3.6 KB  |  72 lines

  1. Newsgroups: comp.lang.c++
  2. Path: sparky!uunet!think.com!spool.mu.edu!umn.edu!csus.edu!netcom.com!nagle
  3. From: nagle@netcom.com (John Nagle)
  4. Subject: Re: Static global initialization outside of main() legal?
  5. Message-ID: <1992Dec31.191123.7222@netcom.com>
  6. Organization: Netcom - Online Communication Services  (408 241-9760 guest) 
  7. References: <34727@sales.GBA.NYU.EDU>
  8. Date: Thu, 31 Dec 1992 19:11:23 GMT
  9. Lines: 61
  10.  
  11. wlee@sales.GBA.NYU.EDU (Wai-Shing Lee) writes:
  12. >   I want to initialize a static global at run-time but I don't want to
  13. >have to have a programmer using my modules to have to call some init() funciton
  14. >at the begining of thier main().
  15.  
  16. >I've traced it and sure enough makepointer() is called and pointer is assigned
  17. >a value before main() even starts.  Is the portable, legal.  I didn't look
  18. >to hard in my C++ book, but there weren't any obvious answers.  Is this
  19. >C++, C or something I should stay away from?
  20.  
  21.        You're working in a very messy area of C++.  The order in which
  22. things happen during static initialization isn't the same in different
  23. compilers.  The language rules arein section r3.4 of "The C++ Programming
  24. Language, Second Edition", and you should read them if you want to do this
  25. sort of thing.
  26.  
  27.        In most implementations, static initializers are run before
  28. "main" is called.  For initializers that don't call functions, this
  29. is enough to get the static variables initialized properly.  But
  30. initializers that call functions can create serious problems, especially
  31. if the functions have side effects, are in a different compilation unit
  32. (file), or depend on other static variables being initialized.  The order
  33. in which things get initialized varies from compiler to compiler and
  34. sometimes from compile to compile, so you can't depend on this at all.
  35.  
  36.        If you use C++ classes, it gets worse.
  37.  
  38.        Constructors are functions.  So static variables declared with
  39. a type that has a constructor result in the class constructor function
  40. being called before startup.  But you're not guaranteed that the static
  41. variables of the class implementing the constructor were initialized 
  42. before the first use of the class.  So it is bad C++ to write a class
  43. which needs static initialization (other than to 0, which is special
  44. and must occur before any code can run) before its constructors can be
  45. validly called.
  46.  
  47.        It's also worth noting that in many implementations, you can't
  48. print anything before "main" is called, so printing messages in a 
  49. constructor may cause problems if the constructor is used to initialize
  50. a static variable.
  51.  
  52.        Does anyone know what happens if you raise an exception in a 
  53. constructor called during static initialization?  The reference manual
  54. is silent on the subject.
  55.  
  56.        Modula 2 has a much better approach to initialization.  They
  57. have the linker sort out the dependency structure, based on the call
  58. graph.  The linker finds an order that will result in the initializers
  59. being called in a valid order, so everything gets initialized before
  60. it can be called.  If the linker can't find a valid order, you get an error
  61. message at link time.  (TopSpeed Modula II is an example of a system that
  62. supports this properly.)  In fact, the need for a "main program" disappears;
  63. it's just another initialization section.  (Nice for programs where the
  64. "main program" is an event loop that comes from a library.)  This is 
  65. clearly the right way to do it, but C++, as a bolt-on to existing C 
  66. compilers, can't do it that way, because it requires support in the linker.  
  67.  
  68.        So, unless you want to worry about all this stuff, calling functions
  69. with side effects in initializers should be avoided.
  70.  
  71.                     John Nagle
  72.