/**
***     dlopen(), dlclose() dlsym(), dlerror() emulation for OS/400.
***
***     See Copyright for the status of this software.
***
***     Author: Patrick Monnerat <pm@datasphere.ch>, DATASPHERE S.A.
**/

#include <stdarg.h>
#include <stdio.h>
#include <ctype.h>
#include <errno.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <dirent.h>
#include <pthread.h>

#include <sys/types.h>
#include <sys/stat.h>

#include <except.h>             /* AS400 exceptions. */
#include <miptrnam.h>           /* MI pointers support. */
#include <qusec.h>              /* Error structures. */
#include <qp0lstdi.h>           /* Path to QSYS object name. */
#include <qp0z1170.h>           /* For Qp0zInitEnv(). */
#include <qleawi.h>             /* For QleActBndPgmLong() definitions. */
#include <qsy.h>                /* Qualified name structure. */
#include <qmhrtvm.h>            /* Retrieve message from message file. */

#include <mih/rinzstat.h>
#include <mih/matactex.h>

#include "libxml/hash.h"
#include "dlfcn.h"


/**
***     Maximum internal path length.
**/

#define MAXPATHLEN              5120


/**
***     Maximum error string length.
**/

#define MAX_ERR_STR             511


/**
***     Field address macro.
**/

#define offset_by(t, b, o)      ((t *) ((char *) (b) + (unsigned int) (o)))


/**
***     Global flags.
**/

#define INITED          000001          /* Package has been initialized. */
#define THREADS         000002          /* Multithreaded job. */
#define MULTIBUF        000004          /* One error buffer per thread. */


/**
***     DLL handle private structure.
**/

typedef struct {
        Qle_ABP_Info_Long_t     actinfo;        /* Activation information. */
        _SYSPTR                 pointer;        /* Pointer to DLL object. */
        unsigned int            actcount;       /* Activation count. */
}               dlinfo;


/**
***     Per-thread structure.
**/

typedef struct {
        unsigned int    lockcount;              /* Mutex lock count. */
        unsigned int    iserror;                /* Flag error present. */
        char            str[MAX_ERR_STR + 1];   /* Error string buffer. */
}               dlts_t;


static pthread_mutex_t  dlmutex = PTHREAD_MUTEX_INITIALIZER;
static xmlHashTablePtr  dldir = (xmlHashTablePtr) NULL; /* DLL directory. */
static unsigned int     dlflags = 0;                    /* Package flags. */
static pthread_key_t    dlkey;
static dlts_t           static_buf;             /* Static error buffer. */



static void
dlthreadterm(void * mem)

{
        free(mem);
        pthread_setspecific(dlkey, NULL);
}


static void
dlterm(void)

{
        void * p;

        if (dlflags & MULTIBUF) {
                p = pthread_getspecific(dlkey);

                if (p)
                        dlthreadterm(p);
                }

        if (dlflags & THREADS)
                pthread_mutex_lock(&dlmutex);

        if (dldir) {
                xmlHashFree(dldir, (xmlHashDeallocator) NULL);
                dldir = NULL;
                }

        if (dlflags & MULTIBUF)
                pthread_key_delete(dlkey);

        dlflags |= ~(INITED | MULTIBUF);
        pthread_mutex_unlock(&dlmutex);
        pthread_mutex_destroy(&dlmutex);
}


static void
dlinit(void)

{
        int locked;

        /**
        ***     Initialize the package.
        ***     Should be call once per process.
        **/

        locked = !pthread_mutex_lock(&dlmutex);

        if (!(dlflags & INITED)) {
                dlflags &= ~THREADS;

                if (locked)
                        dlflags |= THREADS;

                Qp0zInitEnv();
                dldir = xmlHashCreate(16);
                dlflags &= ~MULTIBUF;

                if (dlflags & THREADS)
                        if (!pthread_key_create(&dlkey, dlthreadterm))
                                dlflags |= MULTIBUF;

                atexit(dlterm);
                dlflags |= INITED;
                }

        if (locked)
                pthread_mutex_unlock(&dlmutex);
}


static void
dlthreadinit(void)

{
        dlts_t * p;

        if (!(dlflags & INITED))
                dlinit();

        if (dlflags & MULTIBUF) {
                p = pthread_getspecific(dlkey);

                if (!p) {
                        p = (dlts_t *) malloc(sizeof *p);

                        if (p) {
                                p->lockcount = 0;
                                p->iserror = 0;

                                if (pthread_setspecific(dlkey, p))
                                        free(p);
                                }
                        }
                }
}


static void
dllock(void)

{
        dlts_t * p;

        if (!(dlflags & THREADS))
                return;

        if (dlflags & MULTIBUF) {
                p = pthread_getspecific(dlkey);

                if (p && p->lockcount) {
                        p->lockcount++;
                        return;
                        }
                }
        else
                p = (dlts_t *) NULL;

        if (pthread_mutex_lock(&dlmutex))
                return;

        if (p)
                p->lockcount++;
}


static void
dlunlock(void)

{
        dlts_t * p;

        if (!(dlflags & THREADS))
                return;

        if (dlflags & MULTIBUF) {
                p = pthread_getspecific(dlkey);

                if (p && p->lockcount > 1) {
                        p->lockcount--;
                        return;
                        }
                }
        else
                p = (dlts_t *) NULL;

        if (pthread_mutex_unlock(&dlmutex))
                return;

        if (p)
                p->lockcount--;
}


const char *
dlerror(void)

{
        dlts_t * p;

        dlthreadinit();

        if (!(dlflags & MULTIBUF))
                p = &static_buf;
        else if (!(p = (dlts_t *) pthread_getspecific(dlkey)))
                p = &static_buf;

        if (!p->iserror)
                return (const char *) NULL;

        p->iserror = 0;
        return p->str;
}


static void
dlseterror_from_errno(unsigned int err_no)

{
        dlts_t * p;

        if (!(dlflags & MULTIBUF))
                p = &static_buf;
        else if (!(p = (dlts_t *) pthread_getspecific(dlkey)))
                p = &static_buf;

        strcpy(p->str, strerror(err_no));
        p->iserror = 1;
}


static void
dlseterror_from_exception(volatile _INTRPT_Hndlr_Parms_T * excp)

{
        int i;
        Qmh_Rtvm_RTVM0300_t * imp;
        char * cp;
        _INTRPT_Hndlr_Parms_T * p;
        dlts_t * q;
        char rtvmbuf[30000];
        Qus_EC_t errinfo;

        p = (_INTRPT_Hndlr_Parms_T *) excp;
        errinfo.Bytes_Provided = 0;             /* Exception on error. */
        QMHRTVM(rtvmbuf, sizeof rtvmbuf, "RTVM0300", p->Msg_Id,
            "QCPFMSG   QSYS      ", p->Ex_Data, p->Msg_Data_Len,
            "*YES      ", "*NO       ", &errinfo);
        imp = offset_by(Qmh_Rtvm_RTVM0300_t, rtvmbuf, 0);

        if (!(dlflags & MULTIBUF))
                q = &static_buf;
        else if (!(q = (dlts_t *) pthread_getspecific(dlkey)))
                q = &static_buf;

        if (i = imp->Length_Message_Returned)
                cp = offset_by(char, imp, imp->Offset_Message_Returned);
        else if (i = imp->Length_Help_Returned)
                cp = offset_by(char, imp, imp->Offset_Help_Returned);
        else {
                q->iserror = 0;
                return;
                }

        q->iserror = 1;

        if (i > sizeof q->str - 1)
                i = sizeof q->str - 1;

        memcpy(q->str, cp, i);
        q->str[i] = '\0';
}


static int
dlparentpath(const char * path, size_t len)

{
        if (len <= 1)
                return len;

        while (path[--len] != '/')
                ;

        return len? len: 1;
}


static int
dlmakepath(char * path, size_t pathlen, const char * tail, size_t taillen)

{
        int i;

        if (taillen && tail[0] == '/')
                pathlen = 0;

        for (;;) {
                while (taillen && *tail == '/') {
                        tail++;
                        taillen--;
                        }

                if (!taillen)
                        break;

                for (i = 0; i < taillen; i++)
                        if (tail[i] == '/')
                                break;

                if (*tail == '.')
                        switch (i) {

                        case 2:
                                if (tail[1] != '.')
                                        break;
                                        
                                pathlen = dlparentpath(path, pathlen);

                        case 1:
                                tail += i;
                                taillen -= i;
                                continue;
                                }

                if (pathlen + i + 1 >= MAXPATHLEN) {
                        errno = ENAMETOOLONG;
                        return -1;
                        }

                path[pathlen++] = '/';
                memcpy(path + pathlen, tail, i);
                pathlen += i;
                }

        if (!pathlen)
                path[pathlen++] = '/';

        path[pathlen] = '\0';
        return pathlen;
}


static int
dlresolveLink(const char * path, char * buf, size_t bufsiz)

{
        int n;
        int l1;
        int l2;
        struct stat sbuf;
        char buf1[MAXPATHLEN + 1];
        char buf2[MAXPATHLEN + 1];

        /**
        ***     Resolve symbolic link to IFS object name.
        **/

        if (!buf) {
                errno = EFAULT;
                return -1;
                }

        if (!path || !*path || !bufsiz) {
                errno = EINVAL;
                return -1;
                }

        if (*path != '/') {
                if (!getcwd(buf1, sizeof buf1))
                        return -1;

                l1 = strlen(buf1);
                }
        else
                l1 = 0;

        l1 = dlmakepath(buf1, l1, path, strlen(path));
        n = 0;

        for (;;) {
                if (l1 < 0)
                        return -1;

                if (n++ >= 256) {
                        errno = ELOOP;
                        return -1;
                        }

                if (lstat(buf1, &sbuf)) {
                        if (errno == ENOENT)
                                break;

                        return -1;
                        }

                if (!S_ISLNK(sbuf.st_mode))
                        break;

                if (sbuf.st_size > MAXPATHLEN) {
                        errno = ENAMETOOLONG;
                        return -1;
                        }

                l2 = readlink(buf1, buf2, MAXPATHLEN + 1);

                if (l2 < 0)
                        return -1;

                if (buf2[0] != '/')
                        l1 = dlparentpath(buf1, l1);

                l1 = dlmakepath(buf1, l1, buf2, l2);
                }

        if (l1 >= bufsiz) {
                errno = ENAMETOOLONG;
                return -1;
                }

        memcpy(buf, buf1, l1 + 1);
        return l1;
}


static int
dlGetObjectName(Qp0l_QSYS_Info_t * qsysinfo, const char * dir,
                        int dirlen, const char * link)

{
        int n;
        char * namebuf;
        Qlg_Path_Name_T * qptp;
        char pathbuf[sizeof(Qlg_Path_Name_T) + _QP0L_DIR_NAME_LG + 4];
        Qus_EC_t errinfo;
        struct stat sbuf;

        /**
        ***     Get QSYS object library/name/member and type corresponding to
        ***             the symbolic `link' in directory `dir'.
        **/

        if (!qsysinfo) {
                errno = EFAULT;
                return -1;
                }

        if (!dir && !link) {
                errno = EINVAL;
                return -1;
                }

        qptp = (Qlg_Path_Name_T *) pathbuf;
        namebuf = pathbuf + sizeof(Qlg_Path_Name_T);
        n = 0;

        /**
        ***     Build full path.
        **/

        if (dir) {
                if (dirlen < 0 || dirlen > _QP0L_DIR_NAME_LG + 4)
                        dirlen = _QP0L_DIR_NAME_LG + 4;

                while (*dir && n < dirlen)
                        namebuf[n++] = *dir++;
                }

        if (n && namebuf[n - 1] == '/')
                n--;

        if (link) {
                if (*link && *link != '/' && n < _QP0L_DIR_NAME_LG + 4)
                        namebuf[n++] = '/';

                while (*link && n < _QP0L_DIR_NAME_LG + 4)
                        namebuf[n++] = *link++;
                }

        if (!n || n > _QP0L_DIR_NAME_LG) {
                errno = ENAMETOOLONG;
                return -1;
                }

        namebuf[n] = '\0';
        n = dlresolveLink(namebuf, namebuf, _QP0L_DIR_NAME_LG + 1);

        if (n == -1)
                return -1;

        if (stat(namebuf, &sbuf))
                return -1;

        memset((char *) qptp, 0, sizeof *qptp);
        qptp->Path_Length = n;
        qptp->Path_Name_Delimiter[0] = '/';
        errinfo.Bytes_Provided = sizeof errinfo;
        Qp0lCvtPathToQSYSObjName(qptp, qsysinfo, "QSYS0100", sizeof *qsysinfo,
            0, &errinfo);
        return errinfo.Bytes_Available? -1: 0;
}


static const char *
getcomponent(char * dst, const char * src)

{
        int i;

        /**
        ***     Get a path component of at most 10 characters and
        ***             map it to upper case.
        ***     Return the address of the next delimiter in source.
        **/

        for (i = 0;; src++) {
                if (!*src || *src == ' ' || *src == '/') {
                        *dst = '\0';
                        return src;
                        }

                if (i < 10) {
                        *dst++ = toupper(*src);
                        i++;
                        }
                }
}


static int
dlpath2QSYS(Qp0l_QSYS_Info_t * qsysinfo, const char * path, const char * dftlib)

{
        unsigned int flags;
        char * cp;

        /**
        ***     Convert the given path to a QSYS object name.
        ***     Syntax rules for paths are:
        ***
        ***     '/'+ [ <library> [  '/'+ <file> [ '/'+ <member> ] ] '/'* ]
        ***     <library> '/'+ <file> [ '/'+ <member> ] '/'*
        ***     <file> '/'*
        ***
        ***     If default library is not given, *LIBL is assumed.
        ***     Components may no contain spaces. They are translated to
        ***             uppercase. Only the first 10 characters are significant.
        ***     There is no check for the validity of the given components and
        ***             for the object existence.
        ***     Component types are not in the path, but generated internally.
        ***     CCSID is not processed.
        ***
        ***     Return 0 upon success, else -1.
        **/

        if (!qsysinfo || !path) {
                errno = EFAULT;
                return -1;
                }

        /**
        ***     Strip leading spaces.
        **/

        while (*path == ' ')
                path++;

        /**
        ***     Check for null path.
        **/

        if (!*path) {
                errno = EINVAL;
                return -1;
                }

        /**
        ***     Preset the result structure.
        **/

        memset((char *) qsysinfo, 0, sizeof *qsysinfo);

        /**
        ***     Determine the format.
        **/

        if (*path == '/') {
                /**
                ***     Library component present.
                **/

                while (*++path == '/')
                        ;

                if (!*path || *path == ' ')
                        strcpy(qsysinfo->Lib_Name, "QSYS");
                else
                        path = getcomponent(qsysinfo->Lib_Name, path);

                /**
                ***     Check for file component and get it.
                **/

                if (*path == '/') {
                        while (*++path == '/')
                                ;

                        if (*path && *path != ' ')
                                path = getcomponent(qsysinfo->Obj_Name, path);
                        }
                }
        else {
                /**
                ***     The mandatory component is the <file>.
                **/

                path = getcomponent(qsysinfo->Obj_Name, path);

                while (*path == '/')
                        path++;

                /**
                ***     If there is a second component, move the first to
                ***             the library name and parse the file name.
                **/

                if (*path && *path != ' ') {
                        strcpy(qsysinfo->Lib_Name, qsysinfo->Obj_Name);
                        memset(qsysinfo->Obj_Name, 0,
                            sizeof qsysinfo->Obj_Name);
                        path = getcomponent(qsysinfo->Obj_Name, path);
                        }
                else
                        strcpy(qsysinfo->Lib_Name, dftlib? dftlib: "*LIBL");
                }

        /**
        ***     Check and set-up member.
        **/

        while (*path == '/')
                path++;

        if (*path && *path != ' ') {
                path = getcomponent(qsysinfo->Mbr_Name, path);
                strcpy(qsysinfo->Mbr_Type, "*MBR");

                while (*path == '/')
                        path++;
                }

        strcpy(qsysinfo->Lib_Type, "*LIB");

        if (qsysinfo->Obj_Name[0])
                strcpy(qsysinfo->Obj_Type, "*FILE");

        qsysinfo->Bytes_Returned = sizeof *qsysinfo;
        qsysinfo->Bytes_Available = sizeof *qsysinfo;

        /**
        ***     Strip trailing spaces.
        **/

        while (*path == ' ')
                path++;

        if (*path) {
                errno = EINVAL;
                return -1;
                }

        return 0;
}


static int
dl_ifs_link(Qp0l_QSYS_Info_t * qsysinfo, const char * pathname)

{
        /**
        ***     If `pathname' is a link found in IFS, set `qsysinfo' to its
        ***             DB2 name.
        ***     Return 0 if OK, else -1.
        **/

        return dlGetObjectName(qsysinfo, (const char *) NULL, 0, pathname);
}


static int
dl_path_link(Qp0l_QSYS_Info_t * qsysinfo, const char * pathvar,
        const char * filename, int (* testproc)(const Qp0l_QSYS_Info_t *))

{
        const char * p;
        const char * q;
        unsigned int i;
        const char * path;

        /**
        ***     If `filename' is not a path and is a link found in one of the
        ***             colon-separated paths in environment variable `pathvar',
        ***             set `qsysinfo' to its DB2 name.
        ***     Return 0 if OK, else -1.
        **/

        i = _QP0L_DIR_NAME_LG;

        for (p = filename; *p; p++)
                if (*p == '/' || !--i)
                        return -1;              /* Too long or a path. */

        /**
        ***     Make sure we have the LD_LIBRARY_PATH environment
        ***             variable value.
        **/

        path = getenv(pathvar);

        if (!path)
                return -1;                      /* No path list. */

        /**
        ***     Try in each path listed.
        **/

        q = path;

        if (!*q)
                return -1;                      /* No path list. */

        for (;;) {
                for (p = q; *p && *p != ':'; p++)
                        ;

                if (p > q)                      /* Ignore null path. */
                        if (!dlGetObjectName(qsysinfo, q, p - q, filename))
                                if (!testproc || (*testproc)(qsysinfo))
                                        return 0;       /* Found: return. */

                if (!*p)
                        break;

                q = p + 1;
                }

        errno = ENOENT;
        return -1;
}


static int
dl_DB2_path(Qp0l_QSYS_Info_t * qsysinfo, const char * pathname)

{
        if (dlpath2QSYS(qsysinfo, pathname, (const char *) NULL))
                return -1;

        if (qsysinfo->Mbr_Type[0])
                return -1;      /* Service program may not have members. */

        if (!qsysinfo->Obj_Type[0])
                return -1;      /* Object must be specified. */

        strcpy(qsysinfo->Obj_Type, "*SRVPGM");  /* Set our object type. */
        return 0;
}


static int
dl_DB2_name(char * dst, const char * name)

{
        int i;

        for (i = 0; i < 10; i++) {
                switch (*name) {

                default:
                        if (!islower(*name))
                                break;

                case '\0':
                case '/':
                case ' ':
                        return -1;
                        }

                *dst++ = *name++;
                }

        if (!i)
                return -1;

        *dst = '\0';
        return 0;
}


static int
dl_qualified_object(Qp0l_QSYS_Info_t * qsysinfo, const char * pathname)

{
        memset((char *) qsysinfo, 0, sizeof *qsysinfo);

        if (dl_DB2_name(qsysinfo->Obj_Name, pathname) ||
            dl_DB2_name(qsysinfo->Lib_Name, pathname + 10))
                return -1;

        strcpy(qsysinfo->Lib_Type, "*LIB");
        strcpy(qsysinfo->Obj_Type, "*SRVPGM");
        return 0;
}


static int
dl_lib_object(Qp0l_QSYS_Info_t * qsysinfo,
                                const char * libname, const char * pathname)

{
        int i;
        char * cp;

        strcpy(qsysinfo->Lib_Name, libname);
        strcpy(qsysinfo->Lib_Type, "*LIB");
        strcpy(qsysinfo->Obj_Type, "*SRVPGM");
        cp = qsysinfo->Obj_Name;

        while (*pathname == ' ')
                pathname++;

        for (i = 0;; pathname++) {
                switch (*pathname) {

                case '\0':
                case ' ':
                        break;

                case '/':
                        return -1;

                default:
                        if (i < 10)
                                *cp++ = toupper(*pathname);

                        i++;
                        continue;
                        }

                break;
                }

        while (*pathname == ' ')
                pathname++;

        if (!i || *pathname)
                return -1;

        *cp = '\0';
        return 0;
}


static int
dl_is_srvpgm(const Qp0l_QSYS_Info_t * qsysinfo)

{
        struct stat sbuf;
        char namebuf[100];

        if (!qsysinfo->Lib_Name[0] || strcmp(qsysinfo->Lib_Type, "*LIB") ||
            !qsysinfo->Obj_Name[0] || strcmp(qsysinfo->Obj_Type, "*SRVPGM") ||
            qsysinfo->Mbr_Name[0] || qsysinfo->Mbr_Type[0])
                return 0;

        /**
        ***     Build the IFS path name for the DB2 object.
        **/

        sprintf(namebuf, "%s/%s.LIB/%s.SRVPGM",
            strcmp(qsysinfo->Lib_Name, "QSYS")? "/QSYS.LIB": "",
            qsysinfo->Lib_Name, qsysinfo->Obj_Name);

        return stat(namebuf, &sbuf) == 0;
}


static int
dlreinit(dlinfo * dlip)

{
        RINZ_TEMPL_T t;
        RINZ_TEMPL_T * p;
        volatile _INTRPT_Hndlr_Parms_T excbuf;

        if (dlip->actinfo.Flags & QLE_ABP_WAS_ACTIVE)
                return 0;

        /**
        ***     Attempt to reinitialize the service program that was loaded.
        ***     The service program must be created to allow re-initialization:
        ***             ALWRINZ(*YES) for this to work. The default is
        ***             ALWRINZ(*NO).
        **/

#pragma exception_handler(err, excbuf, 0, _C2_MH_ESCAPE, _CTLA_HANDLE_NO_MSG)
        p = &t;
        t.rinz_pgm = dlip->pointer;
        t.rinz_agpmk = dlip->actinfo.Act_Grp_Mark;
        _RINZSTAT(p);
#pragma disable_handler

        return 0;

err:
        if (!memcmp((char *) excbuf.Msg_Id, "MCH4421", 7))
                return 0;       /* Program cannot be reinitialized. */

        dlseterror_from_exception(&excbuf);
        return -1;
}


void *
dlsym(void * handle, const char * symbol)

{
        dlinfo * dlip;
        void * p;
        int export_type;
        Qus_EC_t errinfo;
        volatile _INTRPT_Hndlr_Parms_T excbuf;
        static int zero = 0;

        dlthreadinit();

        if (!handle || !symbol) {
                dlseterror_from_errno(EFAULT);
                return (void *) NULL;
                }

        dlip = (dlinfo *) handle;

#pragma exception_handler(error, excbuf, 0, _C2_MH_ESCAPE, _CTLA_HANDLE_NO_MSG)
        errinfo.Bytes_Provided = 0;
        QleGetExpLong(&dlip->actinfo.Act_Mark, &zero, &zero,
            (char *) symbol, &p, &export_type, &errinfo);
        return p;
#pragma disable_handler

error:
        dlseterror_from_exception(&excbuf);
        return (void *) NULL;
}


int
dlclose(void * handle)

{
        dlinfo * dlip;
        void (* _fini)(void);

        dlthreadinit();

        if (!handle) {
                dlseterror_from_errno(EFAULT);
                return -1;
                }

        dlip = (dlinfo *) handle;

        if (dlip->actcount) {
                if (--(dlip->actcount))
                        return 0;

                if (_fini = dlsym(handle, "_fini"))
                        (*_fini)();
                }

        return dlreinit(dlip);
}


static void *
dlopenqsys(const Qp0l_QSYS_Info_t * dllinfo)

{
        dlinfo * dlip;
        dlinfo * dlip2;
        void (* _init)(void);
        unsigned int i;
        _SYSPTR pgmptr;
        unsigned long long actmark;
        Qus_EC_t errinfo;
        char actmarkstr[2 * sizeof actmark + 1];
        static int actinfo_size = sizeof dlip->actinfo;
        volatile _INTRPT_Hndlr_Parms_T excbuf;

        /**
        ***     Capture any type of error and if any occurs,
        ***             return not found.
        **/

#pragma exception_handler(error1, excbuf, 0, _C2_MH_ESCAPE, _CTLA_HANDLE_NO_MSG)
        pgmptr = rslvsp(WLI_SRVPGM, (char *) dllinfo->Obj_Name,
            (char *) dllinfo->Lib_Name ,_AUTH_NONE);

        if (!pgmptr) {
                errno = ENOENT;
                return (void *) NULL;
                }

        /**
        ***     Create a new DLL info block.
        **/

        dlip = (dlinfo *) malloc(sizeof *dlip);

        if (!dlip)
                return (void *) NULL;           /* Cannot create block. */
#pragma disable_handler

        dllock();

#pragma exception_handler(error2, excbuf, 0, _C2_MH_ESCAPE, _CTLA_HANDLE_NO_MSG)
        memset((char *) dlip, 0, sizeof *dlip);
        dlip->pointer = pgmptr;

        /**
        ***     Activate the DLL.
        **/

        errinfo.Bytes_Provided = 0;
        QleActBndPgmLong(&pgmptr, &actmark,
            &dlip->actinfo, &actinfo_size, &errinfo);
        dlip->actinfo.Act_Mark = actmark;

        /**
        ***     Dummy string encoding activation mark to use as hash table key.
        **/

        for (i = 0; actmark; actmark >>= 6)
                actmarkstr[i++] = 0x40 + (actmark & 0x3F);

        actmarkstr[i] = '\0';

        /**
        ***     Check if already activated.
        **/

        dlip2 = (dlinfo *) xmlHashLookup(dldir, actmarkstr);

        if (dlip2) {
                free((char *) dlip);
                dlip = dlip2;
                }
        else if (xmlHashAddEntry(dldir, (const xmlChar *) actmarkstr, dlip)) {
                dlreinit(dlip);
                free((char *) dlip);
                dlunlock();
                return (void *) NULL;
                }
#pragma disable_handler

#pragma exception_handler(error2, excbuf, 0, _C2_MH_ESCAPE, _CTLA_HANDLE_NO_MSG)

        /**
        ***     Bump activation counter.
        **/

        if (!(dlip->actcount++) && (_init = dlsym(dlip, "_init")))
                (*_init)();

        dlunlock();

        /**
        ***     Return the handle.
        **/

        return (void *) dlip;
#pragma disable_handler

error2:
        free((char *) dlip);
        dlunlock();

error1:
        dlseterror_from_exception(&excbuf);
        return (void *) NULL;
}


void *
dlopen(const char * filename, int flag)

{
        void * dlhandle;
        int sverrno;
        Qp0l_QSYS_Info_t dllinfo;

        sverrno = errno;
        errno = 0;

        dlthreadinit();

        if (!filename) {
                dlseterror_from_errno(EFAULT);
                errno = sverrno;
                return NULL;
                }

        /**
        ***     Try to locate the object in the following order:
        ***     _       `filename' is an IFS path.
        ***     _       `filename' is not a path and resides in one of
        ***                     LD_LIBRARY_PATH colon-separated paths.
        ***     _       `filename' is not a path and resides in one of
        ***                     PATH colon-separated paths.
        ***     _       `filename' is a DB2 path (as /library/object).
        ***     _       `filename' is a qualified object name.
        ***     _       `filename' is an object in *CURLIB.
        ***     _       `filename' is an object in *LIBL.
        **/

        if (!dl_ifs_link(&dllinfo, filename) && dl_is_srvpgm(&dllinfo))
                dlhandle = dlopenqsys(&dllinfo);
        else if (!dl_path_link(&dllinfo,
            "LD_LIBRARY_PATH", filename, dl_is_srvpgm))
                dlhandle = dlopenqsys(&dllinfo);
        else if (!dl_path_link(&dllinfo, "PATH", filename, dl_is_srvpgm))
                dlhandle = dlopenqsys(&dllinfo);
        else if (!dl_DB2_path(&dllinfo, filename) && dl_is_srvpgm(&dllinfo))
                dlhandle = dlopenqsys(&dllinfo);
        else if (!dl_qualified_object(&dllinfo, filename) &&
            dl_is_srvpgm(&dllinfo))
                dlhandle = dlopenqsys(&dllinfo);
        else if (!dl_lib_object(&dllinfo, "*CURLIB", filename) &&
            dl_is_srvpgm(&dllinfo))
                dlhandle = dlopenqsys(&dllinfo);
        else if (!dl_lib_object(&dllinfo, "*LIBL", filename) &&
            dl_is_srvpgm(&dllinfo))
                dlhandle = dlopenqsys(&dllinfo);
        else
                dlhandle = NULL;

        if (!dlhandle && errno)
                dlseterror_from_errno(errno);

        errno = sverrno;
        return dlhandle;
}
