Fix race condition in bus_ibus_impl_create_engine()
authorYusuke Sato <yusukes@chromium.org>
Tue, 19 Oct 2010 11:30:09 +0000 (20:30 +0900)
committerYusuke Sato <yusukes@chromium.org>
Tue, 19 Oct 2010 11:30:09 +0000 (20:30 +0900)
If the bus_ibus_impl_create_engine() function is called right after an ibus_component_start() call, the function might fail getting a factory object.

To avoid the problem, we should use the busy-wait logic even when ibus_component_is_running() returns true.

BUG=http://crosbug.com/7244
TEST=see the bug (comment #4,7,9)

Review URL: http://codereview.appspot.com/2562041

bus/ibusimpl.c

index bd29e1e928957028e0247840bff7db371a41e781..877f382b8d16166fc5eb83f36cac6311f14f5fb4 100644 (file)
@@ -812,6 +812,27 @@ _ibus_get_address (BusIBusImpl     *ibus,
     return reply;
 }
 
+static BusFactoryProxy *
+_get_factory_proxy(IBusEngineDesc *engine_desc)
+{
+    BusFactoryProxy *factory;
+    GTimeVal t1, t2;
+    g_get_current_time (&t1);
+    while (1) {
+        if (g_main_context_pending (NULL)) {
+            g_main_context_iteration (NULL, FALSE);
+            factory = bus_factory_proxy_get_from_engine (engine_desc);
+            if (factory != NULL) {
+                return factory;
+            }
+        }
+        g_get_current_time (&t2);
+        if (t2.tv_sec - t1.tv_sec >= 5)
+            break;
+    }
+    return NULL;
+}
+
 static BusEngineProxy *
 bus_ibus_impl_create_engine (IBusEngineDesc *engine_desc)
 {
@@ -829,23 +850,8 @@ bus_ibus_impl_create_engine (IBusEngineDesc *engine_desc)
 
         if (!ibus_component_is_running (comp)) {
             ibus_component_start (comp, g_verbose);
-            g_get_current_time (&t1);
-            while (1) {
-                if (g_main_context_pending (NULL)) {
-                    g_main_context_iteration (NULL, FALSE);
-                    factory = bus_factory_proxy_get_from_engine (engine_desc);
-                    if (factory != NULL) {
-                        break;
-                    }
-                }
-                g_get_current_time (&t2);
-                if (t2.tv_sec - t1.tv_sec >= 5)
-                    break;
-            }
-        }
-        else {
-            factory = bus_factory_proxy_get_from_engine (engine_desc);
         }
+        factory = _get_factory_proxy (engine_desc);
     }
 
     if (factory == NULL) {