⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 cdl2.cxx

📁 eCos1.31版
💻 CXX
字号:
//==========================================================================////      cdl2.cxx////      Tests for the CdlHandle class.////==========================================================================//####COPYRIGHTBEGIN####//                                                                          // ----------------------------------------------------------------------------// Copyright (C) 1999, 2000 Red Hat, Inc.//// This file is part of the eCos host tools.//// This program is free software; you can redistribute it and/or modify it // under the terms of the GNU General Public License as published by the Free // Software Foundation; either version 2 of the License, or (at your option) // any later version.// // This program is distributed in the hope that it will be useful, but WITHOUT // ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or // FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for // more details.// // You should have received a copy of the GNU General Public License along with// this program; if not, write to the Free Software Foundation, Inc., // 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.//// ----------------------------------------------------------------------------//                                                                          //####COPYRIGHTEND####//==========================================================================//#####DESCRIPTIONBEGIN####                                             //// Author(s):           bartv// Contributors:        bartv// Date:                1999-01-12// Description:         Large parts of libcdl are implemented using a//                      CdlHandle template and a CdlRefcountSupport class.//                      This tests check that these both work as expected.////####DESCRIPTIONEND####//==========================================================================#include <cstdio>#include <cdlconfig.h>#include <cdl.hxx>#include <cyg/infra/cyg_ass.h>#include <cyg/infra/cyg_trac.h>#include <cyg/infra/testcase.h>#include <cstdlib>#ifndef CYGBLD_LIBCDL_USE_SMART_POINTERSintmain(int argc, char** argv){    CYG_TEST_FAIL_FINISH("Smart pointers not yet enabled - waiting for a working version of Visual C++");    return EXIT_FAILURE;}#else // CYGBLD_LIBCDL_USE_SMART_POINTERS// ----------------------------------------------------------------------------// Miscellaneous statics.// This routine controls the return value of a class1_body check_this()// operation, allowing test code to make sure that using check_this()// on a smart pointer works as expected.static bool check_this_ok = true;// ----------------------------------------------------------------------------// This test case makes use of three implementation classes. It is necessary// to have forward declarations of these, and then it is possible to define// handle classes for each one.class class01_body;class class02_body;class derived_body;typedef CdlHandle<class01_body> class01;typedef CdlHandle<class02_body> class02;typedef CdlHandle<derived_body> derived;// ----------------------------------------------------------------------------// This test needs three additional classes which are reference-counted and// which are accessed via CdlHandle smart pointers. It is necessary to start class class01_body : public CdlRefcountSupport {    friend class CdlTest;      public:    static int class01_objects;    class01_body() : CdlRefcountSupport() {        class01_objects++;        object_number = class01_objects;        modifiable    = 0;        class01_body_cookie = class01_body_magic;    }    ~class01_body() {        class01_objects--;        class01_body_cookie = class01_body_invalid;    }    int    get_number(void) {        return object_number;    }    void    modify(void) {        modifiable++;    }    bool check_this(cyg_assert_class_zeal zeal) const {        CYG_UNUSED_PARAM(cyg_assert_class_zeal, zeal);        if (class01_body_magic != class01_body_cookie) {            return false;        }        return check_this_ok;    }      private:    // Which object is this?    int object_number;    int modifiable;        class01_body(const class01_body&);    class01_body& operator=(const class01_body&);    enum {        class01_body_invalid     = 0,        class01_body_magic       = 0x015b19d6    } class01_body_cookie;};class class02_body : public CdlRefcountSupport {    friend class CdlTest;      public:    static int class02_objects;    class02_body() : CdlRefcountSupport() {        class02_objects++;        class02_body_cookie = class02_body_magic;    }    ~class02_body() {        class02_objects--;        class02_body_cookie = class02_body_invalid;    }    bool check_this(cyg_assert_class_zeal zeal) const {        CYG_UNUSED_PARAM(cyg_assert_class_zeal, zeal);        return class02_body_magic == class02_body_cookie;    }  private:    class02_body(const class02_body&);    class02_body& operator=(const class02_body&);    enum {        class02_body_invalid     = 0,        class02_body_magic       = 0x3225c96c    } class02_body_cookie;};class derived_body : public class01_body {    friend class CdlTest;      public:    static int derived_objects;    derived_body() : class01_body() {        derived_objects++;        derived_body_cookie = derived_body_magic;    }    ~derived_body() {        derived_objects--;        derived_body_cookie = derived_body_invalid;    }    bool check_this(cyg_assert_class_zeal zeal) const {        if (derived_body_magic != derived_body_cookie) {            return false;        }        return class01_body::check_this(zeal);    }  private:    derived_body(const derived_body&);    derived_body& operator=(const derived_body&);    enum {        derived_body_invalid    = 0,        derived_body_magic      = 0x7ed15350    } derived_body_cookie;};int class01_body::class01_objects   = 0;int class02_body::class02_objects   = 0;int derived_body::derived_objects   = 0;// ----------------------------------------------------------------------------// The actual test code.boolcheck_const_arg(const class01 const_ptr){    // Make sure that read-only access is allowed and goes to the right    // object    if (!const_ptr->check_this(cyg_quick)) {        CYG_TEST_FAIL("check_this() on a constant pointer should be fine");        return false;    }    check_this_ok = false;    if (const_ptr->check_this(cyg_quick)) {        CYG_TEST_FAIL("check_this() on a constant pointer should be fine");        check_this_ok = true;        return false;    }    check_this_ok = true;    return true;}intmain(int argc, char** argv){    bool ok = true;    // Make sure that smart pointers do not impose any kind of overhead.    if ((sizeof(void *) != sizeof(class01)) ||        (sizeof(void *) != sizeof(class02)) ||        (sizeof(void *) != sizeof(derived))) {        CYG_TEST_FAIL("smart pointers are not the same size as dumb pointers");    } else {        CYG_TEST_PASS("smart pointers are the same size as dumb pointers");    }        // Start by creating a number of objects to be manipulated.    class01_body *      class01_obj1    = new class01_body;    class01_body *      class01_obj2    = new class01_body;    class02_body *      class02_obj1    = new class02_body;    derived_body *      derived_obj1    = new derived_body;    // Quick sanity check    if ((1 != derived_body::derived_objects) ||        (1 != class02_body::class02_objects) ||        (3 != class01_body::class01_objects)) {        CYG_TEST_FAIL("Testcase has created an invalid number of objects");    }    // Convert the basic objects to smart pointers. If this code compiles    // then the test succeeds.    class01     class01_ptr1    = class01(class01_obj1);    class01     class01_ptr2    = class01(class01_obj2);    class02     class02_ptr1    = class02(class02_obj1);    derived     derived_ptr1    = derived(derived_obj1);    CYG_TEST_PASS("conversion to smart pointers works");    // Also create a couple of other smart pointers. These should be    // initialised to 0.    class01      class01_ptr3;    class01      class01_ptr4     = 0;    class01      class01_ptr5     = class01(0);    CYG_TEST_PASS("smart pointers can have the value zero");    // Try to dereference the smart pointers.    if ((1 != class01_ptr1->get_number()) ||        (2 != class01_ptr2->get_number()) ||        (3 != derived_ptr1->get_number())) {        CYG_TEST_FAIL("-> dereferencing operator broken");    } else {        CYG_TEST_PASS("-> dereferencing operator functional");    }    if ((1 != (*class01_ptr1).get_number()) ||        (2 != (*class01_ptr2).get_number()) ||        (3 != (*derived_ptr1).get_number())) {        CYG_TEST_FAIL("* dereferencing operator broken");    } else {        CYG_TEST_PASS("* dereferencing operator functional");    }    // Also try to access the check_this() member functions    if (!class01_ptr1->check_this(cyg_quick)) {    }        // Do a couple of if's. This checks that the !operator is    // functional. Some of the checks are there to make sure that the    // compiler does the right thing.    ok = true;    if (!class01_ptr1) {        CYG_TEST_FAIL("!(assigned smart pointer) is true");        ok = false;    }    if (0 == class01_ptr1) {        CYG_TEST_FAIL("0 == assigned smart pointer");        ok = false;    }    if (0 != class01_ptr3) {        CYG_TEST_FAIL("0 != unassigned smart pointer");        ok = false;    }    if (class01_ptr1 == 0) {        CYG_TEST_FAIL("0 == assigned smart pointer");        ok = false;    }    if (class01_ptr3 != 0) {        CYG_TEST_FAIL("0 != unassigned smart pointer");        ok = false;    }    if (class01_ptr1 == class01_ptr2) {        CYG_TEST_FAIL("comparing two different smart pointers succeeds");        ok = false;    }    if (class01_ptr1 != class01_ptr2) {        // Do nothing    } else {        CYG_TEST_FAIL("comparing two different smart pointers succeeds");        ok = false;    }#if 0    // Comparing base and derived smart pointers directly does not work yet.    if (class01_ptr1 == derived_ptr1) {        CYG_TEST_FAIL("comparing different base and derived pointers succeeds");    }#endif    if (ok) {        CYG_TEST_PASS("smart pointer comparisons work");    }        // Try some  assignment operators.    class01_ptr3 = class01_ptr1;    class01_ptr4 = derived_ptr1;    class01_ptr5 = class01_ptr2;    // After doing all of these assignments there should be no change in    // the number of underlying objects.    ok = true;    if ((1 != derived_body::derived_objects) ||        (1 != class02_body::class02_objects)   ||        (3 != class01_body::class01_objects)) {        ok = false;        CYG_TEST_FAIL("Assignment of smart pointers has changed the underlying number of objects");    }    if ((class01_ptr1 != class01_ptr3) ||        (class01_ptr2 != class01_ptr5)) {        ok = false;        CYG_TEST_FAIL("Assignment of smart pointers has not worked");    }    if (class01_ptr4.get_dumb_pointer() != derived_ptr1.get_dumb_pointer()) {        ok = false;        CYG_TEST_FAIL("Assignment of derived to base smart pointer has not worked");    }    if ((2 != class01_ptr1->get_refcount()) ||        (2 != class01_ptr2->get_refcount()) ||        (2 != class01_ptr4->get_refcount()) ||        (2 != derived_ptr1->get_refcount())) {        ok = false;        CYG_TEST_FAIL("Reference counts after assignment operators do not match up");    }    if (ok) {        CYG_TEST_PASS("Assignment of smart pointers");    }    // Now try assigning zero. Incidentally this is necessary if the underlying    // objects are to be destroyed again at the end.    class01_ptr3 = 0;    class01_ptr4 = 0;    class01_ptr5 = 0;    ok = true;    if (0 != class01_ptr3) {        ok = false;        CYG_TEST_FAIL("assigning 0 to a smart pointer does not work");    }    if ((1 != class01_ptr1->get_refcount()) ||        (1 != class01_ptr2->get_refcount()) ||        (1 != derived_ptr1->get_refcount())) {        ok = false;        CYG_TEST_FAIL("Reference counts after assignment operators do not match up");    }    if (ok) {        CYG_TEST_PASS("Assigning zero to smart pointers");    }    // Make sure that implicit casts to const work. This is really    // a compiler test.    if (check_const_arg(class01_ptr1) &&        check_const_arg(derived_ptr1)) {        CYG_TEST_PASS("Implicit cast to const smart pointer");    }    #if 0    // All of this code should fail to compile.    // Applying delete to a smart pointer does not work. Use destroy() instead.    delete class01_ptr1;#endif#if 0    // Attempts to do incompatible assignments should fail.    class01_ptr1 = class02_ptr1;#endif#if 0        // Comparing completely different types should fail.    if (class01_ptr1 == class02_ptr1) {        CYG_TEST_FAIL("it should not be possible to compare objects of different types");    }#endif#if 0    {        const class01 const_class01_ptr = class01_ptr1;        const_class01_ptr->modify();    }#endif#if 0    {        const class01 const_derived_ptr = derived_ptr1;        const_derived_ptr->modify();    }#endif        // Check that destroy() actually gets rid of the underlying objects.    class01_ptr1.destroy();    class01_ptr2.destroy();    class02_ptr1.destroy();    derived_ptr1.destroy();    if ((0 != derived_body::derived_objects) ||        (0 != class02_body::class02_objects)    ||        (0 != class01_body::class01_objects)) {        CYG_TEST_FAIL("There are still objects after the smart pointers have been destroyed");    } else {        CYG_TEST_PASS("Using destroy() on the smart pointers cleans up the underlying objects");    }    return EXIT_SUCCESS;}#endif

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -