如何解决包装器代码中的“无效使用不完整类型”?

时间:2018-07-10 14:15:12

标签: c++ c wrapper

我正在尝试编写包装程序代码,以便可以从C调用C ++例程。C++例程将在EXE文件中,而C例程将在DLL中。包装器代码将在单独的DLL中。

我将https://www.teddy.ch/c++_library_in_c/上的代码用作蓝图,但是在该示例中,所有代码最终都存储在单个EXE中。我已经编辑了包装器代码以生成DLL。

我现在正在尝试仅构建包装器代码DLL。包装程序代码DLL由三个文件组成:Wrapper.h,Wrapper.cpp和datatypes.h。尝试编译包装器代码时,出现“无效使用不完整类型”和“转发声明”错误。我知道我收到了错误,因为声明了“ wr_Class”,但未定义。但是,在哪里为类添加定义,以及如何将其定义为C程序?

为什么我所基于的代码没有得到那些错误?他们也没有定义类型。曾经但是他们的代码可以编译并运行。我知道这一点是因为我复制并运行了它。我看到的最大区别是,它们的代码生成一个可执行文件,而我的代码生成一个DLL。

我已经在Stack Overflow上寻找了答案。但是我在这里看到的包装器代码示例要么不在其自己的DLL中生成包装器代码,和/或它们也未定义Class结构。

Wrapper.h-我添加了引导行编号以供参考。

 1. // *****************************************************************************
 2. // *                             W r a p p e r . h                             *
 3. // *                                                                           *
 4. // *                        C <----> Wrapper <----> C++                        *
 5. // *                                                                           *
 6. // *  Programmer:   Colleen Kobe                                               *
 7. // *                                                                           *
 8. // *  Project:      Small Business Innovative Research (SBIR) AF051-071,       *
 9. // *                Phase 2                                                    *
10. // *  Date:         July 09, 2018                                              *
11. // *    Revised:    tbd                                                        *
12. // *                                                                           *
13. // *  Description:  This C header file contains the "wrapper" code that allows *
14. // *                data to be passed between the C and C++ code in this       *
15. // *                project.                                                   *
16. // *                                                                           *
17. // *                This code was based on the code on:                        *
18. // *                https://www.teddy.ch/c++_library_in_c/                     *
19. // *                                                                           *
20. // *  Copyright :    (c) 2018 Infrared Telemetrics, Inc.                       *
21. // *****************************************************************************
22.
23. #ifndef WRAPPER_H
24. #define WRAPPER_H
25.
26. // =============================================================================
27. //                               Compiler Options
28. // =============================================================================
29.
30. // Make sure functions are exported with C linkage under C++ compilers.
31. #ifdef __cplusplus
32. extern "C"
33. {                                       // Export the code below with C linkage.
34. #endif                                  // Close this block below.
35.
36.
37. #define DllExport  __declspec (dllexport)   // Add this code to a DLL.
38. #define DllImport  __declspec (dllimport)
39. #define CALL_TYPE  __stdcall
40.
41.
42. // =============================================================================
43. //                             External Header Files
44. // =============================================================================
45. #include "datatypes.h"                  //  2 a
46.
47. // =============================================================================
48. //                               Global Constants
49. // =============================================================================
50. // tbd
51.
52. // =============================================================================
53. //                                 Global Types
54. // =============================================================================
55. typedef struct  wr_Class_Ignored    wr_Class;   // "C" definition of Wrapper_Class.
56.
57.
58. // =============================================================================
59. //                               Global Variables
60. // =============================================================================
61. // wr_Class*   Local_wr_Ptr;        // Local pointer to Wrapper_Class.
62.
63.
64. // =============================================================================
65. //                                  Prototypes
66. // =============================================================================
67. DllExport   void        CALL_TYPE   wr_Initialize               (void);         // Perform initialization.
68.
69. DllExport   wr_Class*   CALL_TYPE   wr_Create_New_Wrapper_Class (void);         // Create a "new" wrapper class.
70.
71. DllExport   void        CALL_TYPE   wr_Delete_Wrapper_Class     (wr_Class* wr); // "Delete" a wrapper class.
72.
73. DllExport   void        CALL_TYPE   wr_Terminate                (void);         // Perform termination.
74.
75. // .............................................................................
76. //  Add these in later, one by one
77. // .............................................................................
78.
79. // void     wr_Set_P07_NACK_Counter (wr_Class*  wr,     UInt32 n);   // Set Qty_P07_NACKS_Received.
80. // UInt32   wr_Get_P07_NACK_Counter (wr_Class*  wr);                 // Get Qty_P07_NACKS_Received.
81. // void     wr_mf_Set_P08_SysID     (wr_Class*  wr,     char   SysID_ch [gd_bg_P08_QTY_DATAWORDS]); // Set P08 SysID.
82. // void     wr_mf_Get_P08_SysID     (wr_Class*  wr,     char * SysID_ch [gd_bg_P08_QTY_DATAWORDS]); // Set P08 SysID.
83.
84.
85. #ifdef __cplusplus
86. }               // Export the following code with C linkage.
87. #endif
88.
89. #endif // WRAPPER_H

Wrapper.cpp-再次,我添加了引号以供参考

  1. // *****************************************************************************
  2. // *                           W r a p p e r . c p p                           *
  3. // *                                                                           *
  4. // *                        C <----> Wrapper <----> C++                        *
  5. // *                                                                           *
  6. // *  Programmer:   Colleen Kobe                                               *
  7. // *                                                                           *
  8. // *  Project:      Small Business Innovative Research (SBIR) AF051-071,       *
  9. // *                Phase 2                                                    *
 10. // *  Date:         July 09, 2018                                              *
 11. // *    Revised:    tbd                                                        *
 12. // *                                                                           *
 13. // *  Description:  This C header file contains the "wrapper" code that allows *
 14. // *                data to be passed between the C and C++ code in this       *
 15. // *                project.                                                   *
 16. // *                                                                           *
 17. // *                This code was based on the code on:                        *
 18. // *                https://www.teddy.ch/c++_library_in_c/                     *
 19. // *                                                                           *
 20. // *  Copyright :    (c) 2018 Infrared Telemetrics, Inc.                       *
 21. // *****************************************************************************
 22.
 23. // =============================================================================
 24. //                             External Header Files
 25. // =============================================================================
 26. #include "Wrapper.h"                    //  5 w
 27.
 28. // =============================================================================
 29. //                            Set Up Compiler Options
 30. // =============================================================================
 31. extern "C" {
 32.
 33. #define CALL_TYPE __stdcall
 34.
 35.
 36. // =============================================================================
 37. //                        Constants Public in This File
 38. // =============================================================================
 39. // tbd
 40.
 41. // =============================================================================
 42. //                               Global Variables
 43. // =============================================================================
 44. UInt32      Qty_P07_NACKS_Received;
 45. wr_Class*   Local_wr_Ptr;
 46.
 47. // P07_NACK_Pkts   P07_NACKS;           // tbd -- add in later
 48. // P07_Packet      P07_Pkt;             // tbd -- add in later
 49.
 50.
 51. // +===========================================================================+
 52. // |                               wr_Initialize                               |
 53. // |                                                                           |
 54. // |  Description:  Performs the necessary initialization for the Wrapper      |
 55. // |                code.                                                      |
 56. // +===========================================================================+
 57. DllExport   void        CALL_TYPE   wr_Initialize   (void)
 58. {
 59.     Local_wr_Ptr = wr_Create_New_Wrapper_Class ();  //  Create a new Local_wr_Ptr;
 60. } // wr_Initialize
 61.
 62.
 63. // +===========================================================================+
 64. // |                        wr_Create_New_Wrapper_Class                        |
 65. // |                                                                           |
 66. // |  Description:  Creates a new instance of Wrapper_Class, and returns a     |
 67. // |                pointer to it.                                             |
 68. // +===========================================================================+
 69. DllExport   wr_Class*   CALL_TYPE   wr_Create_New_Wrapper_Class (void)
 70. {
 71.
 72.     wr_Class*   temp_wr_ptr;    // for debugging--shorten this code when it's clear that it works.
 73.     temp_wr_ptr =   new wr_Class;
 74.
 75.     return  (temp_wr_ptr);
 76.
 77. } // wr_Create_New_Wrapper_Class
 78.
 79.
 80. // +===========================================================================+
 81. // |                          wr_Delete_Wrapper_Class                          |
 82. // |                                                                           |
 83. // |  Description:  Deletes an existing instance of Wrapper_Class.             |
 84. // +===========================================================================+
 85. DllExport   void        CALL_TYPE   wr_Delete_Wrapper_Class (wr_Class* wr)
 86. {
 87.     delete  wr;
 88. } // wr_Delete_Wrapper_Class
 89.
 90.
 91. // +===========================================================================+
 92. // |                               wr_Terminate                                |
 93. // |                                                                           |
 94. // |  Description:  Performs the necessary termination for the Wrapper code.   |
 95. // |                code.                                                      |
 96. // +===========================================================================+
 97. DllExport   void        CALL_TYPE   wr_Terminate   (void)
 98. {
 99.     wr_Delete_Wrapper_Class (Local_wr_Ptr);     //  Delete our Local_wr_Ptr.
100. } // wr_Terminate
101.
102.
103. // .............................................................................
104. //  Add these in later, one by one
105. // .............................................................................
106.
107. //     void wr_Class_int_set  (wr_Class* wr, int i)
108. //     {
109. //         wr->int_set  (i);
110. //     }
111.
112. //     int wr_Class_int_get  (wr_Class* wr)
113. //     {
114. //         return wr->int_get  ();
115. //     }
116.
117. //     void    wr_mf_Set_SysID (wr_Class* wr, char SysID_ch [gd_bg_P08_QTY_DATAWORDS])
118. //     {
119. // //        mf_Set_SysID (char SysID_ch [gd_bg_P08_QTY_DATAWORDS]);
120. //         ;
121. //     }
122.
123. }   // extern "C"

datatypes.h-我添加了引导行编号以供参考。您可能不需要这个,但是无论如何都在这里。

 1. // *****************************************************************************
 2. // *                           d a t a t y p e s . h                           *
 3. // *                                                                           *
 4. // *  Programmer:   Colleen Kobe                                               *
 5. // *                                                                           *
 6. // *  Project:      Small Business Innovative Research (SBIR) AF051-071        *
 7. // *  Date:         March 14, 2016                                             *
 8. // *    Revised:    July 10, 2018                                              *
 9. // *    Revised:    tbd                                                        *
10. // *                                                                           *
11. // *  Description:  This C header file contains public declarations for        *
12. // *                general use data types.                                    *
13. // *                                                                           *
14. // *                I created these type names to establish with absolute      *
15. // *                certainty the range and bit length of an integer variable. *
16. // *                                                                           *
17. // *  Copyright:    (c) 2018 Infrared Telemetrics, Inc.                        *
18. // *****************************************************************************
19.
20. #ifndef DATATYPES_H
21. #define DATATYPES_H
22.
23. // =============================================================================
24. //                            Set Up Compiler Options
25. // =============================================================================
26.
27. /* Make sure functions are exported with C linkage under C++ compilers. */
28. #ifdef __cplusplus
29. extern "C"
30. {               // Export the following code with C linkage.
31. #endif          // Notice that this block is still open. It is closed below.
32.
33. #define DllExport  __declspec (dllexport)
34. #define DllImport  __declspec (dllimport)
35. #define CALL_TYPE __stdcall
36.
37. // =============================================================================
38. //                             External Header Files
39. // =============================================================================
40. #include <stdint.h>                     //  1 c3
41.
42. // =============================================================================
43. //                               Global Constants
44. // =============================================================================
45. // None.
46.
47. // =============================================================================
48. //                                 Global Types
49. // =============================================================================
50.
51.                                                             //  --------------------------------------------------------------------------------
52.                                                             //                                       Range
53.                                                             //  --------------------------------------------------------------------------------
54. typedef signed char     Int08;                              //  -2** 7 .. (2** 7) - 1 [                       -128 ..                        127]
55. typedef short           Int16;                              //  -2**15 .. (2**15) - 1 [                    -32,768 ..                     32,767]
56. typedef int             Int32;  // AKA long                 //  -2**31 .. (2**31) - 1 [             -2,147,483,648 ..              2,147,483,647]
57. typedef int64_t         Int64;  // AKA long long            //  -2**63 .. (2**63) - 1 [ -9,223,372,036,854,775,808 ..  9,223,372,036,854,775,807]
58.
59. typedef unsigned char   UInt08;                             //       0 .. (2** 8) - 1 [                          0 ..                        255]
60. typedef unsigned short  UInt16;                             //       0 .. (2**16) - 1 [                          0 ..                     65,535]
61. typedef unsigned int    UInt32; // AKA DWORD                //       0 .. (2**32) - 1 [                          0 ..              4,294,967,295]
62. typedef uint64_t        UInt64; // AKA unsigned long long   //       0 .. (2**64) - 1 [                          0 .. 18,446,744,073,709,551,615]
63.
64.
65. // =============================================================================
66. //                                  Prototypes
67. // =============================================================================
68. // None.
69.
70. #ifdef __cplusplus
71. }               // export the following code with C linkage.
72. #endif
73.
74. #endif // DATATYPES_H

Buildlog.txt

 1. C:\Windows\system32\cmd.exe /C C:/MinGW/bin/mingw32-make.exe -j4 SHELL=cmd.exe -e -f  "Wrapper_Code.mk"  MakeIntermediateDirs && C:/MinGW/bin/mingw32-make.exe -j4 SHELL=cmd.exe -e -f  "Wrapper_Code.mk"  all
 2. ----------Building project:[ Wrapper_Code - Debug ]----------
 3. C:/MinGW/bin/g++.exe  -c  "F:/SBIR_Phase_II_A/Wrapper_Code/Wrapper.cpp" -g -O0 -Wall -c  -o ./Debug/Wrapper.cpp.o -I. -IC:\MinGW\include -IC:\wxWidgets\include -I. -I..\Background -I..\Behind_the_Scenes -I..\Main -I..\Resources -I..\Run_Here -I..\Wrapper_Code
 4. F:/SBIR_Phase_II_A/Wrapper_Code/Wrapper.cpp: In function 'wr_Class* wr_Create_New_Wrapper_Class()':
 5. F:/SBIR_Phase_II_A/Wrapper_Code/Wrapper.cpp:73:25: error: invalid use of incomplete type 'wr_Class {aka struct wr_Class_Ignored}'
 6.      temp_wr_ptr =   new wr_Class;
 7.                          ^~~~~~~~
 8. In file included from F:/SBIR_Phase_II_A/Wrapper_Code/Wrapper.cpp:26:0:
 9. F:/SBIR_Phase_II_A/Wrapper_Code/Wrapper.h:55:17: note: forward declaration of 'wr_Class {aka struct wr_Class_Ignored}'
10.  typedef struct  wr_Class_Ignored    wr_Class;   // "C" definition of Wrapper_Class.
11.                  ^~~~~~~~~~~~~~~~
12. F:/SBIR_Phase_II_A/Wrapper_Code/Wrapper.cpp: In function 'void wr_Delete_Wrapper_Class(wr_Class*)':
13. F:/SBIR_Phase_II_A/Wrapper_Code/Wrapper.cpp:87:13: warning: possible problem detected in invocation of delete operator: [-Wdelete-incomplete]
14.      delete  wr;
15.              ^~
16. F:/SBIR_Phase_II_A/Wrapper_Code/Wrapper.cpp:85:72: warning: 'wr' has incomplete type
17.  DllExport   void        CALL_TYPE   wr_Delete_Wrapper_Class (wr_Class* wr)
18.                                                                         ^~
19. In file included from F:/SBIR_Phase_II_A/Wrapper_Code/Wrapper.cpp:26:0:
20. F:/SBIR_Phase_II_A/Wrapper_Code/Wrapper.h:55:17: note: forward declaration of 'struct wr_Class_Ignored'
21.  typedef struct  wr_Class_Ignored    wr_Class;   // "C" definition of Wrapper_Class.
22.                  ^~~~~~~~~~~~~~~~
23. F:/SBIR_Phase_II_A/Wrapper_Code/Wrapper.cpp:87:13: note: neither the destructor nor the class-specific operator delete will be called, even if they are declared when the class is defined
24.      delete  wr;
25.              ^~
26. mingw32-make.exe: *** [Debug/Wrapper.cpp.o] Error 1
27. Wrapper_Code.mk:101: recipe for target 'Debug/Wrapper.cpp.o' failed
28. ====1 errors, 7 warnings====

如何解决“无效使用不完整类型”警告?我得到它是因为我正在构建DLL而不是EXE吗?如果是这样,关于如何声明Wrapper类,以便我能够成功处理C和C ++编译器和链接器,我还有其他选择吗?

建议?有评论吗?

编码环境:

 Windows 10
 C & C++
 MinGW / gcc / g++
 wxWidgets
 CodeLite v12.0.3

谢谢! 科琳

1 个答案:

答案 0 :(得分:0)

在Wrapper.cpp中,不存在struct wr_Class_Ignored的定义,因此您无法访问其任何成员。

此类的实际定义可能存在于单独的标头中,因此请将该标头包含在Wrapper.cpp中。您将看到从其建模的示例代码执行的操作相同。