提交 459f071c 编写于 作者: M Michal Privoznik

virpcimock: Mock __open_2()

Hold on to your hat, this is going to be a wild ride. As nearly
nothing in glibc, nor open() is a real function. Just look into
bits/fcntl2.h and you'll see that open() is actually a thin
wrapper that calls either __open_alias() or __open_2(). Now,
before 801ebb5e the open() done in
virPCIDeviceConfigOpenInternal() had a constant oflags (we were
opening the pci config with O_RDWR). And since we were not
passing any mode nor O_CREAT the wrapper decided to call
__open_alias() which was open() provided by our mock. So far so
good. But after the referenced commit, the oflags is no longer
compile time constant and therefore the wrapper calls __open_2()
which we don't mock and thus the real __open_2() from glibc was
called and thus we did try to open real path from host's /sys.
This of course fails with variety of errors.
Signed-off-by: NMichal Privoznik <mprivozn@redhat.com>
Reviewed-by: NErik Skultety <eskultet@redhat.com>
Reviewed-by: NJán Tomko <jtomko@redhat.com>
上级 301eb18b
...@@ -32,6 +32,7 @@ ...@@ -32,6 +32,7 @@
static int (*real_access)(const char *path, int mode); static int (*real_access)(const char *path, int mode);
static int (*real_open)(const char *path, int flags, ...); static int (*real_open)(const char *path, int flags, ...);
static int (*real___open_2)(const char *path, int flags);
static int (*real_close)(int fd); static int (*real_close)(int fd);
static DIR * (*real_opendir)(const char *name); static DIR * (*real_opendir)(const char *name);
static char *(*real_virFileCanonicalizePath)(const char *path); static char *(*real_virFileCanonicalizePath)(const char *path);
...@@ -805,6 +806,7 @@ init_syms(void) ...@@ -805,6 +806,7 @@ init_syms(void)
VIR_MOCK_REAL_INIT(access); VIR_MOCK_REAL_INIT(access);
VIR_MOCK_REAL_INIT(open); VIR_MOCK_REAL_INIT(open);
VIR_MOCK_REAL_INIT(__open_2);
VIR_MOCK_REAL_INIT(close); VIR_MOCK_REAL_INIT(close);
VIR_MOCK_REAL_INIT(opendir); VIR_MOCK_REAL_INIT(opendir);
VIR_MOCK_REAL_INIT(virFileCanonicalizePath); VIR_MOCK_REAL_INIT(virFileCanonicalizePath);
...@@ -932,6 +934,33 @@ open(const char *path, int flags, ...) ...@@ -932,6 +934,33 @@ open(const char *path, int flags, ...)
return ret; return ret;
} }
int
__open_2(const char *path, int flags)
{
VIR_AUTOFREE(char *) newpath = NULL;
int ret;
init_syms();
if (STRPREFIX(path, SYSFS_PCI_PREFIX) &&
getrealpath(&newpath, path) < 0)
return -1;
ret = real___open_2(newpath ? newpath : path, flags);
/* Catch both: /sys/bus/pci/drivers/... and
* /sys/bus/pci/device/.../driver/... */
if (ret >= 0 && STRPREFIX(path, SYSFS_PCI_PREFIX) &&
strstr(path, "driver") && add_fd(ret, path) < 0) {
real_close(ret);
ret = -1;
}
return ret;
}
DIR * DIR *
opendir(const char *path) opendir(const char *path)
{ {
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册