sl@0: /* GObject - GLib Type, Object, Parameter and Signal Library sl@0: * Copyright (C) 2005 Red Hat, Inc. sl@0: * Portions copyright (c) 2006-2009 Nokia Corporation. All rights reserved. sl@0: * This library is free software; you can redistribute it and/or sl@0: * modify it under the terms of the GNU Lesser General Public sl@0: * License as published by the Free Software Foundation; either sl@0: * version 2 of the License, or (at your option) any later version. sl@0: * sl@0: * This library is distributed in the hope that it will be useful, sl@0: * but WITHOUT ANY WARRANTY; without even the implied warranty of sl@0: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU sl@0: * Lesser General Public License for more details. sl@0: * sl@0: * You should have received a copy of the GNU Lesser General sl@0: * Public License along with this library; if not, write to the sl@0: * Free Software Foundation, Inc., 59 Temple Place, Suite 330, sl@0: * Boston, MA 02111-1307, USA. sl@0: */ sl@0: sl@0: #undef G_LOG_DOMAIN sl@0: #define G_LOG_DOMAIN "TestReferences" sl@0: sl@0: #undef G_DISABLE_ASSERT sl@0: #undef G_DISABLE_CHECKS sl@0: #undef G_DISABLE_CAST_CHECKS sl@0: sl@0: #include sl@0: sl@0: #ifdef __SYMBIAN32__ sl@0: #include "mrt2_glib2_test.h" sl@0: #endif /*__SYMBIAN32__*/ sl@0: /* This test tests weak and toggle references sl@0: */ sl@0: sl@0: static GObject *global_object; sl@0: sl@0: static gboolean object_destroyed; sl@0: static gboolean weak_ref1_notified; sl@0: static gboolean weak_ref2_notified; sl@0: static gboolean toggle_ref1_weakened; sl@0: static gboolean toggle_ref1_strengthened; sl@0: static gboolean toggle_ref2_weakened; sl@0: static gboolean toggle_ref2_strengthened; sl@0: static gboolean toggle_ref3_weakened; sl@0: static gboolean toggle_ref3_strengthened; sl@0: sl@0: /* sl@0: * TestObject, a parent class for TestObject sl@0: */ sl@0: #define TEST_TYPE_OBJECT (test_object_get_type ()) sl@0: typedef struct _TestObject TestObject; sl@0: typedef struct _TestObjectClass TestObjectClass; sl@0: sl@0: struct _TestObject sl@0: { sl@0: GObject parent_instance; sl@0: }; sl@0: struct _TestObjectClass sl@0: { sl@0: GObjectClass parent_class; sl@0: }; sl@0: sl@0: G_DEFINE_TYPE (TestObject, test_object, G_TYPE_OBJECT); sl@0: sl@0: static void sl@0: test_object_finalize (GObject *object) sl@0: { sl@0: object_destroyed = TRUE; sl@0: sl@0: G_OBJECT_CLASS (test_object_parent_class)->finalize (object); sl@0: } sl@0: sl@0: static void sl@0: test_object_class_init (TestObjectClass *class) sl@0: { sl@0: GObjectClass *object_class = G_OBJECT_CLASS (class); sl@0: sl@0: object_class->finalize = test_object_finalize; sl@0: } sl@0: sl@0: static void sl@0: test_object_init (TestObject *test_object) sl@0: { sl@0: } sl@0: sl@0: static void sl@0: clear_flags (void) sl@0: { sl@0: object_destroyed = FALSE; sl@0: weak_ref1_notified = FALSE; sl@0: weak_ref2_notified = FALSE; sl@0: toggle_ref1_weakened = FALSE; sl@0: toggle_ref1_strengthened = FALSE; sl@0: toggle_ref2_weakened = FALSE; sl@0: toggle_ref2_strengthened = FALSE; sl@0: toggle_ref3_weakened = FALSE; sl@0: toggle_ref3_strengthened = FALSE; sl@0: } sl@0: sl@0: static void sl@0: weak_ref1 (gpointer data, sl@0: GObject *object) sl@0: { sl@0: g_assert (object == global_object); sl@0: g_assert (data == GUINT_TO_POINTER (42)); sl@0: sl@0: weak_ref1_notified = TRUE; sl@0: } sl@0: sl@0: static void sl@0: weak_ref2 (gpointer data, sl@0: GObject *object) sl@0: { sl@0: g_assert (object == global_object); sl@0: g_assert (data == GUINT_TO_POINTER (24)); sl@0: sl@0: weak_ref2_notified = TRUE; sl@0: } sl@0: sl@0: static void sl@0: toggle_ref1 (gpointer data, sl@0: GObject *object, sl@0: gboolean is_last_ref) sl@0: { sl@0: g_assert (object == global_object); sl@0: g_assert (data == GUINT_TO_POINTER (42)); sl@0: sl@0: if (is_last_ref) sl@0: toggle_ref1_weakened = TRUE; sl@0: else sl@0: toggle_ref1_strengthened = TRUE; sl@0: } sl@0: sl@0: static void sl@0: toggle_ref2 (gpointer data, sl@0: GObject *object, sl@0: gboolean is_last_ref) sl@0: { sl@0: g_assert (object == global_object); sl@0: g_assert (data == GUINT_TO_POINTER (24)); sl@0: sl@0: if (is_last_ref) sl@0: toggle_ref2_weakened = TRUE; sl@0: else sl@0: toggle_ref2_strengthened = TRUE; sl@0: } sl@0: sl@0: static void sl@0: toggle_ref3 (gpointer data, sl@0: GObject *object, sl@0: gboolean is_last_ref) sl@0: { sl@0: g_assert (object == global_object); sl@0: g_assert (data == GUINT_TO_POINTER (34)); sl@0: sl@0: if (is_last_ref) sl@0: { sl@0: toggle_ref3_weakened = TRUE; sl@0: g_object_remove_toggle_ref (object, toggle_ref3, GUINT_TO_POINTER (34)); sl@0: } sl@0: else sl@0: toggle_ref3_strengthened = TRUE; sl@0: } sl@0: sl@0: int sl@0: main (int argc, sl@0: char *argv[]) sl@0: { sl@0: GObject *object; sl@0: sl@0: g_log_set_always_fatal (g_log_set_always_fatal (G_LOG_FATAL_MASK) | sl@0: G_LOG_LEVEL_WARNING | sl@0: G_LOG_LEVEL_CRITICAL); sl@0: g_type_init (); sl@0: sl@0: #ifdef __SYMBIAN32__ sl@0: g_log_set_handler (NULL, G_LOG_FLAG_FATAL| G_LOG_FLAG_RECURSION | G_LOG_LEVEL_CRITICAL | G_LOG_LEVEL_WARNING | G_LOG_LEVEL_MESSAGE | G_LOG_LEVEL_INFO | G_LOG_LEVEL_DEBUG, &mrtLogHandler, NULL); sl@0: #endif /*__SYMBIAN32__*/ sl@0: /* Test basic weak reference operation sl@0: */ sl@0: global_object = object = g_object_new (TEST_TYPE_OBJECT, NULL); sl@0: sl@0: g_object_weak_ref (object, weak_ref1, GUINT_TO_POINTER (42)); sl@0: sl@0: clear_flags (); sl@0: g_object_unref (object); sl@0: g_assert (weak_ref1_notified == TRUE); sl@0: g_assert (object_destroyed == TRUE); sl@0: sl@0: /* Test two weak references at once sl@0: */ sl@0: global_object = object = g_object_new (TEST_TYPE_OBJECT, NULL); sl@0: sl@0: g_object_weak_ref (object, weak_ref1, GUINT_TO_POINTER (42)); sl@0: g_object_weak_ref (object, weak_ref2, GUINT_TO_POINTER (24)); sl@0: sl@0: clear_flags (); sl@0: g_object_unref (object); sl@0: g_assert (weak_ref1_notified == TRUE); sl@0: g_assert (weak_ref2_notified == TRUE); sl@0: g_assert (object_destroyed == TRUE); sl@0: sl@0: /* Test remove weak references sl@0: */ sl@0: global_object = object = g_object_new (TEST_TYPE_OBJECT, NULL); sl@0: sl@0: g_object_weak_ref (object, weak_ref1, GUINT_TO_POINTER (42)); sl@0: g_object_weak_ref (object, weak_ref2, GUINT_TO_POINTER (24)); sl@0: g_object_weak_unref (object, weak_ref1, GUINT_TO_POINTER (42)); sl@0: sl@0: clear_flags (); sl@0: g_object_unref (object); sl@0: g_assert (weak_ref1_notified == FALSE); sl@0: g_assert (weak_ref2_notified == TRUE); sl@0: g_assert (object_destroyed == TRUE); sl@0: sl@0: /* Test basic toggle reference operation sl@0: */ sl@0: global_object = object = g_object_new (TEST_TYPE_OBJECT, NULL); sl@0: sl@0: g_object_add_toggle_ref (object, toggle_ref1, GUINT_TO_POINTER (42)); sl@0: sl@0: clear_flags (); sl@0: g_object_unref (object); sl@0: g_assert (toggle_ref1_weakened == TRUE); sl@0: g_assert (toggle_ref1_strengthened == FALSE); sl@0: g_assert (object_destroyed == FALSE); sl@0: sl@0: clear_flags (); sl@0: g_object_ref (object); sl@0: g_assert (toggle_ref1_weakened == FALSE); sl@0: g_assert (toggle_ref1_strengthened == TRUE); sl@0: g_assert (object_destroyed == FALSE); sl@0: sl@0: g_object_unref (object); sl@0: sl@0: clear_flags (); sl@0: g_object_remove_toggle_ref (object, toggle_ref1, GUINT_TO_POINTER (42)); sl@0: g_assert (toggle_ref1_weakened == FALSE); sl@0: g_assert (toggle_ref1_strengthened == FALSE); sl@0: g_assert (object_destroyed == TRUE); sl@0: sl@0: global_object = object = g_object_new (TEST_TYPE_OBJECT, NULL); sl@0: sl@0: /* Test two toggle references at once sl@0: */ sl@0: g_object_add_toggle_ref (object, toggle_ref1, GUINT_TO_POINTER (42)); sl@0: g_object_add_toggle_ref (object, toggle_ref2, GUINT_TO_POINTER (24)); sl@0: sl@0: clear_flags (); sl@0: g_object_unref (object); sl@0: g_assert (toggle_ref1_weakened == FALSE); sl@0: g_assert (toggle_ref1_strengthened == FALSE); sl@0: g_assert (toggle_ref2_weakened == FALSE); sl@0: g_assert (toggle_ref2_strengthened == FALSE); sl@0: g_assert (object_destroyed == FALSE); sl@0: sl@0: clear_flags (); sl@0: g_object_remove_toggle_ref (object, toggle_ref1, GUINT_TO_POINTER (42)); sl@0: g_assert (toggle_ref1_weakened == FALSE); sl@0: g_assert (toggle_ref1_strengthened == FALSE); sl@0: g_assert (toggle_ref2_weakened == TRUE); sl@0: g_assert (toggle_ref2_strengthened == FALSE); sl@0: g_assert (object_destroyed == FALSE); sl@0: sl@0: clear_flags (); sl@0: g_object_remove_toggle_ref (object, toggle_ref2, GUINT_TO_POINTER (24)); sl@0: g_assert (toggle_ref1_weakened == FALSE); sl@0: g_assert (toggle_ref1_strengthened == FALSE); sl@0: g_assert (toggle_ref2_weakened == FALSE); sl@0: g_assert (toggle_ref2_strengthened == FALSE); sl@0: g_assert (object_destroyed == TRUE); sl@0: sl@0: /* Test a toggle reference that removes itself sl@0: */ sl@0: global_object = object = g_object_new (TEST_TYPE_OBJECT, NULL); sl@0: sl@0: g_object_add_toggle_ref (object, toggle_ref3, GUINT_TO_POINTER (34)); sl@0: sl@0: clear_flags (); sl@0: g_object_unref (object); sl@0: g_assert (toggle_ref3_weakened == TRUE); sl@0: g_assert (toggle_ref3_strengthened == FALSE); sl@0: g_assert (object_destroyed == TRUE); sl@0: sl@0: #ifdef __SYMBIAN32__ sl@0: testResultXml("references"); sl@0: #endif /*__SYMBIAN32__*/ sl@0: return 0; sl@0: }