[4.1] 2765c02 Let vcl_dir and vmod_dir also take colon separated paths.
Lasse Karstensen
lkarsten at varnish-software.com
Thu Jan 14 15:15:12 CET 2016
commit 2765c02d6eec7599c2b16ffd76ea28b1a9748c31
Author: Poul-Henning Kamp <phk at FreeBSD.org>
Date: Fri Jan 8 18:51:44 2016 +0000
Let vcl_dir and vmod_dir also take colon separated paths.
diff --git a/bin/varnishd/mgt/mgt_param_tbl.c b/bin/varnishd/mgt/mgt_param_tbl.c
index 16886b2..59fcfed 100644
--- a/bin/varnishd/mgt/mgt_param_tbl.c
+++ b/bin/varnishd/mgt/mgt_param_tbl.c
@@ -58,14 +58,16 @@ struct parspec mgt_parspec[] = {
VCC_CC , NULL },
{ "vcl_dir", tweak_string, &mgt_vcl_dir,
NULL, NULL,
- "Directory from which relative VCL filenames (vcl.load and "
- "include) are opened.",
+ "Directory (or colon separated list of directories) "
+ "from which relative VCL filenames (vcl.load and "
+ "include) are to be found.",
0,
VARNISH_VCL_DIR,
NULL },
{ "vmod_dir", tweak_string, &mgt_vmod_dir,
NULL, NULL,
- "Directory where VCL modules are to be found.",
+ "Directory (or colon separated list of directories) "
+ "where VMODs are to be found.",
0,
VARNISH_VMOD_DIR,
NULL },
diff --git a/bin/varnishtest/tests/m00008.vtc b/bin/varnishtest/tests/m00008.vtc
index 232d3c0..833a282 100644
--- a/bin/varnishtest/tests/m00008.vtc
+++ b/bin/varnishtest/tests/m00008.vtc
@@ -13,12 +13,12 @@ varnish v1 -vcl+backend {
varnish v1 -cliok "param.set vcc_unsafe_path off"
-varnish v1 -errvcl {'import ... from path ...' not allowed.} {
+varnish v1 -errvcl {'import ... from path ...' is unsafe.} {
backend default { .host = "${s1_sock}"; }
import ${vmod_std};
}
-varnish v1 -cliok "param.set vmod_dir ${topbuild}/lib/libvmod_std/.libs/"
+varnish v1 -cliok "param.set vmod_dir /nowhere:${topbuild}/lib/libvmod_std/.libs/:/else"
varnish v1 -vcl+backend {
import std;
diff --git a/lib/libvcc/vcc_compile.c b/lib/libvcc/vcc_compile.c
index aaba4bf..c52dd8d 100644
--- a/lib/libvcc/vcc_compile.c
+++ b/lib/libvcc/vcc_compile.c
@@ -450,22 +450,24 @@ vcc_destroy_source(struct source *sp)
/*--------------------------------------------------------------------*/
static struct source *
-vcc_file_source(const struct vcp * const vcp, struct vsb *sb, const char *fn)
+vcc_file_source(const struct vcp * const vcp, struct vsb *sb, char *fn)
{
- char *f;
+ char *f, *fnp;
struct source *sp;
if (!vcp->unsafe_path && strchr(fn, '/') != NULL) {
VSB_printf(sb, "Include path is unsafe '%s'\n", fn);
return (NULL);
}
- f = VFIL_readfile(vcp->vcl_dir, fn, NULL);
- if (f == NULL) {
- VSB_printf(sb, "Cannot read file '%s': %s\n",
- fn, strerror(errno));
+ f = NULL;
+ fnp = fn;
+ if (VFIL_searchpath(vcp->vcl_path, NULL, &f, &fnp) || f == NULL) {
+ VSB_printf(sb, "Cannot read file '%s' (%s)\n",
+ fnp != NULL ? fnp : fn, strerror(errno));
return (NULL);
}
- sp = vcc_new_source(f, NULL, fn);
+ sp = vcc_new_source(f, NULL, fnp);
+ free(fnp);
sp->freeit = f;
return (sp);
}
@@ -801,6 +803,7 @@ VCP_VCL_dir(struct vcp *vcp, const char *str)
CHECK_OBJ_NOTNULL(vcp, VCP_MAGIC);
REPLACE(vcp->vcl_dir, str);
+ VFIL_setpath(&vcp->vcl_path, str);
}
/*--------------------------------------------------------------------
@@ -813,6 +816,7 @@ VCP_VMOD_dir(struct vcp *vcp, const char *str)
CHECK_OBJ_NOTNULL(vcp, VCP_MAGIC);
REPLACE(vcp->vmod_dir, str);
+ VFIL_setpath(&vcp->vmod_path, str);
}
/*--------------------------------------------------------------------
diff --git a/lib/libvcc/vcc_compile.h b/lib/libvcc/vcc_compile.h
index 72ff7b7..3feecd3 100644
--- a/lib/libvcc/vcc_compile.h
+++ b/lib/libvcc/vcc_compile.h
@@ -161,7 +161,9 @@ struct vcp {
char *builtin_vcl;
char *vcl_dir;
+ struct vfil_path *vcl_path;
char *vmod_dir;
+ struct vfil_path *vmod_path;
unsigned err_unref;
unsigned allow_inline_c;
unsigned unsafe_path;
diff --git a/lib/libvcc/vcc_vmod.c b/lib/libvcc/vcc_vmod.c
index d82ad3e..0a165c7 100644
--- a/lib/libvcc/vcc_vmod.c
+++ b/lib/libvcc/vcc_vmod.c
@@ -30,20 +30,39 @@
#include <dlfcn.h>
#include <stdio.h>
+#include <stdlib.h>
#include <string.h>
#include "vcc_compile.h"
#include "vcs_version.h"
+#include "vfil.h"
#include "vmod_abi.h"
#include "vrt.h"
+static int
+vcc_path_dlopen(void *priv, const char *fn)
+{
+ void *hdl, **pp;
+
+ AN(priv);
+ AN(fn);
+
+fprintf(stderr, "TRY <%s>\n", fn);
+ hdl = dlopen(fn, RTLD_NOW | RTLD_LOCAL);
+ if (hdl == NULL)
+ return (1);
+ pp = priv;
+ *pp = hdl;
+ return (0);
+}
+
void
vcc_ParseImport(struct vcc *tl)
{
void *hdl;
- char fn[1024];
+ char fn[1024], *fnp;
char buf[256];
struct token *mod, *t1;
struct inifin *ifp;
@@ -85,32 +104,33 @@ vcc_ParseImport(struct vcc *tl)
sym->def_e = tl->t;
if (tl->t->tok == ID) {
- if (!tl->param->unsafe_path) {
- VSB_printf(tl->sb,
- "'import ... from path ...' not allowed.\nAt:");
- vcc_ErrToken(tl, tl->t);
- vcc_ErrWhere(tl, tl->t);
- return;
- }
if (!vcc_IdIs(tl->t, "from")) {
VSB_printf(tl->sb, "Expected 'from path ...'\n");
vcc_ErrWhere(tl, tl->t);
return;
}
vcc_NextToken(tl);
+ if (!tl->param->unsafe_path && strchr(tl->t->dec, '/')) {
+ VSB_printf(tl->sb,
+ "'import ... from path ...' is unsafe.\nAt:");
+ vcc_ErrToken(tl, tl->t);
+ vcc_ErrWhere(tl, tl->t);
+ return;
+ }
ExpectErr(tl, CSTR);
bprintf(fn, "%s", tl->t->dec);
vcc_NextToken(tl);
} else {
- bprintf(fn, "%s/libvmod_%.*s.so", tl->param->vmod_dir, PF(mod));
+ bprintf(fn, "libvmod_%.*s.so", PF(mod));
}
SkipToken(tl, ';');
- hdl = dlopen(fn, RTLD_NOW | RTLD_LOCAL);
- if (hdl == NULL) {
+ fnp = fn;
+ if (VFIL_searchpath(tl->param->vmod_path,
+ vcc_path_dlopen, &hdl, &fnp)) {
VSB_printf(tl->sb, "Could not load VMOD %.*s\n", PF(mod));
- VSB_printf(tl->sb, "\tFile name: %s\n", fn);
+ VSB_printf(tl->sb, "\tFile name: %s\n", fnp != NULL ? fnp : fn);
VSB_printf(tl->sb, "\tdlerror: %s\n", dlerror());
vcc_ErrWhere(tl, mod);
return;
@@ -120,7 +140,7 @@ vcc_ParseImport(struct vcc *tl)
vmd = dlsym(hdl, buf);
if (vmd == NULL) {
VSB_printf(tl->sb, "Malformed VMOD %.*s\n", PF(mod));
- VSB_printf(tl->sb, "\tFile name: %s\n", fn);
+ VSB_printf(tl->sb, "\tFile name: %s\n", fnp);
VSB_printf(tl->sb, "\t(no Vmod_Data symbol)\n");
vcc_ErrWhere(tl, mod);
return;
@@ -128,7 +148,7 @@ vcc_ParseImport(struct vcc *tl)
if (strcmp(VCS_Branch, "master") == 0 &&
strcmp(vmd->abi, VMOD_ABI_Version) != 0) {
VSB_printf(tl->sb, "Incompatible VMOD %.*s\n", PF(mod));
- VSB_printf(tl->sb, "\tFile name: %s\n", fn);
+ VSB_printf(tl->sb, "\tFile name: %s\n", fnp);
VSB_printf(tl->sb, "\tABI mismatch, expected <%s>, got <%s>\n",
VMOD_ABI_Version, vmd->abi);
vcc_ErrWhere(tl, mod);
@@ -137,7 +157,7 @@ vcc_ParseImport(struct vcc *tl)
if (vmd->vrt_major != VRT_MAJOR_VERSION ||
vmd->vrt_minor > VRT_MINOR_VERSION) {
VSB_printf(tl->sb, "Incompatible VMOD %.*s\n", PF(mod));
- VSB_printf(tl->sb, "\tFile name: %s\n", fn);
+ VSB_printf(tl->sb, "\tFile name: %s\n", fnp);
VSB_printf(tl->sb, "\tVMOD version %u.%u\n",
vmd->vrt_major, vmd->vrt_minor);
VSB_printf(tl->sb, "\tvarnishd version %u.%u\n",
@@ -151,7 +171,7 @@ vcc_ParseImport(struct vcc *tl)
vmd->proto == NULL ||
vmd->abi == NULL) {
VSB_printf(tl->sb, "Mangled VMOD %.*s\n", PF(mod));
- VSB_printf(tl->sb, "\tFile name: %s\n", fn);
+ VSB_printf(tl->sb, "\tFile name: %s\n", fnp);
VSB_printf(tl->sb, "\tInconsistent metadata\n");
vcc_ErrWhere(tl, mod);
return;
@@ -159,7 +179,7 @@ vcc_ParseImport(struct vcc *tl)
if (!vcc_IdIs(mod, vmd->name)) {
VSB_printf(tl->sb, "Wrong VMOD file %.*s\n", PF(mod));
- VSB_printf(tl->sb, "\tFile name: %s\n", fn);
+ VSB_printf(tl->sb, "\tFile name: %s\n", fnp);
VSB_printf(tl->sb, "\tContains vmod \"%s\"\n", vmd->name);
vcc_ErrWhere(tl, mod);
return;
@@ -172,7 +192,8 @@ vcc_ParseImport(struct vcc *tl)
VSB_printf(ifp->ini, "\t sizeof(Vmod_%.*s_Func),\n", PF(mod));
VSB_printf(ifp->ini, "\t \"%.*s\",\n", PF(mod));
VSB_printf(ifp->ini, "\t ");
- EncString(ifp->ini, fn, NULL, 0);
+ EncString(ifp->ini, fnp, NULL, 0);
+ free(fnp);
VSB_printf(ifp->ini, ",\n");
AN(vmd);
AN(vmd->file_id);
More information about the varnish-commit
mailing list