문제

C++에서 C 소켓 API가 제대로 작동하도록 하는 데 문제가 있습니다. z/OS.

포함하고 있지만 sys/socket.h, 여전히 컴파일 시간 오류가 발생하여 다음과 같은 내용이 표시됩니다. AF_INET 정의되지 않았습니다.

제가 뭔가 분명한 것을 놓치고 있는 걸까요? 아니면 이것이 현재 진행 중인 사실과 관련이 있는 걸까요? z/OS 내 문제를 훨씬 더 복잡하게 만드는가?


업데이트:추가 조사를 통해 나는 다음과 같은 사실이 있음을 발견했습니다. #ifdef 내가 때리고 있는 것.보기에 z/OS 내가 사용하는 소켓의 "유형"을 정의하지 않으면 만족스럽지 않습니다.

#define _OE_SOCKETS

이제 개인적으로 이것이 무엇인지 전혀 모르겠습니다. _OE_SOCKETS 실제로는 다음을 위한 것입니다. 그렇다면 z/OS 소켓 프로그래머가 저 밖에 있습니다(여러분 3명 모두). 이 모든 것이 어떻게 작동하는지 요약해 주실 수 있나요?


테스트 앱

#include <sys/socket.h>

int main()
{
    return AF_INET;
}

컴파일/링크 출력:

cxx -Wc,xplink -Wl,xplink -o inet_test inet.C

"./inet.C", line 5.16: CCN5274 (S) The name lookup for "AF_INET" did not find a declaration.
CCN0797(I) Compilation failed for file ./inet.C. Object file not created.

sys/sockets.h를 확인하면 필요한 정의가 포함되어 있고 내가 알 수 있는 한 #ifdef 문에 의해 차단되지 않습니다.

그러나 나는 그것이 다음과 같은 내용을 포함하고 있음을 발견했습니다.

#ifdef __cplusplus
  extern "C" {
#endif

기본적으로 전체 파일을 캡슐화합니다.그것이 중요한지 확실하지 않습니다.

도움이 되었습니까?

해결책

IBM 매뉴얼 사본을 가까이에 보관하십시오.

IBM 출판물은 일반적으로 매우 훌륭하지만 형식에 익숙해져야 하고 답변을 어디서 찾을 수 있는지 알아야 합니다.사용하려는 기능이 "기능 테스트 매크로"에 의해 보호되는 경우가 많습니다.

친숙한 시스템 프로그래머에게 설치를 요청해야 합니다. XL C/C++ 런타임 라이브러리 참조:맨페이지 귀하의 시스템에서.그런 다음 "man connect"와 같은 작업을 수행하여 소켓 connect() API에 대한 매뉴얼 페이지를 가져올 수 있습니다.그렇게 하면 다음과 같습니다.

체재

X/열기

#define _XOPEN_SOURCE_EXTENDED 1
#include <sys/socket.h>

int connect(int socket, const struct sockaddr *address, socklen_t address_len);

버클리 소켓

#define _OE_SOCKETS
#include <sys/types.h>
#include <sys/socket.h>

int connect(int socket, struct sockaddr *address, int address_len);

다른 팁

저는 C++, GNU/Linux에서 BSD 소켓 API를 사용하는 데 아무런 문제가 없었습니다.내가 사용한 샘플 프로그램은 다음과 같습니다.

#include <sys/socket.h>

int
main()
{
    return AF_INET;
}

그래서 제 생각에는 z/OS가 아마도 여기에서 복잡한 요소일 것입니다. 그러나 저는 이전에 z/OS를 사용해 본 적이 없고 훨씬 덜 프로그래밍되었기 때문에 이에 대해 확실히 말할 수는 없습니다.:-피

참조 z/OS UNIX 시스템 서비스 소켓 사용 z/OS XL C/C++ 프로그래밍 안내서의 섹션을 참조하세요.필요한 헤더 파일을 포함하고 적절한 #define을 사용하고 있는지 확인하세요.

문서에 대한 링크는 수년에 걸쳐 변경되었지만 현재 위치를 찾아 쉽게 접근할 수 있습니다. 지원 및 다운로드 섹션 ~에 ibm.com 제목으로 문서를 검색합니다.

그러니 시도해 보세요

#define _OE_SOCKETS

sys/socket.h를 포함하기 전에

_OE_SOCKETS는 단순히 소켓 관련 기호 정의를 활성화/비활성화하는 것으로 보입니다.일부 라이브러리에서는 필요하지 않은 부분을 컴파일/링크하지 않도록 하기 위해 많은 매크로를 사용하는 것은 드문 일이 아닙니다.매크로는 다른 소켓 구현의 표준이 아니며 z/OS에 특정한 것으로 보입니다.

이 페이지를 살펴보십시오:
z/VM C 소켓 프로그램 컴파일 및 링크

당신은 한 번 살펴보고 싶을 수도 있습니다 cpp 소켓, 소켓 시스템 호출을 위한 C++ 래퍼입니다.이는 다양한 운영 체제(Win32, POSIX, Linux, *BSD)에서 작동합니다.나는 이것이 z/OS에서 작동할 것이라고 생각하지 않지만 그것이 사용하는 포함 파일을 살펴볼 수 있으며 다른 OS에서 잘 작동하는 테스트된 코드의 많은 예를 갖게 될 것입니다.

@잭스:그만큼 extern "C" 정말 중요해요.헤더 파일에 헤더 파일이 없으면(C++ 전용 헤더 파일이 아닌 경우) 다음을 묶어야 합니다. #include 그것으로:

extern "C" {
#include <sys/socket.h>
// include other similarly non-compliant header files
}

기본적으로 C++ 프로그램이 C 기반 기능에 연결하려는 경우 언제든지 extern "C" 중요합니다.실제로 이는 외부 참조에 사용된 이름이 일반적인 C++ 이름처럼 손상되지 않음을 의미합니다. 참조.

부인 성명:저는 C++ 프로그래머는 아니지만 C를 잘 알고 있습니다.나는 내가 가지고있는 일부 c 코드 에서이 전화를 적용했습니다.

또한 마크다운에서는 이러한 이상한 _을 밑줄로 표시했습니다.

다음과 같이 C 소켓 주위에 추상화 클래스를 작성할 수 있어야 합니다.

class my_sock {
    private int sock;
    private int socket_type;
    private socklen_t sock_len;
    private struct sockaddr_in server_addr;
    public char *server_ip;
    public unsigned short server_port;
};

그런 다음 소켓을 열고, 닫고, 패킷을 보내는 방법을 갖습니다.

예를 들어 공개 통화는 다음과 같을 수 있습니다.

int my_socket_connect()
{
    int return_code = 0;

    if ( this->socket_type != CLIENT_SOCK ) {
        cout << "This is a not a client socket!\n";
        return -1;
    }

    return_code = connect( this->local_sock, (struct sockaddr *) &this->server_addr, sizeof(this->server_addr));

    if( return_code < 0 ) {
        cout << "Connect() failure! %s\n", strerror(errno);
        return return_code;
    }

    return return_code;
}

대답은 다음과 같은 c89 플래그를 사용하는 것입니다.

 -D_OE_SOCKETS

예는 다음과 같습니다.

 bash-2.03$ c89 -D_OE_SOCKETS [filename].c

자세한 내용은 z/OS XLC/C++ 사용자 가이드에서 C89 옵션을 찾아보세요.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top