stas        2003/12/14 19:13:36

  Modified:    src/modules/perl modperl_mgv.c
               .        Changes
  Log:
  Prevent a problem where an autovivified package (stash) prevents from
  modperl_mgv to load the file with that package (until now it was
  checking whether the stash existed already and skipped the loading if
  that was the case). Now checking %INC and attempting to load the
  module. Reporting the failure only if the module has failed to load
  and the stash is not defined (so that it's possible to autovivify
  packages without loading them from an external file).
  
  Revision  Changes    Path
  1.28      +56 -12    modperl-2.0/src/modules/perl/modperl_mgv.c
  
  Index: modperl_mgv.c
  ===================================================================
  RCS file: /home/cvs/modperl-2.0/src/modules/perl/modperl_mgv.c,v
  retrieving revision 1.27
  retrieving revision 1.28
  diff -u -u -r1.27 -r1.28
  --- modperl_mgv.c     18 Sep 2003 07:58:46 -0000      1.27
  +++ modperl_mgv.c     15 Dec 2003 03:13:36 -0000      1.28
  @@ -181,6 +181,31 @@
   }
   #endif
   
  +
  +static void package2filename(apr_pool_t *p, const char *package,
  +                             char **filename, int *len)
  +{
  +    *filename = apr_palloc(p, (strlen(package)+4)*sizeof(char));
  +    const char *s;
  +    char *d;
  +
  +    for (s = package, d = *filename; *s; s++, d++) {
  +        if (*s == ':' && s[1] == ':') {
  +            *d = '/';
  +            s++;
  +        }
  +        else {
  +            *d = *s;
  +        }
  +    }
  +    *d++ = '.';
  +    *d++ = 'p';
  +    *d++ = 'm';
  +    *d   = '\0';
  +
  +    *len = d - *filename;
  +}
  +
   /* currently used for complex filters attributes parsing */
   /* XXX: may want to generalize it for any handlers */
   #define MODPERL_MGV_DEEP_RESOLVE(handler, p) \
  @@ -259,23 +284,42 @@
           }
       }
   
  -    if (!(stash || (stash = gv_stashpv(name, FALSE))) &&
  -        MpHandlerAUTOLOAD(handler)) {
  -        MP_TRACE_h(MP_FUNC,
  -                   "package %s not defined, attempting to load\n", name);
  -
  -        if (modperl_require_module(aTHX_ name, FALSE)) {
  -            MP_TRACE_h(MP_FUNC, "loaded %s package\n", name);
  -            if (!(stash = gv_stashpv(name, FALSE))) {
  -                MP_TRACE_h(MP_FUNC, "%s package still does not exist\n",
  -                           name);
  +    if (!stash && MpHandlerAUTOLOAD(handler)) {
  +        int len;
  +        char *filename;
  +        SV **svp;
  +
  +        package2filename(p, name, &filename, &len);
  +        svp = hv_fetch(GvHVn(PL_incgv), filename, len, 0);
  +
  +        if (!(svp && *svp != &PL_sv_undef)) { /* not in %INC */
  +            MP_TRACE_h(MP_FUNC,
  +                       "package %s not in %INC, attempting to load '%s'\n",
  +                       name, filename);
  +
  +            if (modperl_require_module(aTHX_ name, FALSE)) {
  +                MP_TRACE_h(MP_FUNC, "loaded %s package\n", name);
  +            }
  +            else {
  +                MP_TRACE_h(MP_FUNC, "failed to load %s package\n", name);
                   return 0;
               }
           }
           else {
  -            MP_TRACE_h(MP_FUNC, "failed to load %s package\n", name);
  -            return 0;
  +            MP_TRACE_h(MP_FUNC, "package %s seems to be loaded\n"
  +                       "  $INC{%s)='%s';\n",
  +                       name, filename, SvPV_nolen(*svp));
           }
  +    }
  +
  +    /* try to lookup the stash only after loading the module, to avoid
  +     * the case where a stash is autovivified by a user before the
  +     * module was loaded, preventing from loading the module
  +     */
  +    if (!(stash || (stash = gv_stashpv(name, FALSE)))) {
  +        MP_TRACE_h(MP_FUNC, "package %s seems to be loaded, "
  +                   "but can't find its stash\n", name);
  +        return 0;
       }
   
       if ((gv = gv_fetchmethod(stash, handler_name)) && (cv = GvCV(gv))) {
  
  
  
  1.281     +8 -0      modperl-2.0/Changes
  
  Index: Changes
  ===================================================================
  RCS file: /home/cvs/modperl-2.0/Changes,v
  retrieving revision 1.280
  retrieving revision 1.281
  diff -u -u -r1.280 -r1.281
  --- Changes   15 Dec 2003 02:50:22 -0000      1.280
  +++ Changes   15 Dec 2003 03:13:36 -0000      1.281
  @@ -12,6 +12,14 @@
   
   =item 1.99_12-dev
   
  +Prevent a problem where an autovivified package (stash) prevents from
  +modperl_mgv to load the file with that package (until now it was
  +checking whether the stash existed already and skipped the loading if
  +that was the case). Now checking %INC and attempting to load the
  +module. Reporting the failure only if the module has failed to load
  +and the stash is not defined (so that it's possible to autovivify
  +packages without loading them from an external file). [Stas]
  +
   MaxClients is now overridable from the t/TEST -maxclients command line
   option (it was hardcoded before). [Stas]
   
  
  
  

Reply via email to