Search code examples
clibcurlloadlibrary

Passing back data from function loaded by LoadLibrary in C?


I'm trying to learn how to use LoadLibrary properly in a C function, but am having difficulty and there are not a lot of good tutorials to follow. I've created a simple C program that uses the libCurl library to successfully fetch the HTML of a website and print it to console. I am now trying to re-implement the same function using LoadLibrary and GetProcAddress and the libcurl.dll.

How do I pass data back from a function that is loaded into memory?

Posted below is the function using the .lib that works and subsequently the function trying to use the DLL that is failing to compile.

Here is my working program:

#include "stdafx.h"
#include "TestWebService.h"
#include "curl/curl.h"

int main(int argc, char **argv)
{
    CURL *curl;
    CURLcode res;

    curl = curl_easy_init();
    if (curl) {

        struct string s;
        init_string(&s);

        curl_easy_setopt(curl, CURLOPT_URL, "http://example.com");
        /* example.com is redirected, so we tell libcurl to follow redirection */
        curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1L);
        curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, writefunc);
        curl_easy_setopt(curl, CURLOPT_WRITEDATA, &s);

        /* Perform the request, res will get the return code */
        res = curl_easy_perform(curl);
        /* Check for errors */
        if (res != CURLE_OK)
            fprintf(stderr, "curl_easy_perform() failed: %s\n", curl_easy_strerror(res));

        /* always cleanup */
        printf("%s\n", s.ptr);
        free(s.ptr);
        curl_easy_cleanup(curl);
    }

    return 0;
}

Here is my attempt to replicate the same functionality using LoadLibrary only (i.e. Not using the libCurl.lib). But I get the following error message and cannot determine why.

1) a value of type "CURL" cannot be assigned to an entity of type "CURL *"  
2) '=': cannot convert from 'CURL' to 'CURL *' 

#include "stdafx.h"
#include "TestWebService.h"
#include "curl/curl.h"

typedef CURL (*CurlInitFunc)();

int  main(int argc, char **argv)
{
    HINSTANCE            hLib = NULL;
    hLib = LoadLibrary("libcurl.dll");
    if (hLib != NULL)
    {
        CURL *curl;
        CurlInitFunc _CurlInitFunc;
        _CurlInitFunc = (CurlInitFunc)GetProcAddress(hLib, "curl_easy_init");
        if (_CurlInitFunc)
        {
            curl = _CurlInitFunc();

        }

    }
    return 0;
}

Solution

  • This line:

    typedef CURL (*CurlInitFunc)();
    

    declares a pointer to a function that returns a CURL. But the prototype of curl_easy_init() is:

    CURL *curl_easy_init();
    

    that means it returns a pointer to CURL, that is CURL*

    Therefore the correct declaration is:

    typedef CURL *(*CurlInitFunc)();