2011-11-03 8 views
7

저는 Ada에 모듈을 가지고 있고, 매개 변수 (스칼라 값)와 구조를 전달하는 C++의 많은 모듈을 가진 응용 프로그램에서 사용할 통신 미들웨어를 설계하고 있습니다. 응용 프로그램은 MS Windows XP 및 Windows 7에서 실행되고 C++ 부분은 MSVC++ 2008에서 개발되고 Ada 부분은 GPS/GNAT를 사용하여 개발됩니다. Ada 버전은 1995 년이지만 새로운 Ada 스펙을 사용할 가능성이있는 컴파일러 마이그레이션 (GPS/GNAT의 최신 버전) 중반에 있습니다.Ada Variant 레코드가 C++ 유니온과 이진 호환이 가능합니까?

미들웨어는 C++로 작성되었으며 시스템에서 사용되는 각 유형에 대해 하나의 put/get 함수를 지정할 필요가 없도록 모듈간에 전달되는 모든 유형을 포함하는 공용체 유형을 사용하고자합니다. .

질문은 C++ 유니온이 Ada 변형 레코드와 이진 호환이 가능합니까? 즉, C++ 유니온을 Ada 코드에 전달하면 Variant 레코드로 읽을 수 있습니까? (반대의 경우도 마찬가지)

나는 이것이 가능하기 위해 일부 조정이 필요할 것이라고 생각 ...

+1

플랫폼, 컴파일러 등을 지정해야 할 것입니다. –

+0

감사합니다. 방금 추가했습니다. 우리의 환경에 관한 정보. – Guarita

답변

2
(예 : C++ 조합은 에이다 변형 기록 할 동안 그 내용을 설명 멤버를 포함하지 않음)

아니요. 아타 변종 기록에는 자신을 진술 할 때 태그 필드가 있습니다. C 노조에는 그게 없다. (최소한 MSVC++ 및 GCC에는 없습니다 - ISO C에서 허용됩니다)

+0

Ahm, 네,하지만 제 질문은 C 유니온을 Ada의 Variant와 호환 가능하게 만들고 플러그 앤 플레이가 아닌 몇 가지 추가 작업을 할 수 있는지의 여부입니다. 이미 C 부분을 Ada 코드와 바이너리로 바꾸는 데 어려움이있을 것으로 예상됩니다. – Guarita

7

가능합니다.

Ada 2005는 프로그램이 주어진 구분 된 형식과 일부 공용체 간의 인터페이스 일치를 "[지정] 할 수있게 해주는 Unchecked_Union 플러그 - 마를 제공합니다 .Pragma는 관련 형식에 해당 형식을 부여 할 공간이 없도록 지정합니다 discriminant (s). "

RM 섹션을 읽은 후 변형 레코드를 정의하는 데 필요한 판별자를 사용하여 Ada 유형을 선언하지만 판별자가 저장 공간을 할당하지 않습니다. 저는이 판결문을 차후에 참조 할 수 없다는 것을 Ada 측의 의미로 받아들입니다. (다른 필드도 마찬가지입니다. 모든 필드는 C 호환 가능해야합니다. 자세한 내용은 RM B.3.3을 참조하십시오.)

필자는이 pragma를 사용한 적이 없으며 일부는 필요하다고 생각합니다. 실험을 통해 시스템과 작업 할 수 있습니다. 행운을 빕니다!

+2

실험의 일부는 당신이 GNAT에 MSVC++가 기대하는 방식으로 레코드를 배치 할 필요가 있는지 여부와 그 방법을 알려주는 것입니다. GNAT는 물론 GCC의 협약을 이해합니다. C 노조와 직접적인 유형으로 자신을 제한하는 한 너무 나쁘지 않아야합니다. –

+1

Windows의 GCC는 플랫폼 C ABI를 따르므로 Windows의 GNAT는 ABI와 MSVC++가 호환되어야합니다. – MSalters

3

언급 된 MSalter와 같이, 어떤 이유에서든 C 공용체에 변형을 지정하는 필드가 없으면 작동하지 않습니다. 이것은 C에서 필요하지 않으므로 종종 작동하지 않습니다. 그러나 부터이 해당 C 유형의 구현을 제어하면 제대로 작동 할 수 있습니다. 어떤 조합이 사용되는지 지정하는 조합 앞에 필드가 있어야합니다.

C 유니온 구조체와 완벽하게 이진 호환되도록하려면 레코드 표현 절과 함께 간단한 Ada 레코드 유형으로 이동하여 필드가 동일한 위치에 배치되어 있는지 확인해야합니다 당신의 C 컴파일러가 그것을 넣습니다. 그리고 네, 레이아웃을 변경시키는 C 컴파일러 변경에 취약하게 만듭니다. C 코드에서 비트 필드를 사용하여 보호 할 수는 있지만 Ada 레코드 rep 절이 실제로 할 수있는 방식으로는 충분하지 않습니다. 그것이 우리가 하위 작업을 위해 Ada를 사용하는 이유 중 하나입니다.

내가 마지막으로 확인했을 때 Gnat의 Windows 버전은 VisualStudio 바이너리와 링커 호환되지 않았 음을 언급해야합니다. 두 컴파일러가 함께 작동하도록하는 유일한 방법은 전체 인터페이스를 DLL에 넣는 것입니다. 그렇지 않으면 GCC를 사용하여 C++ 시스템을 구축하거나 ObjectAda과 같은 다른 Ada 컴파일러를 사용해야합니다.

+0

"MSalters가 언급했듯이 어떤 이유에서든 C 유니온에 변형을 지정하는 필드가 포함되어 있지 않으면 작동하지 않습니다. 어쩌면 내가 이런 구조체를 할 수 : struct foo { some_tag_type 태그; 노동 조합 { ... } my_union; } ?? – Guarita

+0

@guarita 유용한 링크를 얻으려면 내 대답을 참조하십시오. 저는이 아이디어로 올바른 길을 가고 있다고 생각합니다. – NWS

+0

예. @NWS가 말했듯이, 당신은 올바른 길을 가고 있습니다. –

5

예.

Ada는 C/C++ 조합과 호환됩니다. 그것을 수행하는 방법은 here을 참조하십시오 (pdf) 특히 페이지 5는 유니온 & 태그로 작업하는 방법을 보여줍니다. Discriminant 레코드를 사용하는 경우에도 동일해야합니다. (주의 : 아마도 사용하는 컴파일러가 아닐지 모르지만, 당신의 행동이 똑같지 않으면 매우 놀랄 것이다!)

+1

다른 Ada/C/C++ 컴파일러가 큰 문제없이이 문제를 처리 할 것으로 기대할 수 있다는 점에 대해서는 다소 낙관적 인 생각이지만 문제의 유용한 가이드입니다. –

+0

@Marc My Optimism은 Ada 컴파일러의 유효성을 확인해야하므로 동일한 작업을 수행 할 수 있어야합니다. – NWS

+0

Ada 측이 걱정하지 않아도됩니다. 레이아웃과 다른 컴파일러들 사이의 미세 관을 연결하여 나를 회의적으로 만든다 (낙천주의의 :-). 나는 바인딩에 대해 낯선 사람이 아니며 심지어 GNAT와 gcc 사이에서 데이터 구조를 공유하는 경우에도주의가 필요합니다. –