Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Apache2 can't load mod_dav_fs.so #2479

Closed
flxchn opened this issue Jun 1, 2018 · 11 comments · Fixed by #8049
Closed

Apache2 can't load mod_dav_fs.so #2479

flxchn opened this issue Jun 1, 2018 · 11 comments · Fixed by #8049
Labels
bug report Something is not working properly help wanted Help is wanted in order to solve the issue

Comments

@flxchn
Copy link

flxchn commented Jun 1, 2018

Clean install apache2.
Open /data/data/com.termux/files/usr/etc/apache2/httpd.conf
Change

#LoadModule dav_module libexec/apache2/mod_dav.so
#LoadModule dav_fs_module libexec/apache2/mod_dav_fs.so
#LoadModule dav_lock_module libexec/apache2/mod_dav_lock.so

To

LoadModule dav_module libexec/apache2/mod_dav.so
LoadModule dav_fs_module libexec/apache2/mod_dav_fs.so
LoadModule dav_lock_module libexec/apache2/mod_dav_lock.so

Save, Run

$ httpd -t
httpd: Syntax error on line 168 of /data/data/com.termux/files/usr/etc/apache2/httpd.conf: Cannot load libexec/apache2/mod_dav_fs.so into server: dlopen failed: cannot locate symbol "dav_hook_gather_propsets" referenced by "mod_dav_fs.so"...

@fornwall
Copy link
Member

fornwall commented Jun 6, 2018

Thanks for reporting! Which Android version are you running?

@flxchn
Copy link
Author

flxchn commented Jun 6, 2018

I'm running android 5.1.1

$ uname
Linux localhost 3.14.29 #2 SMP PREEMPT Sat May 7 19:48:29 CST 2016 aarch64 GNU/Linux
$ getprop
[ro.product.cpu.abi2]: [armeabi]
[ro.product.cpu.abi]: [armeabi-v7a]
[ro.product.cpu.abilist32]: [armeabi-v7a,armeabi]
[ro.product.cpu.abilist64]: []
[ro.product.cpu.abilist]: [armeabi-v7a,armeabi]
[ro.product.device]: [p201]
[ro.product.locale.language]: [en]
[ro.product.locale.region]: [US]
[ro.product.manufacturer]: [amlogic]
[ro.product.model]: [MXQPRO]
[ro.product.name]: [p201]

And found other problem.
Apache2 and nginx do not correctly display files larger than 2 GB. I looked up the previous issue, #902, does nginx and Apache2 need update?

@fornwall
Copy link
Member

fornwall commented Jun 7, 2018

Seems to be a problem also on Android 8.1. dav_hook_gather_propsets should be provided by libexec/apache2/mod_dav.so.

Apache2 and nginx do not correctly display files larger than 2 GB. I looked up the previous issue, #902, does nginx and Apache2 need update?

It's a problem with -D_FILE_OFFSET_BITS=64 not working on 32-bit Android prior to Android 7.0, so the packages are not yet built with that enabled.

@tomty89
Copy link
Contributor

tomty89 commented Jun 7, 2018

It's just android/ndk#201 again.

$ sed -i "s/#LoadModule dav_lock_module/LoadModule dav_lock_module/" ../usr/etc/apache2/httpd.conf
$ httpd                                                                            
httpd: Syntax error on line 170 of /data/data/com.termux/files/usr/etc/apache2/httpd.conf: Cannot load libexec/apache2/mod_dav_lock.so into server: dlopen failed: cannot locate symbol "dav_new_error" referenced by "/data/data/com.termux/files/usr/libexec/apache2/mod_dav_lock.so"...
$ sed -i "s/#LoadModule dav_fs_module/LoadModule dav_fs_module/" ../usr/etc/apache2/httpd.conf
$ httpd                                                                            
httpd: Syntax error on line 169 of /data/data/com.termux/files/usr/etc/apache2/httpd.conf: Cannot load libexec/apache2/mod_dav_fs.so into server: dlopen failed: cannot locate symbol "dav_hook_gather_propsets" referenced by "/data/data/com.termux/files/usr/libexec/apache2/mod_dav_fs.so"...
$ LD_PRELOAD=$PREFIX/libexec/apache2/mod_dav.so httpd                              
AH00558: httpd: Could not reliably determine the server's fully qualified domain name, using 127.0.0.1. Set the 'ServerName' directive globally to suppress this message
$ curl http://localhost:8080                                                       
<html><body><h1>It works!</h1></body></html>
$

@fornwall
Copy link
Member

fornwall commented Jun 8, 2018

@tomty89 But android/ndk#201 is about On Android only the main executable and LD_PRELOADs are considered to be RTLD_GLOBAL, all the dependencies of the main executable remain RTLD_LOCAL - and in this case mod_dav.so contains the symbol, which is not a dependency of the main exectable, right?

So if mod_dav.so is dlopen:ed with RTLD_GLOBAL its symbol should be available for the later dlopen:ed mod_dav_lock.so (at least on Android 6.0+, which supports RTLD_GLOBAL), or am i missing what is happening here?

@fornwall
Copy link
Member

fornwall commented Jun 8, 2018

From looking at apache2 sources, it seems that modules/core/mod_so.c does the module loading:

static const char *dso_load(cmd_parms *cmd, apr_dso_handle_t **modhandlep,
                            const char *filename, const char **used_filename)
{   
    int retry = 0;
    const char *fullname = ap_server_root_relative(cmd->temp_pool, filename);
    char my_error[256];
    if (filename != NULL && ap_strchr_c(filename, '/') == NULL) {
        /* retry on error without path to use dlopen()'s search path */
        retry = 1;
    }
    
    if (fullname == NULL && !retry) {
        return apr_psprintf(cmd->temp_pool, "Invalid %s path %s",
                            cmd->cmd->name, filename);
    }
    *used_filename = fullname;
    if (apr_dso_load(modhandlep, fullname, cmd->pool) == APR_SUCCESS) {
        return NULL;
    }
    if (retry) {
        *used_filename = filename;
        if (apr_dso_load(modhandlep, filename, cmd->pool) == APR_SUCCESS)
            return NULL;
    }
    
    return apr_pstrcat(cmd->temp_pool, "Cannot load ", filename,
                        " into server: ",
                        apr_dso_error(*modhandlep, my_error, sizeof(my_error)),
                        NULL);
}

Here we can see the Cannot load $filename into server: log message. So it loads the module with apr_dso_load() from apr, which there is defined in dso/unix/dso.c to use RTLD_GLOBAL as:

APR_DECLARE(apr_status_t) apr_dso_load(apr_dso_handle_t **res_handleconst char *path, apr_pool_t *pool)
{
#if defined(DSO_USE_SHL)
    shl_t os_handle = shl_load(path, BIND_IMMEDIATE, 0L);

#elif defined(DSO_USE_DYLD)
    [...]
#elif defined(DSO_USE_DLFCN)
#if defined(OSF1) || defined(SEQUENT) || defined(SNI) ||\
    (defined(__FreeBSD_version) && (__FreeBSD_version >= 220000)) ||\
    defined(__DragonFly__)
    void *os_handle = dlopen((char *)path, RTLD_NOW | RTLD_GLOBAL);

#else
    int flags = RTLD_NOW | RTLD_GLOBAL;
    void *os_handle;
#ifdef _AIX
    if (strchr(path + 1, '(') && path[strlen(path) - 1] == ')')
    {
        /* This special archive.a(dso.so) syntax is required for
         * the way libtool likes to build shared libraries on AIX.
         * dlopen() support for such a library requires that the
         * RTLD_MEMBER flag be enabled.
         */
        flags |= RTLD_MEMBER;
    }
#endif
    os_handle = dlopen(path, flags);
#endif····
#endif /* DSO_USE_x */

    *res_handle = apr_pcalloc(pool, sizeof(**res_handle));

    if(os_handle == NULL) {
#if defined(DSO_USE_SHL)
        (*res_handle)->errormsg = strerror(errno);
        return APR_EDSOOPEN;
#elif defined(DSO_USE_DYLD)
        (*res_handle)->errormsg = (err_msg) ? err_msg : "link failed";
        return APR_EDSOOPEN;
#elif defined(DSO_USE_DLFCN)
        (*res_handle)->errormsg = dlerror();
        return APR_EDSOOPEN;
#endif
    }

    (*res_handle)->handle = (void*)os_handle;
    (*res_handle)->pool = pool;
    (*res_handle)->errormsg = NULL;

    apr_pool_cleanup_register(pool, *res_handle, dso_cleanup, apr_pool_cleanup_null);

    return APR_SUCCESS;
}

@fornwall fornwall added the bug report Something is not working properly label Jun 8, 2018
@vishalbiswas
Copy link
Contributor

vishalbiswas commented Jun 8, 2018

3 options:

  1. LD_PRELOAD the dependency
  2. Use patchelf to explicitly state dependency.
  3. Use static modules.

PS: This is exactly what's happening to php modules.

@ghost ghost added the help wanted Help is wanted in order to solve the issue label May 6, 2020
@stale
Copy link

stale bot commented Nov 18, 2021

This issue/PR has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions.

@stale stale bot added the wontfix Issue won't be fixed label Nov 18, 2021
@xtkoba
Copy link
Contributor

xtkoba commented Nov 22, 2021

Another option will be to complement DT_NEEDED and DT_RUNPATH with ld options --as-needed and -rpath respectively. The effect should be the same as when using patchelf.

@stale stale bot removed the wontfix Issue won't be fixed label Nov 22, 2021
@xtkoba
Copy link
Contributor

xtkoba commented Nov 22, 2021

Other dependencies for currently built modules:

  • mod_cache_*.so needs mod_cache.so
  • mod_dav_*.so needs mod_dav.so
  • mod_heartbeat.so needs mod_watchdog.so
  • mod_proxy_*.so needs mod_proxy.so
  • mod_session_*.so needs mod_session.so

@xtkoba
Copy link
Contributor

xtkoba commented Nov 24, 2021

PR #8049 is based on #2479 (comment) and is rather hacky, but at least it works:

$ readelf -Wa libexec/apache2/mod_dav_fs.so | egrep '(RUNPATH|NEEDED)'
 0x000000000000001d (RUNPATH)            Library runpath: [/data/data/com.termux/files/usr/lib:/data/data/com.termux/files/usr/libexec/apache2]
 0x0000000000000001 (NEEDED)             Shared library: [libandroid-support.so]
 0x0000000000000001 (NEEDED)             Shared library: [libapr-1.so]
 0x0000000000000001 (NEEDED)             Shared library: [libaprutil-1.so]
 0x0000000000000001 (NEEDED)             Shared library: [mod_dav.so]
 0x0000000000000001 (NEEDED)             Shared library: [libc.so]

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug report Something is not working properly help wanted Help is wanted in order to solve the issue
Projects
None yet
Development

Successfully merging a pull request may close this issue.

5 participants