From 24bf52bc691cca9f8b3a668e26b4dd695ec4991c Mon Sep 17 00:00:00 2001 From: Patrick Monnerat Date: Tue, 20 May 2008 10:21:50 +0000 Subject: [PATCH] Adapting last changes to OS400: _ Updated packages/OS400/curl.inc.in with new definitions. _ New connect/bind/sendto/recvfrom wrappers to support AF_UNIX sockets. _ Include files line length shortened below 100 chars. _ Const parameter in lib/qssl.[ch]. _ Typos in packages/OS400/initscript.sh. --- include/curl/curl.h | 18 +++-- include/curl/mprintf.h | 6 +- include/curl/multi.h | 2 +- include/curl/typecheck-gcc.h | 17 ++-- lib/config-os400.h | 6 ++ lib/qssl.c | 6 +- lib/qssl.h | 2 +- lib/setup-os400.h | 16 ++++ packages/OS400/curl.inc.in | 35 +++++++-- packages/OS400/initscript.sh | 4 +- packages/OS400/os400sys.c | 146 ++++++++++++++++++++++++++++++++++- 11 files changed, 230 insertions(+), 28 deletions(-) diff --git a/include/curl/curl.h b/include/curl/curl.h index 042367466..1e7f3b3fb 100644 --- a/include/curl/curl.h +++ b/include/curl/curl.h @@ -33,7 +33,8 @@ * Define WIN32 when build target is Win32 API */ -#if (defined(_WIN32) || defined(__WIN32__)) && !defined(WIN32) && !defined(__SYMBIAN32__) +#if (defined(_WIN32) || defined(__WIN32__)) && \ + !defined(WIN32) && !defined(__SYMBIAN32__) #define WIN32 #endif @@ -62,7 +63,8 @@ /* HP-UX systems version 9, 10 and 11 lack sys/select.h and so does oldish libc5-based Linux systems. Only include it on system that are known to require it! */ -#if defined(_AIX) || defined(__NOVELL_LIBC__) || defined(__NetBSD__) || defined(__minix) || defined(__SYMBIAN32__) +#if defined(_AIX) || defined(__NOVELL_LIBC__) || defined(__NetBSD__) || \ + defined(__minix) || defined(__SYMBIAN32__) #include #endif @@ -89,7 +91,8 @@ typedef void CURL; * Decorate exportable functions for Win32 and Symbian OS DLL linking. * This avoids using a .def file for building libcurl.dll. */ -#if (defined(WIN32) || defined(_WIN32) || defined(__SYMBIAN32__)) && !defined(CURL_STATICLIB) +#if (defined(WIN32) || defined(_WIN32) || defined(__SYMBIAN32__)) && \ + !defined(CURL_STATICLIB) #if defined(BUILDING_LIBCURL) #define CURL_EXTERN __declspec(dllexport) #else @@ -118,7 +121,8 @@ typedef void CURL; * Note: "pocc -Ze" is MSVC compatibility mode and this sets _MSC_VER! */ -#if (defined(_MSC_VER) && !defined(__POCC__)) || (defined(__LCC__) && defined(WIN32)) +#if (defined(_MSC_VER) && !defined(__POCC__)) || (defined(__LCC__) && \ + defined(WIN32)) /* MSVC */ #ifdef _WIN32_WCE typedef long curl_off_t; @@ -1379,9 +1383,11 @@ CURL_EXTERN CURLFORMcode curl_formadd(struct curl_httppost **httppost, /* * callback function for curl_formget() - * The void *arg pointer will be the one passed as second argument to curl_formget(). + * The void *arg pointer will be the one passed as second argument to + * curl_formget(). * The character buffer passed to it must not be freed. - * Should return the buffer length passed to it as the argument "len" on success. + * Should return the buffer length passed to it as the argument "len" on + * success. */ typedef size_t (*curl_formget_callback)(void *arg, const char *buf, size_t len); diff --git a/include/curl/mprintf.h b/include/curl/mprintf.h index 5c526882f..d6d7f4455 100644 --- a/include/curl/mprintf.h +++ b/include/curl/mprintf.h @@ -35,11 +35,13 @@ extern "C" { CURL_EXTERN int curl_mprintf(const char *format, ...); CURL_EXTERN int curl_mfprintf(FILE *fd, const char *format, ...); CURL_EXTERN int curl_msprintf(char *buffer, const char *format, ...); -CURL_EXTERN int curl_msnprintf(char *buffer, size_t maxlength, const char *format, ...); +CURL_EXTERN int curl_msnprintf(char *buffer, size_t maxlength, + const char *format, ...); CURL_EXTERN int curl_mvprintf(const char *format, va_list args); CURL_EXTERN int curl_mvfprintf(FILE *fd, const char *format, va_list args); CURL_EXTERN int curl_mvsprintf(char *buffer, const char *format, va_list args); -CURL_EXTERN int curl_mvsnprintf(char *buffer, size_t maxlength, const char *format, va_list args); +CURL_EXTERN int curl_mvsnprintf(char *buffer, size_t maxlength, + const char *format, va_list args); CURL_EXTERN char *curl_maprintf(const char *format, ...); CURL_EXTERN char *curl_mvaprintf(const char *format, va_list args); diff --git a/include/curl/multi.h b/include/curl/multi.h index 094c64849..92621aa99 100644 --- a/include/curl/multi.h +++ b/include/curl/multi.h @@ -283,7 +283,7 @@ CURL_EXTERN CURLMcode curl_multi_timeout(CURLM *multi_handle, #undef CINIT /* re-using the same name as in curl.h */ #ifdef CURL_ISOCPP -#define CINIT(name,type,number) CURLMOPT_ ## name = CURLOPTTYPE_ ## type + number +#define CINIT(name,type,num) CURLMOPT_ ## name = CURLOPTTYPE_ ## type + num #else /* The macro "##" is ISO C, we assume pre-ISO C doesn't support it. */ #define LONG CURLOPTTYPE_LONG diff --git a/include/curl/typecheck-gcc.h b/include/curl/typecheck-gcc.h index 969e2bbe4..4c7569698 100644 --- a/include/curl/typecheck-gcc.h +++ b/include/curl/typecheck-gcc.h @@ -127,7 +127,8 @@ _CURL_WARNING(_curl_easy_setopt_err_long, _CURL_WARNING(_curl_easy_setopt_err_curl_off_t, "curl_easy_setopt expects a curl_off_t argument for this option") _CURL_WARNING(_curl_easy_setopt_err_string, - "curl_easy_setopt expects a string (char* or char[]) argument for this option") + "curl_easy_setopt expects a string (char* or char[]) argument for this option" + ) _CURL_WARNING(_curl_easy_setopt_err_write_callback, "curl_easy_setopt expects a curl_write_callback argument for this option") _CURL_WARNING(_curl_easy_setopt_err_read_cb, @@ -137,7 +138,8 @@ _CURL_WARNING(_curl_easy_setopt_err_ioctl_cb, _CURL_WARNING(_curl_easy_setopt_err_sockopt_cb, "curl_easy_setopt expects a curl_sockopt_callback argument for this option") _CURL_WARNING(_curl_easy_setopt_err_opensocket_cb, - "curl_easy_setopt expects a curl_opensocket_callback argument for this option") + "curl_easy_setopt expects a curl_opensocket_callback argument for this option" + ) _CURL_WARNING(_curl_easy_setopt_err_progress_cb, "curl_easy_setopt expects a curl_progress_callback argument for this option") _CURL_WARNING(_curl_easy_setopt_err_debug_cb, @@ -280,7 +282,7 @@ _CURL_WARNING(_curl_easy_getinfo_err_curl_slist, #define _curl_is_double_info(info) \ (CURLINFO_DOUBLE < (info) && (info) < CURLINFO_SLIST) -/* evaluates to true if info expects a pointer to struct curl_slist * argument */ +/* true if info expects a pointer to struct curl_slist * argument */ #define _curl_is_slist_info(info) \ (CURLINFO_SLIST < (info)) @@ -408,10 +410,12 @@ typedef size_t (_curl_read_callback6)(void *, size_t, size_t, FILE*); _curl_callback_compatible((expr), _curl_write_callback5) || \ _curl_callback_compatible((expr), _curl_write_callback6)) typedef size_t (_curl_write_callback1)(const char *, size_t, size_t, void*); -typedef size_t (_curl_write_callback2)(const char *, size_t, size_t, const void*); +typedef size_t (_curl_write_callback2)(const char *, size_t, size_t, + const void*); typedef size_t (_curl_write_callback3)(const char *, size_t, size_t, FILE*); typedef size_t (_curl_write_callback4)(const void *, size_t, size_t, void*); -typedef size_t (_curl_write_callback5)(const void *, size_t, size_t, const void*); +typedef size_t (_curl_write_callback5)(const void *, size_t, size_t, + const void*); typedef size_t (_curl_write_callback6)(const void *, size_t, size_t, FILE*); /* evaluates to true if expr is of type curl_ioctl_callback or "similar" */ @@ -434,7 +438,8 @@ typedef curlioerr (_curl_ioctl_callback4)(CURL *, curliocmd, const void*); _curl_callback_compatible((expr), _curl_sockopt_callback1) || \ _curl_callback_compatible((expr), _curl_sockopt_callback2)) typedef int (_curl_sockopt_callback1)(void *, curl_socket_t, curlsocktype); -typedef int (_curl_sockopt_callback2)(const void *, curl_socket_t, curlsocktype); +typedef int (_curl_sockopt_callback2)(const void *, curl_socket_t, + curlsocktype); /* evaluates to true if expr is of type curl_opensocket_callback or "similar" */ #define _curl_is_opensocket_cb(expr) \ diff --git a/lib/config-os400.h b/lib/config-os400.h index 5e30e435d..edc398768 100644 --- a/lib/config-os400.h +++ b/lib/config-os400.h @@ -322,6 +322,9 @@ /* Define if you have the header file. */ #define HAVE_SYS_TYPES_H +/* Define if you have the header file. */ +#define HAVE_SYS_UN_H + /* Define if you have the header file. */ #define HAVE_SYS_IOCTL_H @@ -379,6 +382,9 @@ #define SIZEOF_CURL_OFF_T 8 +/* Define this if you have struct sockaddr_storage */ +#define HAVE_STRUCT_SOCKADDR_STORAGE + /* Define if you have the ANSI C header files. */ #define STDC_HEADERS diff --git a/lib/qssl.c b/lib/qssl.c index 15684096d..2dd46c35c 100644 --- a/lib/qssl.c +++ b/lib/qssl.c @@ -372,15 +372,15 @@ int Curl_qsossl_shutdown(struct connectdata * conn, int sockindex) } -ssize_t Curl_qsossl_send(struct connectdata * conn, int sockindex, void * mem, - size_t len) +ssize_t Curl_qsossl_send(struct connectdata * conn, int sockindex, + const void * mem, size_t len) { /* SSL_Write() is said to return 'int' while write() and send() returns 'size_t' */ int rc; - rc = SSL_Write(conn->ssl[sockindex].handle, mem, (int) len); + rc = SSL_Write(conn->ssl[sockindex].handle, (void *) mem, (int) len); if(rc < 0) { switch(rc) { diff --git a/lib/qssl.h b/lib/qssl.h index 55d72d4dc..ff3f6f56a 100644 --- a/lib/qssl.h +++ b/lib/qssl.h @@ -38,7 +38,7 @@ int Curl_qsossl_shutdown(struct connectdata * conn, int sockindex); ssize_t Curl_qsossl_send(struct connectdata * conn, int sockindex, - void * mem, + const void * mem, size_t len); ssize_t Curl_qsossl_recv(struct connectdata * conn, /* connection data */ int num, /* socketindex */ diff --git a/lib/setup-os400.h b/lib/setup-os400.h index 8466d9c43..d6e704ace 100644 --- a/lib/setup-os400.h +++ b/lib/setup-os400.h @@ -137,4 +137,20 @@ extern OM_uint32 Curl_gss_delete_sec_context_a(OM_uint32 * minor_status, #define ldap_first_attribute Curl_ldap_first_attribute_a #define ldap_next_attribute Curl_ldap_next_attribute_a +/* Some socket functions must be wrapped to process textual addresses + like AF_UNIX. */ + +extern int Curl_os400_connect(int sd, struct sockaddr * destaddr, int addrlen); +extern int Curl_os400_bind(int sd, struct sockaddr * localaddr, int addrlen); +extern int Curl_os400_sendto(int sd, char * buffer, int buflen, int flags, + struct sockaddr * dstaddr, int addrlen); +extern int Curl_os400_recvfrom(int sd, char * buffer, int buflen, int flags, + struct sockaddr * fromaddr, int * addrlen); + +#define connect Curl_os400_connect +#define bind Curl_os400_bind +#define sendto Curl_os400_sendto +#define recvfrom Curl_os400_recvfrom + + #endif /* __SETUP_OS400_H */ diff --git a/packages/OS400/curl.inc.in b/packages/OS400/curl.inc.in index eae8da6ab..23808f4b7 100644 --- a/packages/OS400/curl.inc.in +++ b/packages/OS400/curl.inc.in @@ -382,6 +382,8 @@ d c 79 d CURLE_SSL_SHUTDOWN_FAILED... d c 80 + d CURLE_AGAIN... + d c 81 * d curlioerr s 10i 0 based(######ptr######) Enum d CURLIOE_OK c 0 @@ -872,15 +874,17 @@ d CURLINFO_OS_ERRNO... CURLINFO_LONG + 25 d c X'00200019' d CURLINFO_NUM_CONNECTS... CURLINFO_LONG + 26 - d c X'00200020' + d c X'0020001A' d CURLINFO_SSL_ENGINES... CURLINFO_SLIST + 27 - d c X'00400021' + d c X'0040001B' d CURLINFO_COOKIELIST... CURLINFO_SLIST + 28 - d c X'00400022' + d c X'0040001C' d CURLINFO_LASTSOCKET... CURLINFO_LONG + 29 - d c X'00200023' + d c X'0020001D' d CURLINFO_FTP_ENTRY_PATH... CURLINFO_STRING + 30 - d c X'00100024' + d c X'0010001E' + d CURLINFO_REDIRECT_URL... CURLINFO_STRING + 31 + d c X'0010001F' d CURLINFO_HTTP_CODE... Old ...RESPONSE_CODE d c X'00200002' * @@ -1111,6 +1115,9 @@ d s * based(######ptr######) procptr * d curl_read_callback... + d s * based(######ptr######) procptr + * + d curl_write_callback... d s * based(######ptr######) procptr * d curl_seek_callback... @@ -1164,7 +1171,7 @@ d curl_strnequal pr 10i 0 extproc('curl_strnequal') d s1 * value options(*string) d s2 * value options(*string) - d n 10i 0 value + d n 10u 0 value * d curl_formget pr 10i 0 extproc('curl_formget') d form * value curl_httppost * @@ -1359,6 +1366,22 @@ d pr extproc('curl_easy_reset') d curl * value CURL * * + d curl_easy_recv... + d pr extproc('curl_easy_recv') + d like(CURLcode) + d curl * value CURL * + d buffer * value void * + d buflen 10u 0 value size_t + d n 10u 0 size_t * + * + d curl_easy_send... + d pr extproc('curl_easy_send') + d like(CURLcode) + d curl * value CURL * + d buffer * value const void * + d buflen 10u 0 value size_t + d n 10u 0 size_t * + * d curl_easy_pause... d pr extproc('curl_easy_pause') d curl * value CURL * diff --git a/packages/OS400/initscript.sh b/packages/OS400/initscript.sh index 4dcbe7235..ad4aa7da2 100644 --- a/packages/OS400/initscript.sh +++ b/packages/OS400/initscript.sh @@ -40,10 +40,10 @@ SRVPGM="CURL.${SONAME}" # Service program. TGTCCSID='500' # Target CCSID of objects DEBUG='*ALL' # Debug level OPTIMIZE='10' # Optimisation level -OUTPUT='*NONE' # Compilation output option. +OUTPUT='*NONE' # Compilation output option. TGTRLS='V5R2M0' # Target OS release -export TARGETLIB STATBNDDIR DYNBNDDIR SRVPGM TGTCCSID DEBUG OPTIMIZE OUTPUTC +export TARGETLIB STATBNDDIR DYNBNDDIR SRVPGM TGTCCSID DEBUG OPTIMIZE OUTPUT export TGTRLS diff --git a/packages/OS400/os400sys.c b/packages/OS400/os400sys.c index 404bc7107..608aab69a 100644 --- a/packages/OS400/os400sys.c +++ b/packages/OS400/os400sys.c @@ -24,12 +24,14 @@ /* OS/400 additional support. */ -#include "config-os400.h" /* Not setup.h: we only need some defines. */ +#include "config-os400.h" /* Not setup.h: we only need some defines. */ #include #include +#include #include +#include #include #include #include @@ -965,3 +967,145 @@ Curl_ldap_next_attribute_a(void * ld, } #endif /* CURL_DISABLE_LDAP */ + + +static int +convert_sockaddr(struct sockaddr_storage * dstaddr, + const struct sockaddr * srcaddr, int srclen) + +{ + const struct sockaddr_un * srcu; + struct sockaddr_un * dstu; + unsigned int i; + unsigned int dstsize; + + /* Convert a socket address into job CCSID, if needed. */ + + if (!srcaddr || srclen < offsetof(struct sockaddr, sa_family) + + sizeof srcaddr->sa_family || srclen > sizeof *dstaddr) { + errno = EINVAL; + return -1; + } + + memcpy((char *) dstaddr, (char *) srcaddr, srclen); + + switch (srcaddr->sa_family) { + + case AF_UNIX: + srcu = (const struct sockaddr_un *) srcaddr; + dstu = (struct sockaddr_un *) dstaddr; + dstsize = sizeof *dstaddr - offsetof(struct sockaddr_un, sun_path); + srclen -= offsetof(struct sockaddr_un, sun_path); + i = QadrtConvertA2E(dstu->sun_path, srcu->sun_path, dstsize - 1, srclen); + dstu->sun_path[i] = '\0'; + i += offsetof(struct sockaddr_un, sun_path); + srclen = i; + } + + return srclen; +} + + +int +Curl_os400_connect(int sd, struct sockaddr * destaddr, int addrlen) + +{ + int i; + struct sockaddr_storage laddr; + + i = convert_sockaddr(&laddr, destaddr, addrlen); + + if (i < 0) + return -1; + + return connect(sd, (struct sockaddr *) &laddr, i); +} + + +int +Curl_os400_bind(int sd, struct sockaddr * localaddr, int addrlen) + +{ + int i; + struct sockaddr_storage laddr; + + i = convert_sockaddr(&laddr, localaddr, addrlen); + + if (i < 0) + return -1; + + return bind(sd, (struct sockaddr *) &laddr, i); +} + + +int +Curl_os400_sendto(int sd, char * buffer, int buflen, int flags, + struct sockaddr * dstaddr, int addrlen) + +{ + int i; + struct sockaddr_storage laddr; + + i = convert_sockaddr(&laddr, dstaddr, addrlen); + + if (i < 0) + return -1; + + return sendto(sd, buffer, buflen, flags, (struct sockaddr *) &laddr, i); +} + + +int +Curl_os400_recvfrom(int sd, char * buffer, int buflen, int flags, + struct sockaddr * fromaddr, int * addrlen) + +{ + int i; + int rcvlen; + int laddrlen; + const struct sockaddr_un * srcu; + struct sockaddr_un * dstu; + struct sockaddr_storage laddr; + + if (!fromaddr || !addrlen || *addrlen <= 0) + return recvfrom(sd, buffer, buflen, flags, fromaddr, addrlen); + + laddrlen = sizeof laddr; + laddr.ss_family = AF_UNSPEC; /* To detect if unused. */ + rcvlen = recvfrom(sd, buffer, buflen, flags, + (struct sockaddr *) &laddr, &laddrlen); + + if (rcvlen < 0) + return rcvlen; + + switch (laddr.ss_family) { + + case AF_UNIX: + srcu = (const struct sockaddr_un *) &laddr; + dstu = (struct sockaddr_un *) fromaddr; + i = *addrlen - offsetof(struct sockaddr_un, sun_path); + laddrlen -= offsetof(struct sockaddr_un, sun_path); + i = QadrtConvertE2A(dstu->sun_path, srcu->sun_path, i, laddrlen); + laddrlen = i + offsetof(struct sockaddr_un, sun_path); + + if (laddrlen < *addrlen) + dstu->sun_path[i] = '\0'; + + break; + + case AF_UNSPEC: + break; + + default: + if (laddrlen > *addrlen) + laddrlen = *addrlen; + + if (laddrlen) + memcpy((char *) fromaddr, (char *) &laddr, laddrlen); + + break; + } + + *addrlen = laddrlen; + return rcvlen; +}