1 /***************************************************************************
3 * Project ___| | | | _ \| |
5 * | (__| |_| | _ <| |___
6 * \___|\___/|_| \_\_____|
8 * Copyright (C) 1998 - 2013, Daniel Stenberg, <daniel@haxx.se>, et al.
10 * This software is licensed as described in the file COPYING, which
11 * you should have received as part of this distribution. The terms
12 * are also available at http://curl.haxx.se/docs/copyright.html.
14 * You may opt to use, copy, modify, merge, publish, distribute and/or sell
15 * copies of the Software, and permit persons to whom the Software is
16 * furnished to do so, under the terms of the COPYING file.
18 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
19 * KIND, either express or implied.
22 ***************************************************************************/
24 /* OS/400 additional support. */
26 #include "curlbuild.h"
27 #include "config-os400.h" /* Not curl_setup.h: we only need some defines. */
29 #include <sys/types.h>
30 #include <sys/socket.h>
58 #ifndef CURL_DISABLE_LDAP
62 #include <netinet/in.h>
63 #include <arpa/inet.h>
69 *** QADRT OS/400 ASCII runtime defines only the most used procedures, but
70 *** but a lot of them are not supported. This module implements
71 *** ASCII wrappers for those that are used by libcurl, but not
75 #pragma convert(0) /* Restore EBCDIC. */
78 #define MIN_BYTE_GAIN 1024 /* Minimum gain when shortening a buffer. */
81 unsigned long size; /* Buffer size. */
82 char * buf; /* Buffer address. */
86 static char * buffer_undef(localkey_t key, long size);
87 static char * buffer_threaded(localkey_t key, long size);
88 static char * buffer_unthreaded(localkey_t key, long size);
90 static pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
91 static pthread_key_t thdkey;
92 static buffer_t * locbufs;
94 char * (* Curl_thread_buffer)(localkey_t key, long size) = buffer_undef;
98 thdbufdestroy(void * private)
105 p = (buffer_t *) private;
107 for(i = (localkey_t) 0; i < LK_LAST; i++) {
123 if(Curl_thread_buffer == buffer_threaded) {
124 locbufs = pthread_getspecific(thdkey);
125 pthread_setspecific(thdkey, (void *) NULL);
126 pthread_key_delete(thdkey);
129 if(Curl_thread_buffer != buffer_undef) {
130 thdbufdestroy((void *) locbufs);
131 locbufs = (buffer_t *) NULL;
134 Curl_thread_buffer = buffer_undef;
139 get_buffer(buffer_t * buf, long size)
144 /* If `size' >= 0, make sure buffer at `buf' is at least `size'-byte long.
145 Return the buffer address. */
151 if((buf->buf = malloc(size)))
157 if((unsigned long) size <= buf->size) {
158 /* Shorten the buffer only if it frees a significant byte count. This
159 avoids some realloc() overhead. */
161 if(buf->size - size < MIN_BYTE_GAIN)
165 /* Resize the buffer. */
167 if((cp = realloc(buf->buf, size))) {
171 else if(size <= buf->size)
179 buffer_unthreaded(localkey_t key, long size)
182 return get_buffer(locbufs + key, size);
187 buffer_threaded(localkey_t key, long size)
192 /* Get the buffer for the given local key in the current thread, and
193 make sure it is at least `size'-byte long. Set `size' to < 0 to get
196 bufs = (buffer_t *) pthread_getspecific(thdkey);
200 return (char *) NULL; /* No buffer yet. */
202 /* Allocate buffer descriptors for the current thread. */
204 if(!(bufs = calloc((size_t) LK_LAST, sizeof *bufs)))
205 return (char *) NULL;
207 if(pthread_setspecific(thdkey, (void *) bufs)) {
209 return (char *) NULL;
213 return get_buffer(bufs + key, size);
218 buffer_undef(localkey_t key, long size)
221 /* Define the buffer system, get the buffer for the given local key in
222 the current thread, and make sure it is at least `size'-byte long.
223 Set `size' to < 0 to get its address only. */
225 pthread_mutex_lock(&mutex);
227 /* Determine if we can use pthread-specific data. */
229 if(Curl_thread_buffer == buffer_undef) { /* If unchanged during lock. */
230 if(!pthread_key_create(&thdkey, thdbufdestroy))
231 Curl_thread_buffer = buffer_threaded;
232 else if(!(locbufs = calloc((size_t) LK_LAST, sizeof *locbufs))) {
233 pthread_mutex_unlock(&mutex);
234 return (char *) NULL;
237 Curl_thread_buffer = buffer_unthreaded;
242 pthread_mutex_unlock(&mutex);
243 return Curl_thread_buffer(key, size);
248 set_thread_string(localkey_t key, const char * s)
255 return (char *) NULL;
258 cp = Curl_thread_buffer(key, MAX_CONV_EXPANSION * i + 1);
261 i = QadrtConvertE2A(cp, s, MAX_CONV_EXPANSION * i, i);
270 Curl_getnameinfo_a(const struct sockaddr * sa, curl_socklen_t salen,
271 char * nodename, curl_socklen_t nodenamelen,
272 char * servname, curl_socklen_t servnamelen,
281 enodename = (char *) NULL;
282 eservname = (char *) NULL;
284 if(nodename && nodenamelen)
285 if(!(enodename = malloc(nodenamelen)))
288 if(servname && servnamelen)
289 if(!(eservname = malloc(servnamelen))) {
296 status = getnameinfo(sa, salen, enodename, nodenamelen,
297 eservname, servnamelen, flags);
301 i = QadrtConvertE2A(nodename, enodename,
302 nodenamelen - 1, strlen(enodename));
307 i = QadrtConvertE2A(servname, eservname,
308 servnamelen - 1, strlen(eservname));
324 Curl_getaddrinfo_a(const char * nodename, const char * servname,
325 const struct addrinfo * hints,
326 struct addrinfo * * res)
334 enodename = (char *) NULL;
335 eservname = (char *) NULL;
338 i = strlen(nodename);
340 if(!(enodename = malloc(i + 1)))
343 i = QadrtConvertA2E(enodename, nodename, i, i);
348 i = strlen(servname);
350 if(!(eservname = malloc(i + 1))) {
357 QadrtConvertA2E(eservname, servname, i, i);
361 status = getaddrinfo(enodename, eservname, hints, res);
375 /* ASCII wrappers for the SSL procedures. */
378 Curl_SSL_Init_Application_a(SSLInitApp * init_app)
385 if(!init_app || !init_app->applicationID || !init_app->applicationIDLen)
386 return SSL_Init_Application(init_app);
388 memcpy((char *) &ia, (char *) init_app, sizeof ia);
389 i = ia.applicationIDLen;
391 if(!(ia.applicationID = malloc(i + 1))) {
396 QadrtConvertA2E(ia.applicationID, init_app->applicationID, i, i);
397 ia.applicationID[i] = '\0';
398 rc = SSL_Init_Application(&ia);
399 free(ia.applicationID);
400 init_app->localCertificateLen = ia.localCertificateLen;
401 init_app->sessionType = ia.sessionType;
407 Curl_SSL_Init_a(SSLInit * init)
414 if(!init || (!init->keyringFileName && !init->keyringPassword))
415 return SSL_Init(init);
417 memcpy((char *) &ia, (char *) init, sizeof ia);
419 if(ia.keyringFileName) {
420 i = strlen(ia.keyringFileName);
422 if(!(ia.keyringFileName = malloc(i + 1))) {
427 QadrtConvertA2E(ia.keyringFileName, init->keyringFileName, i, i);
428 ia.keyringFileName[i] = '\0';
431 if(ia.keyringPassword) {
432 i = strlen(ia.keyringPassword);
434 if(!(ia.keyringPassword = malloc(i + 1))) {
435 if(ia.keyringFileName)
436 free(ia.keyringFileName);
442 QadrtConvertA2E(ia.keyringPassword, init->keyringPassword, i, i);
443 ia.keyringPassword[i] = '\0';
448 if(ia.keyringFileName)
449 free(ia.keyringFileName);
451 if(ia.keyringPassword)
452 free(ia.keyringPassword);
459 Curl_SSL_Strerror_a(int sslreturnvalue, SSLErrorMsg * serrmsgp)
462 return set_thread_string(LK_SSL_ERROR,
463 SSL_Strerror(sslreturnvalue, serrmsgp));
466 #endif /* USE_QSOSSL */
471 /* ASCII wrappers for the GSKit procedures. */
474 * EBCDIC --> ASCII string mapping table.
475 * Some strings returned by GSKit are dynamically allocated and automatically
476 * released when closing the handle.
477 * To provide the same functionality, we use a "private" handle that
478 * holds the GSKit handle and a list of string mappings. This will allow
479 * avoid conversion of already converted strings and releasing them upon
484 struct gskstrlist * next;
485 const char * ebcdicstr;
486 const char * asciistr;
489 struct Curl_gsk_descriptor {
491 struct gskstrlist * strlist;
496 Curl_gsk_environment_open(gsk_handle * my_env_handle)
499 struct Curl_gsk_descriptor * p;
504 return GSK_OS400_ERROR_INVALID_POINTER;
505 if(!(p = (struct Curl_gsk_descriptor *) malloc(sizeof *p)))
506 return GSK_INSUFFICIENT_STORAGE;
507 p->strlist = (struct gskstrlist *) NULL;
508 if((rc = gsk_environment_open(&p->h)) != GSK_OK)
511 *my_env_handle = (gsk_handle) p;
517 Curl_gsk_secure_soc_open(gsk_handle my_env_handle,
518 gsk_handle * my_session_handle)
521 struct Curl_gsk_descriptor * p;
526 return GSK_INVALID_HANDLE;
527 if(!my_session_handle)
528 return GSK_OS400_ERROR_INVALID_POINTER;
529 h = ((struct Curl_gsk_descriptor *) my_env_handle)->h;
530 if(!(p = (struct Curl_gsk_descriptor *) malloc(sizeof *p)))
531 return GSK_INSUFFICIENT_STORAGE;
532 p->strlist = (struct gskstrlist *) NULL;
533 if((rc = gsk_secure_soc_open(h, &p->h)) != GSK_OK)
536 *my_session_handle = (gsk_handle) p;
542 gsk_free_handle(struct Curl_gsk_descriptor * p)
545 struct gskstrlist * q;
547 while((q = p->strlist)) {
549 free((void *) q->asciistr);
557 Curl_gsk_environment_close(gsk_handle * my_env_handle)
560 struct Curl_gsk_descriptor * p;
564 return GSK_OS400_ERROR_INVALID_POINTER;
566 return GSK_INVALID_HANDLE;
567 p = (struct Curl_gsk_descriptor *) *my_env_handle;
568 if((rc = gsk_environment_close(&p->h)) == GSK_OK) {
570 *my_env_handle = (gsk_handle) NULL;
577 Curl_gsk_secure_soc_close(gsk_handle * my_session_handle)
580 struct Curl_gsk_descriptor * p;
583 if(!my_session_handle)
584 return GSK_OS400_ERROR_INVALID_POINTER;
585 if(!*my_session_handle)
586 return GSK_INVALID_HANDLE;
587 p = (struct Curl_gsk_descriptor *) *my_session_handle;
588 if((rc = gsk_secure_soc_close(&p->h)) == GSK_OK) {
590 *my_session_handle = (gsk_handle) NULL;
597 Curl_gsk_environment_init(gsk_handle my_env_handle)
600 struct Curl_gsk_descriptor * p;
603 return GSK_INVALID_HANDLE;
604 p = (struct Curl_gsk_descriptor *) my_env_handle;
605 return gsk_environment_init(p->h);
610 Curl_gsk_secure_soc_init(gsk_handle my_session_handle)
613 struct Curl_gsk_descriptor * p;
615 if(!my_session_handle)
616 return GSK_INVALID_HANDLE;
617 p = (struct Curl_gsk_descriptor *) my_session_handle;
618 return gsk_secure_soc_init(p->h);
623 Curl_gsk_attribute_set_buffer_a(gsk_handle my_gsk_handle, GSK_BUF_ID bufID,
624 const char * buffer, int bufSize)
627 struct Curl_gsk_descriptor * p;
632 return GSK_INVALID_HANDLE;
634 return GSK_OS400_ERROR_INVALID_POINTER;
636 return GSK_ATTRIBUTE_INVALID_LENGTH;
637 p = (struct Curl_gsk_descriptor *) my_gsk_handle;
639 bufSize = strlen(buffer);
640 if(!(ebcdicbuf = malloc(bufSize + 1)))
641 return GSK_INSUFFICIENT_STORAGE;
642 QadrtConvertA2E(ebcdicbuf, buffer, bufSize, bufSize);
643 ebcdicbuf[bufSize] = '\0';
644 rc = gsk_attribute_set_buffer(p->h, bufID, ebcdicbuf, bufSize);
651 Curl_gsk_attribute_set_enum(gsk_handle my_gsk_handle, GSK_ENUM_ID enumID,
652 GSK_ENUM_VALUE enumValue)
655 struct Curl_gsk_descriptor * p;
658 return GSK_INVALID_HANDLE;
659 p = (struct Curl_gsk_descriptor *) my_gsk_handle;
660 return gsk_attribute_set_enum(p->h, enumID, enumValue);
665 Curl_gsk_attribute_set_numeric_value(gsk_handle my_gsk_handle,
666 GSK_NUM_ID numID, int numValue)
669 struct Curl_gsk_descriptor * p;
672 return GSK_INVALID_HANDLE;
673 p = (struct Curl_gsk_descriptor *) my_gsk_handle;
674 return gsk_attribute_set_numeric_value(p->h, numID, numValue);
679 Curl_gsk_attribute_set_callback(gsk_handle my_gsk_handle,
680 GSK_CALLBACK_ID callBackID,
681 void * callBackAreaPtr)
684 struct Curl_gsk_descriptor * p;
687 return GSK_INVALID_HANDLE;
688 p = (struct Curl_gsk_descriptor *) my_gsk_handle;
689 return gsk_attribute_set_callback(p->h, callBackID, callBackAreaPtr);
694 cachestring(struct Curl_gsk_descriptor * p,
695 const char * ebcdicbuf, int bufsize, const char * * buffer)
700 struct gskstrlist * sp;
702 for(sp = p->strlist; sp; sp = sp->next)
703 if(sp->ebcdicstr == ebcdicbuf)
706 if(!(sp = (struct gskstrlist *) malloc(sizeof *sp)))
707 return GSK_INSUFFICIENT_STORAGE;
708 if(!(asciibuf = malloc(bufsize + 1))) {
710 return GSK_INSUFFICIENT_STORAGE;
712 QadrtConvertE2A(asciibuf, ebcdicbuf, bufsize, bufsize);
713 asciibuf[bufsize] = '\0';
714 sp->ebcdicstr = ebcdicbuf;
715 sp->asciistr = asciibuf;
716 sp->next = p->strlist;
719 *buffer = sp->asciistr;
725 Curl_gsk_attribute_get_buffer_a(gsk_handle my_gsk_handle, GSK_BUF_ID bufID,
726 const char * * buffer, int * bufSize)
729 struct Curl_gsk_descriptor * p;
735 return GSK_INVALID_HANDLE;
736 if(!buffer || !bufSize)
737 return GSK_OS400_ERROR_INVALID_POINTER;
738 p = (struct Curl_gsk_descriptor *) my_gsk_handle;
739 if((rc = gsk_attribute_get_buffer(p->h, bufID, &mybuf, &mylen)) != GSK_OK)
741 if((rc = cachestring(p, mybuf, mylen, buffer)) == GSK_OK)
748 Curl_gsk_attribute_get_enum(gsk_handle my_gsk_handle, GSK_ENUM_ID enumID,
749 GSK_ENUM_VALUE * enumValue)
752 struct Curl_gsk_descriptor * p;
755 return GSK_INVALID_HANDLE;
756 p = (struct Curl_gsk_descriptor *) my_gsk_handle;
757 return gsk_attribute_get_enum(p->h, enumID, enumValue);
762 Curl_gsk_attribute_get_numeric_value(gsk_handle my_gsk_handle,
763 GSK_NUM_ID numID, int * numValue)
766 struct Curl_gsk_descriptor * p;
769 return GSK_INVALID_HANDLE;
770 p = (struct Curl_gsk_descriptor *) my_gsk_handle;
771 return gsk_attribute_get_numeric_value(p->h, numID, numValue);
776 Curl_gsk_attribute_get_cert_info(gsk_handle my_gsk_handle,
778 const gsk_cert_data_elem * * certDataElem,
779 int * certDataElementCount)
782 struct Curl_gsk_descriptor * p;
785 return GSK_INVALID_HANDLE;
786 p = (struct Curl_gsk_descriptor *) my_gsk_handle;
787 /* No need to convert code: text results are already in ASCII. */
788 return gsk_attribute_get_cert_info(p->h, certID,
789 certDataElem, certDataElementCount);
794 Curl_gsk_secure_soc_misc(gsk_handle my_session_handle, GSK_MISC_ID miscID)
797 struct Curl_gsk_descriptor * p;
799 if(!my_session_handle)
800 return GSK_INVALID_HANDLE;
801 p = (struct Curl_gsk_descriptor *) my_session_handle;
802 return gsk_secure_soc_misc(p->h, miscID);
807 Curl_gsk_secure_soc_read(gsk_handle my_session_handle, char * readBuffer,
808 int readBufSize, int * amtRead)
811 struct Curl_gsk_descriptor * p;
813 if(!my_session_handle)
814 return GSK_INVALID_HANDLE;
815 p = (struct Curl_gsk_descriptor *) my_session_handle;
816 return gsk_secure_soc_read(p->h, readBuffer, readBufSize, amtRead);
821 Curl_gsk_secure_soc_write(gsk_handle my_session_handle, char * writeBuffer,
822 int writeBufSize, int * amtWritten)
825 struct Curl_gsk_descriptor * p;
827 if(!my_session_handle)
828 return GSK_INVALID_HANDLE;
829 p = (struct Curl_gsk_descriptor *) my_session_handle;
830 return gsk_secure_soc_write(p->h, writeBuffer, writeBufSize, amtWritten);
835 Curl_gsk_strerror_a(int gsk_return_value)
838 return set_thread_string(LK_GSK_ERROR, gsk_strerror(gsk_return_value));
842 Curl_gsk_secure_soc_startInit(gsk_handle my_session_handle,
843 int IOCompletionPort,
844 Qso_OverlappedIO_t * communicationsArea)
847 struct Curl_gsk_descriptor * p;
849 if(!my_session_handle)
850 return GSK_INVALID_HANDLE;
851 p = (struct Curl_gsk_descriptor *) my_session_handle;
852 return gsk_secure_soc_startInit(p->h, IOCompletionPort, communicationsArea);
855 #endif /* USE_GSKIT */
861 /* ASCII wrappers for the GSSAPI procedures. */
864 Curl_gss_convert_in_place(OM_uint32 * minor_status, gss_buffer_t buf)
870 /* Convert `buf' in place, from EBCDIC to ASCII.
871 If error, release the buffer and return -1. Else return 0. */
876 if(!(t = malloc(i))) {
877 gss_release_buffer(minor_status, buf);
880 *minor_status = ENOMEM;
885 QadrtConvertE2A(t, buf->value, i, i);
886 memcpy(buf->value, t, i);
895 Curl_gss_import_name_a(OM_uint32 * minor_status, gss_buffer_t in_name,
896 gss_OID in_name_type, gss_name_t * out_name)
903 if(!in_name || !in_name->value || !in_name->length)
904 return gss_import_name(minor_status, in_name, in_name_type, out_name);
906 memcpy((char *) &in, (char *) in_name, sizeof in);
909 if(!(in.value = malloc(i + 1))) {
911 *minor_status = ENOMEM;
913 return GSS_S_FAILURE;
916 QadrtConvertA2E(in.value, in_name->value, i, i);
917 ((char *) in.value)[i] = '\0';
918 rc = gss_import_name(minor_status, &in, in_name_type, out_name);
925 Curl_gss_display_status_a(OM_uint32 * minor_status, OM_uint32 status_value,
926 int status_type, gss_OID mech_type,
927 gss_msg_ctx_t * message_context, gss_buffer_t status_string)
932 rc = gss_display_status(minor_status, status_value, status_type,
933 mech_type, message_context, status_string);
935 if(rc != GSS_S_COMPLETE || !status_string ||
936 !status_string->length || !status_string->value)
939 /* No way to allocate a buffer here, because it will be released by
940 gss_release_buffer(). The solution is to overwrite the EBCDIC buffer
941 with ASCII to return it. */
943 if(Curl_gss_convert_in_place(minor_status, status_string))
944 return GSS_S_FAILURE;
951 Curl_gss_init_sec_context_a(OM_uint32 * minor_status,
952 gss_cred_id_t cred_handle,
953 gss_ctx_id_t * context_handle,
954 gss_name_t target_name, gss_OID mech_type,
955 gss_flags_t req_flags, OM_uint32 time_req,
956 gss_channel_bindings_t input_chan_bindings,
957 gss_buffer_t input_token,
958 gss_OID * actual_mech_type,
959 gss_buffer_t output_token, gss_flags_t * ret_flags,
960 OM_uint32 * time_rec)
970 if((inp = input_token))
971 if(inp->length && inp->value) {
974 if(!(in.value = malloc(i + 1))) {
976 *minor_status = ENOMEM;
978 return GSS_S_FAILURE;
981 QadrtConvertA2E(in.value, input_token->value, i, i);
982 ((char *) in.value)[i] = '\0';
987 rc = gss_init_sec_context(minor_status, cred_handle, context_handle,
988 target_name, mech_type, req_flags, time_req,
989 input_chan_bindings, inp, actual_mech_type,
990 output_token, ret_flags, time_rec);
995 if(rc != GSS_S_COMPLETE || !output_token ||
996 !output_token->length || !output_token->value)
999 /* No way to allocate a buffer here, because it will be released by
1000 gss_release_buffer(). The solution is to overwrite the EBCDIC buffer
1001 with ASCII to return it. */
1003 if(Curl_gss_convert_in_place(minor_status, output_token))
1004 return GSS_S_FAILURE;
1011 Curl_gss_delete_sec_context_a(OM_uint32 * minor_status,
1012 gss_ctx_id_t * context_handle,
1013 gss_buffer_t output_token)
1018 rc = gss_delete_sec_context(minor_status, context_handle, output_token);
1020 if(rc != GSS_S_COMPLETE || !output_token ||
1021 !output_token->length || !output_token->value)
1024 /* No way to allocate a buffer here, because it will be released by
1025 gss_release_buffer(). The solution is to overwrite the EBCDIC buffer
1026 with ASCII to return it. */
1028 if(Curl_gss_convert_in_place(minor_status, output_token))
1029 return GSS_S_FAILURE;
1034 #endif /* HAVE_GSSAPI */
1037 #ifndef CURL_DISABLE_LDAP
1039 /* ASCII wrappers for the LDAP procedures. */
1042 Curl_ldap_init_a(char * host, int port)
1050 return (void *) ldap_init(host, port);
1054 if(!(ehost = malloc(i + 1)))
1055 return (void *) NULL;
1057 QadrtConvertA2E(ehost, host, i, i);
1059 result = (void *) ldap_init(ehost, port);
1066 Curl_ldap_simple_bind_s_a(void * ld, char * dn, char * passwd)
1073 edn = (char *) NULL;
1074 epasswd = (char *) NULL;
1079 if(!(edn = malloc(i + 1)))
1080 return LDAP_NO_MEMORY;
1082 QadrtConvertA2E(edn, dn, i, i);
1089 if(!(epasswd = malloc(i + 1))) {
1093 return LDAP_NO_MEMORY;
1096 QadrtConvertA2E(epasswd, passwd, i, i);
1100 i = ldap_simple_bind_s(ld, edn, epasswd);
1113 Curl_ldap_search_s_a(void * ld, char * base, int scope, char * filter,
1114 char * * attrs, int attrsonly, LDAPMessage * * res)
1124 ebase = (char *) NULL;
1125 efilter = (char *) NULL;
1126 eattrs = (char * *) NULL;
1127 status = LDAP_SUCCESS;
1132 if(!(ebase = malloc(i + 1)))
1133 status = LDAP_NO_MEMORY;
1135 QadrtConvertA2E(ebase, base, i, i);
1140 if(filter && status == LDAP_SUCCESS) {
1143 if(!(efilter = malloc(i + 1)))
1144 status = LDAP_NO_MEMORY;
1146 QadrtConvertA2E(efilter, filter, i, i);
1151 if(attrs && status == LDAP_SUCCESS) {
1152 for(i = 0; attrs[i++];)
1155 if(!(eattrs = calloc(i, sizeof *eattrs)))
1156 status = LDAP_NO_MEMORY;
1158 for(j = 0; attrs[j]; j++) {
1159 i = strlen(attrs[j]);
1161 if(!(eattrs[j] = malloc(i + 1))) {
1162 status = LDAP_NO_MEMORY;
1166 QadrtConvertA2E(eattrs[j], attrs[j], i, i);
1167 eattrs[j][i] = '\0';
1172 if(status == LDAP_SUCCESS)
1173 status = ldap_search_s(ld, ebase? ebase: "", scope,
1174 efilter? efilter: "(objectclass=*)",
1175 eattrs, attrsonly, res);
1178 for(j = 0; eattrs[j]; j++)
1195 Curl_ldap_get_values_len_a(void * ld, LDAPMessage * entry, const char * attr)
1200 struct berval * * result;
1207 if(!(cp = malloc(i + 1))) {
1208 ldap_set_lderrno(ld, LDAP_NO_MEMORY, NULL,
1209 ldap_err2string(LDAP_NO_MEMORY));
1210 return (struct berval * *) NULL;
1213 QadrtConvertA2E(cp, attr, i, i);
1217 result = ldap_get_values_len(ld, entry, cp);
1222 /* Result data are binary in nature, so they haven't been
1223 converted to EBCDIC. Therefore do not convert. */
1230 Curl_ldap_err2string_a(int error)
1233 return set_thread_string(LK_LDAP_ERROR, ldap_err2string(error));
1238 Curl_ldap_get_dn_a(void * ld, LDAPMessage * entry)
1245 cp = ldap_get_dn(ld, entry);
1252 if(!(cp2 = malloc(i + 1)))
1255 QadrtConvertE2A(cp2, cp, i, i);
1258 /* No way to allocate a buffer here, because it will be released by
1259 ldap_memfree() and ldap_memalloc() does not exist. The solution is to
1260 overwrite the EBCDIC buffer with ASCII to return it. */
1269 Curl_ldap_first_attribute_a(void * ld,
1270 LDAPMessage * entry, BerElement * * berptr)
1277 cp = ldap_first_attribute(ld, entry, berptr);
1284 if(!(cp2 = malloc(i + 1)))
1287 QadrtConvertE2A(cp2, cp, i, i);
1290 /* No way to allocate a buffer here, because it will be released by
1291 ldap_memfree() and ldap_memalloc() does not exist. The solution is to
1292 overwrite the EBCDIC buffer with ASCII to return it. */
1301 Curl_ldap_next_attribute_a(void * ld,
1302 LDAPMessage * entry, BerElement * berptr)
1309 cp = ldap_next_attribute(ld, entry, berptr);
1316 if(!(cp2 = malloc(i + 1)))
1319 QadrtConvertE2A(cp2, cp, i, i);
1322 /* No way to allocate a buffer here, because it will be released by
1323 ldap_memfree() and ldap_memalloc() does not exist. The solution is to
1324 overwrite the EBCDIC buffer with ASCII to return it. */
1331 #endif /* CURL_DISABLE_LDAP */
1335 convert_sockaddr(struct sockaddr_storage * dstaddr,
1336 const struct sockaddr * srcaddr, int srclen)
1339 const struct sockaddr_un * srcu;
1340 struct sockaddr_un * dstu;
1342 unsigned int dstsize;
1344 /* Convert a socket address into job CCSID, if needed. */
1346 if(!srcaddr || srclen < offsetof(struct sockaddr, sa_family) +
1347 sizeof srcaddr->sa_family || srclen > sizeof *dstaddr) {
1352 memcpy((char *) dstaddr, (char *) srcaddr, srclen);
1354 switch (srcaddr->sa_family) {
1357 srcu = (const struct sockaddr_un *) srcaddr;
1358 dstu = (struct sockaddr_un *) dstaddr;
1359 dstsize = sizeof *dstaddr - offsetof(struct sockaddr_un, sun_path);
1360 srclen -= offsetof(struct sockaddr_un, sun_path);
1361 i = QadrtConvertA2E(dstu->sun_path, srcu->sun_path, dstsize - 1, srclen);
1362 dstu->sun_path[i] = '\0';
1363 i += offsetof(struct sockaddr_un, sun_path);
1372 Curl_os400_connect(int sd, struct sockaddr * destaddr, int addrlen)
1376 struct sockaddr_storage laddr;
1378 i = convert_sockaddr(&laddr, destaddr, addrlen);
1383 return connect(sd, (struct sockaddr *) &laddr, i);
1388 Curl_os400_bind(int sd, struct sockaddr * localaddr, int addrlen)
1392 struct sockaddr_storage laddr;
1394 i = convert_sockaddr(&laddr, localaddr, addrlen);
1399 return bind(sd, (struct sockaddr *) &laddr, i);
1404 Curl_os400_sendto(int sd, char * buffer, int buflen, int flags,
1405 struct sockaddr * dstaddr, int addrlen)
1409 struct sockaddr_storage laddr;
1411 i = convert_sockaddr(&laddr, dstaddr, addrlen);
1416 return sendto(sd, buffer, buflen, flags, (struct sockaddr *) &laddr, i);
1421 Curl_os400_recvfrom(int sd, char * buffer, int buflen, int flags,
1422 struct sockaddr * fromaddr, int * addrlen)
1428 const struct sockaddr_un * srcu;
1429 struct sockaddr_un * dstu;
1430 struct sockaddr_storage laddr;
1432 if(!fromaddr || !addrlen || *addrlen <= 0)
1433 return recvfrom(sd, buffer, buflen, flags, fromaddr, addrlen);
1435 laddrlen = sizeof laddr;
1436 laddr.ss_family = AF_UNSPEC; /* To detect if unused. */
1437 rcvlen = recvfrom(sd, buffer, buflen, flags,
1438 (struct sockaddr *) &laddr, &laddrlen);
1443 switch (laddr.ss_family) {
1446 srcu = (const struct sockaddr_un *) &laddr;
1447 dstu = (struct sockaddr_un *) fromaddr;
1448 i = *addrlen - offsetof(struct sockaddr_un, sun_path);
1449 laddrlen -= offsetof(struct sockaddr_un, sun_path);
1450 i = QadrtConvertE2A(dstu->sun_path, srcu->sun_path, i, laddrlen);
1451 laddrlen = i + offsetof(struct sockaddr_un, sun_path);
1453 if(laddrlen < *addrlen)
1454 dstu->sun_path[i] = '\0';
1462 if(laddrlen > *addrlen)
1463 laddrlen = *addrlen;
1466 memcpy((char *) fromaddr, (char *) &laddr, laddrlen);
1471 *addrlen = laddrlen;
1478 Curl_os400_zlibVersion(void)
1481 return set_thread_string(LK_ZLIB_VERSION, zlibVersion());
1486 Curl_os400_inflateInit_(z_streamp strm, const char * version, int stream_size)
1489 z_const char * msgb4 = strm->msg;
1492 ret = inflateInit(strm);
1494 if(strm->msg != msgb4)
1495 strm->msg = set_thread_string(LK_ZLIB_MSG, strm->msg);
1502 Curl_os400_inflateInit2_(z_streamp strm, int windowBits,
1503 const char * version, int stream_size)
1506 z_const char * msgb4 = strm->msg;
1509 ret = inflateInit2(strm, windowBits);
1511 if(strm->msg != msgb4)
1512 strm->msg = set_thread_string(LK_ZLIB_MSG, strm->msg);
1519 Curl_os400_inflate(z_streamp strm, int flush)
1522 z_const char * msgb4 = strm->msg;
1525 ret = inflate(strm, flush);
1527 if(strm->msg != msgb4)
1528 strm->msg = set_thread_string(LK_ZLIB_MSG, strm->msg);
1535 Curl_os400_inflateEnd(z_streamp strm)
1538 z_const char * msgb4 = strm->msg;
1541 ret = inflateEnd(strm);
1543 if(strm->msg != msgb4)
1544 strm->msg = set_thread_string(LK_ZLIB_MSG, strm->msg);