help-smalltalk
[Top][All Lists]
Advanced

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

[Help-smalltalk] faster quit, again


From: Paolo Bonzini
Subject: [Help-smalltalk] faster quit, again
Date: Mon, 05 Feb 2007 08:35:49 +0100
User-agent: Thunderbird 1.5.0.9 (Macintosh/20061207)

This I had promised last December, but it took me a while before I sat down to do it. The trick is to avoid #allSubinstancesDo: and instead iterate on a WeakIdentitySet.

This brings some more changes because we need WeakIdentitySet to be available when we initialize the kernel. But it also simplifies a little, because the Dependencies dictionary was born as an IdentityDictionary and then transformed into a WeakKeyIdentityDictionary: now the WKID is available from the start and we can use it.

The speedup is 5-15%.

Paolo
2007-02-05  Paolo Bonzini  <address@hidden>

        * kernel/FileDescr.st: Remove #allSubinstancesDo: on quit, instead
        register open files in a WeakIdentitySet.
        * kernel/Object.st: Store dependencies in a WeakKeyIdentityDictionary.
        * kernel/WeakObjects.st: Don't transform dependencies into a
        WeakKeyIdentityDictionary here.

        * libgst/dict.c: Add variables and declarations for weak objects.
        * libgst/dict.h: Add variables for weak objects.
        * libgst/lib.c: Load WeakObjects.st as part of the kernel classes.


--- orig/kernel/FileDescr.st
+++ mod/kernel/FileDescr.st
@@ -33,7 +33,7 @@
 
 ByteStream subclass: #FileDescriptor
                instanceVariableNames: 'file name isPipe atEnd peek'
-               classVariableNames: ''
+               classVariableNames: 'AllOpenFiles'
                poolDictionaries: ''
                category: 'Streams-Files'
 !
@@ -183,8 +183,7 @@ popen: commandName dir: direction
      Else answer a new FileStream.
      The pipe will not be automatically closed upon GC, even if the object
      is not referenced anymore, because when you close a pipe you have to wait
-     for the associated process to terminate. To enforce automatic closing of
-     the pipe, send it #addToBeFinalized.
+     for the associated process to terminate.
      direction is returned by #read or #write ('r' or 'w') and is interpreted
      from the point of view of Smalltalk: reading means Smalltalk reads the
      standard output of the command, writing means Smalltalk writes the 
standard input of the command. The other channel
@@ -203,8 +202,7 @@ popen: commandName dir: direction ifFail
      file cannot be opened. Else answer a new FileStream.
      The pipe will not be automatically closed upon GC, even if the object
      is not referenced anymore, because when you close a pipe you have to wait
-     for the associated process to terminate. To enforce automatic closing of
-     the pipe, send it #addToBeFinalized.
+     for the associated process to terminate.
      direction is interpreted from the point of view of Smalltalk: reading
      means that Smalltalk reads the standard output of the command, writing
      means that Smalltalk writes the standard input of the command"
@@ -232,7 +230,8 @@ write
 
 initialize
     "Initialize the receiver's class variables"
-    ObjectMemory addDependent: self
+    ObjectMemory addDependent: self.
+    AllOpenFiles := WeakIdentitySet with: stdin with: stdout with: stderr
 !
 
 update: aspect
@@ -241,9 +240,7 @@ update: aspect
        stdin flush. stdout flush. stderr flush
     ].
     aspect == #aboutToQuit ifTrue: [
-        self allSubinstancesDo: [ :each |
-           each isOpen ifTrue: [ each close ]
-       ]
+        AllOpenFiles asArray do: [ :each | each close ]
     ]
 ! !
 
@@ -278,6 +275,7 @@ close
 finalize
     "Close the file if it is still open by the time the object becomes
     garbage."
+    AllOpenFiles remove: self.
     file isNil ifFalse: [ self close ].
 !
 
@@ -603,6 +601,14 @@ basicNextPutByte: anInteger
 
 !FileDescriptor methodsFor: 'initialize-release'!
 
+addToBeFinalized
+    AllOpenFiles add: self.
+    super addToBeFinalized!
+
+removeToBeFinalized
+    AllOpenFiles remove: self.
+    super removeToBeFinalized!
+
 initialize
     "Initialize the receiver's instance variables"
     self addToBeFinalized.


--- orig/kernel/Object.st
+++ mod/kernel/Object.st
@@ -69,11 +69,10 @@ finalizableObjects
     ^FinalizableObjects!
 
 initialize
-    "Initialize the Dependencies dictionary to be an IdentityDictionary.  In a 
later
-     phase of the bootstrap process this is changed to be a 
WeakKeyIdentityDictionary."
+    "Initialize the Dependencies dictionary to be a WeakKeyIdentityDictionary."
 
     self == Object ifFalse: [ ^self ].
-    self dependencies: IdentityDictionary new.
+    self dependencies: WeakKeyIdentityDictionary new.
     ObjectMemory addDependent: self
 ! !
 


--- orig/kernel/WeakObjects.st
+++ mod/kernel/WeakObjects.st
@@ -569,10 +569,3 @@ findIndex: anObject
     ] repeat
 ! !
 
-| wkid |
-wkid := WeakKeyIdentityDictionary new.
-Object dependencies associationsDo: [ :assoc |
-    wkid add: assoc
-].
-Object dependencies: wkid!
-


--- orig/libgst/dict.c
+++ mod/libgst/dict.c
@@ -169,6 +169,13 @@ OOP _gst_undefined_object_class = NULL;
 OOP _gst_unicode_character_class = NULL;
 OOP _gst_unicode_string_class = NULL;
 OOP _gst_variable_binding_class = NULL;
+OOP _gst_weak_array_class = NULL;
+OOP _gst_weak_set_class = NULL;
+OOP _gst_weak_key_dictionary_class = NULL;
+OOP _gst_weak_value_lookup_table_class = NULL;
+OOP _gst_weak_identity_set_class = NULL;
+OOP _gst_weak_key_identity_dictionary_class = NULL;
+OOP _gst_weak_value_identity_dictionary_class = NULL;
 OOP _gst_write_stream_class = NULL;
 OOP _gst_processor_oop = NULL;
 
@@ -444,6 +451,10 @@ static const class_definition class_info
    ISP_POINTER, true, 0,
    "Array", NULL, NULL, NULL },
 
+  {&_gst_weak_array_class, &_gst_array_class,
+   ISP_FIXED, false, 2,
+   "WeakArray", "values nilValues", NULL, NULL },
+
   {&_gst_character_array_class, &_gst_arrayed_collection_class,
    ISP_ULONG, false, 0,
    "CharacterArray", NULL, NULL, NULL },
@@ -509,18 +520,42 @@ static const class_definition class_info
    ISP_POINTER, false, 0,
    "Set", NULL, NULL, NULL },
 
+  {&_gst_weak_set_class, &_gst_set_class,
+   ISP_POINTER, false, 0,
+   "WeakSet", NULL, NULL, NULL },
+
   {&_gst_identity_set_class, &_gst_set_class,
    ISP_POINTER, false, 0,
    "IdentitySet", NULL, NULL, NULL },
 
+  {&_gst_weak_identity_set_class, &_gst_weak_set_class,
+   ISP_POINTER, false, 0,
+   "WeakIdentitySet", NULL, NULL, NULL },
+
   {&_gst_dictionary_class, &_gst_hashed_collection_class,
    ISP_POINTER, true, 0,
    "Dictionary", NULL, NULL, NULL },
 
+  {&_gst_weak_key_dictionary_class, &_gst_dictionary_class,
+   ISP_POINTER, false, 1,
+   "WeakKeyDictionary", "keys", NULL, NULL },
+
+  {&_gst_weak_key_identity_dictionary_class, &_gst_weak_key_dictionary_class,
+   ISP_POINTER, false, 0,
+   "WeakKeyIdentityDictionary", NULL, NULL, NULL },
+
   {&_gst_lookup_table_class, &_gst_dictionary_class,
    ISP_POINTER, false, 0,
    "LookupTable", NULL, NULL, NULL },
 
+  {&_gst_weak_value_lookup_table_class, &_gst_lookup_table_class,
+   ISP_POINTER, false, 1,
+   "WeakValueLookupTable", "values", NULL, NULL },
+
+  {&_gst_weak_value_identity_dictionary_class, 
&_gst_weak_value_lookup_table_class,
+   ISP_POINTER, false, 0,
+   "WeakValueIdentityDictionary", NULL, NULL, NULL },
+
   {&_gst_identity_dictionary_class, &_gst_lookup_table_class,
    ISP_POINTER, false, 0,
    "IdentityDictionary", NULL, NULL, NULL },
@@ -581,7 +616,7 @@ static const class_definition class_info
 
   {&_gst_file_descriptor_class, &_gst_byte_stream_class,
    ISP_FIXED, true, 5,
-   "FileDescriptor", "file name isPipe atEnd peek", NULL, NULL },
+   "FileDescriptor", "file name isPipe atEnd peek", "AllOpenFiles", NULL },
 
   {&_gst_file_stream_class, &_gst_file_descriptor_class,
    ISP_FIXED, true, 2,


--- orig/libgst/dict.h
+++ mod/libgst/dict.h
@@ -386,6 +386,13 @@ extern OOP _gst_undefined_object_class A
 extern OOP _gst_unicode_character_class ATTRIBUTE_HIDDEN;
 extern OOP _gst_unicode_string_class ATTRIBUTE_HIDDEN;
 extern OOP _gst_variable_binding_class ATTRIBUTE_HIDDEN;
+extern OOP _gst_weak_array_class ATTRIBUTE_HIDDEN;
+extern OOP _gst_weak_set_class ATTRIBUTE_HIDDEN;
+extern OOP _gst_weak_key_dictionary_class ATTRIBUTE_HIDDEN;
+extern OOP _gst_weak_value_lookup_table_class ATTRIBUTE_HIDDEN;
+extern OOP _gst_weak_identity_set_class ATTRIBUTE_HIDDEN;
+extern OOP _gst_weak_key_identity_dictionary_class ATTRIBUTE_HIDDEN;
+extern OOP _gst_weak_value_identity_dictionary_class ATTRIBUTE_HIDDEN;
 extern OOP _gst_write_stream_class ATTRIBUTE_HIDDEN;
 extern OOP _gst_processor_oop ATTRIBUTE_HIDDEN;
 


--- orig/libgst/lib.c
+++ mod/libgst/lib.c
@@ -375,11 +375,11 @@ static const char standard_files[] = {
   "FileDescr.st\0"
   "SymLink.st\0"
   "Security.st\0"
+  "WeakObjects.st\0"
   "ObjMemory.st\0"
 
   /* More core classes */
   "Transcript.st\0"
-  "WeakObjects.st\0"
   "RecursionLock.st\0"
   "Point.st\0"
   "Rectangle.st\0"




reply via email to

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