Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
openeuler
libvirt
提交
8bd1604c
L
libvirt
项目概览
openeuler
/
libvirt
通知
3
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
L
libvirt
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
提交
8bd1604c
编写于
15年前
作者:
D
Daniel P. Berrange
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
Core internal driver stub for sVirt support (Jams Morris & Dan Walsh)
上级
a8cd24b3
无相关合并请求
变更
18
隐藏空白更改
内联
并排
Showing
18 changed file
with
395 addition
and
1 deletion
+395
-1
ChangeLog
ChangeLog
+22
-0
Makefile.maint
Makefile.maint
+1
-0
docs/schemas/capability.rng
docs/schemas/capability.rng
+15
-0
docs/schemas/domain.rng
docs/schemas/domain.rng
+15
-0
include/libvirt/virterror.h
include/libvirt/virterror.h
+2
-0
po/POTFILES.in
po/POTFILES.in
+1
-0
src/Makefile.am
src/Makefile.am
+10
-1
src/capabilities.c
src/capabilities.c
+10
-0
src/capabilities.h
src/capabilities.h
+7
-0
src/domain_conf.c
src/domain_conf.c
+50
-0
src/domain_conf.h
src/domain_conf.h
+10
-0
src/libvirt_private.syms
src/libvirt_private.syms
+9
-0
src/security.c
src/security.c
+113
-0
src/security.h
src/security.h
+86
-0
src/storage_backend.c
src/storage_backend.c
+1
-0
src/virterror.c
src/virterror.c
+9
-0
src/xml.c
src/xml.c
+30
-0
src/xml.h
src/xml.h
+4
-0
未找到文件。
ChangeLog
浏览文件 @
8bd1604c
Tue Mar 3 09:40:13 GMT 2009 Daniel P. Berrange <berrange@redhat.com>
Core internal driver stub for sVirt support (Jams Morris & Dan Walsh)
* Makefile.maint: Add virSecurityReportError as a msggen
function
* docs/schemas/capability.rng: Add <secmodel> element
* docs/schemas/domain.rng: Add <seclabel> element
* include/libvirt/virterror.h, src/virterror.c: Add
VIR_FROM_SECURITY and VIR_ERR_NO_SECURITY_MODEL
* po/POTFILES.in: Add src/security.c
* src/Makefile.am: Build security driver into libvirt.so
* src/capabilities.c, src/capabilities.h: Handling of
<secmodel> element / data
* src/domain_conf.c, src/domain_conf.h: Handling of
<seclabel> element / data
* src/libvirt_private.syms: Add virXPathStringLimit and
virSecurity* methods
* src/security.c, src/security.h: Add internal driver
stub impl
* src/storage_backend.c: TODO item about seclabel
* src/xml.c, src/xml.h: Add virXPathStringLimit
Tue Mar 3 09:25:13 GMT 2009 Daniel P. Berrange <berrange@redhat.com>
Remote protocol / RPC API for sVirt support (James Morris & Dan Walsh)
...
...
This diff is collapsed.
Click to expand it.
Makefile.maint
浏览文件 @
8bd1604c
...
...
@@ -343,6 +343,7 @@ msg_gen_function += umlLog
msg_gen_function
+=
umlReportError
msg_gen_function
+=
virConfError
msg_gen_function
+=
virDomainReportError
msg_gen_function
+=
virSecurityReportError
msg_gen_function
+=
virHashError
msg_gen_function
+=
virLibConnError
msg_gen_function
+=
virLibDomainError
...
...
This diff is collapsed.
Click to expand it.
docs/schemas/capability.rng
浏览文件 @
8bd1604c
...
...
@@ -33,9 +33,24 @@
<optional>
<ref name='topology'/>
</optional>
<optional>
<ref name='secmodel'/>
</optional>
</element>
</define>
<define name='secmodel'>
<element name='secmodel'>
<element name='model'>
<text/>
</element>
<element name='doi'>
<text/>
</element>
</element>
</define>
<define name='cpufeatures'>
<element name='features'>
<optional>
...
...
This diff is collapsed.
Click to expand it.
docs/schemas/domain.rng
浏览文件 @
8bd1604c
...
...
@@ -22,10 +22,25 @@
<optional>
<ref
name=
'devices'
/>
</optional>
<optional>
<ref
name=
'seclabel'
/>
</optional>
</interleave>
</element>
</define>
<define
name=
'seclabel'
>
<element
name=
'seclabel'
>
<attribute
name=
'model'
>
<text/>
</attribute>
<element
name=
'label'
>
<text/>
</element>
</element>
</define>
<define
name=
'hvs'
>
<attribute
name=
'type'
>
<choice>
...
...
This diff is collapsed.
Click to expand it.
include/libvirt/virterror.h
浏览文件 @
8bd1604c
...
...
@@ -61,6 +61,7 @@ typedef enum {
VIR_FROM_UML
,
/* Error at the UML driver */
VIR_FROM_NODEDEV
,
/* Error from node device monitor */
VIR_FROM_XEN_INOTIFY
,
/* Error from xen inotify layer */
VIR_FROM_SECURITY
,
/* Error from security framework */
}
virErrorDomain
;
...
...
@@ -154,6 +155,7 @@ typedef enum {
VIR_WAR_NO_NODE
,
/* failed to start node driver */
VIR_ERR_INVALID_NODE_DEVICE
,
/* invalid node device object */
VIR_ERR_NO_NODE_DEVICE
,
/* node device not found */
VIR_ERR_NO_SECURITY_MODEL
,
/* security model not found */
}
virErrorNumber
;
/**
...
...
This diff is collapsed.
Click to expand it.
po/POTFILES.in
浏览文件 @
8bd1604c
...
...
@@ -23,6 +23,7 @@ src/proxy_internal.c
src/qemu_conf.c
src/qemu_driver.c
src/remote_internal.c
src/security.c
src/storage_backend.c
src/storage_backend_disk.c
src/storage_backend_fs.c
...
...
This diff is collapsed.
Click to expand it.
src/Makefile.am
浏览文件 @
8bd1604c
...
...
@@ -140,7 +140,7 @@ UML_DRIVER_SOURCES = \
NETWORK_DRIVER_SOURCES
=
\
network_driver.h network_driver.c
#
And finally s
torage backend specific impls
#
S
torage backend specific impls
STORAGE_DRIVER_SOURCES
=
\
storage_driver.h storage_driver.c
\
storage_backend.h storage_backend.c
...
...
@@ -166,6 +166,11 @@ STORAGE_HELPER_DISK_SOURCES = \
parthelper.c
# Security framework and drivers for various models
SECURITY_DRIVER_SOURCES
=
\
security.h security.c
NODE_DEVICE_DRIVER_SOURCES
=
\
node_device.c node_device.h
...
...
@@ -379,6 +384,10 @@ endif
endif
libvirt_driver_security_la_SOURCES
=
$(SECURITY_DRIVER_SOURCES)
noinst_LTLIBRARIES
+=
libvirt_driver_security.la
libvirt_la_LIBADD
+=
libvirt_driver_security.la
# Add all conditional sources just in case...
EXTRA_DIST
+=
\
$(TEST_DRIVER_SOURCES)
\
...
...
This diff is collapsed.
Click to expand it.
src/capabilities.c
浏览文件 @
8bd1604c
...
...
@@ -150,6 +150,8 @@ virCapabilitiesFree(virCapsPtr caps) {
VIR_FREE
(
caps
->
host
.
migrateTrans
);
VIR_FREE
(
caps
->
host
.
arch
);
VIR_FREE
(
caps
->
host
.
secModel
.
model
);
VIR_FREE
(
caps
->
host
.
secModel
.
doi
);
VIR_FREE
(
caps
);
}
...
...
@@ -599,6 +601,14 @@ virCapabilitiesFormatXML(virCapsPtr caps)
virBufferAddLit
(
&
xml
,
" </cells>
\n
"
);
virBufferAddLit
(
&
xml
,
" </topology>
\n
"
);
}
if
(
caps
->
host
.
secModel
.
model
)
{
virBufferAddLit
(
&
xml
,
" <secmodel>
\n
"
);
virBufferVSprintf
(
&
xml
,
" <model>%s</model>
\n
"
,
caps
->
host
.
secModel
.
model
);
virBufferVSprintf
(
&
xml
,
" <doi>%s</doi>
\n
"
,
caps
->
host
.
secModel
.
doi
);
virBufferAddLit
(
&
xml
,
" </secmodel>
\n
"
);
}
virBufferAddLit
(
&
xml
,
" </host>
\n\n
"
);
...
...
This diff is collapsed.
Click to expand it.
src/capabilities.h
浏览文件 @
8bd1604c
...
...
@@ -78,6 +78,12 @@ struct _virCapsHostNUMACell {
int
*
cpus
;
};
typedef
struct
_virCapsHostSecModel
virCapsHostSecModel
;
struct
_virCapsHostSecModel
{
char
*
model
;
char
*
doi
;
};
typedef
struct
_virCapsHost
virCapsHost
;
typedef
virCapsHost
*
virCapsHostPtr
;
struct
_virCapsHost
{
...
...
@@ -90,6 +96,7 @@ struct _virCapsHost {
char
**
migrateTrans
;
int
nnumaCell
;
virCapsHostNUMACellPtr
*
numaCell
;
virCapsHostSecModel
secModel
;
};
typedef
struct
_virCaps
virCaps
;
...
...
This diff is collapsed.
Click to expand it.
src/domain_conf.c
浏览文件 @
8bd1604c
...
...
@@ -387,6 +387,15 @@ void virDomainDeviceDefFree(virDomainDeviceDefPtr def)
VIR_FREE
(
def
);
}
void
virSecurityLabelDefFree
(
virDomainDefPtr
def
);
void
virSecurityLabelDefFree
(
virDomainDefPtr
def
)
{
VIR_FREE
(
def
->
seclabel
.
model
);
VIR_FREE
(
def
->
seclabel
.
label
);
VIR_FREE
(
def
->
seclabel
.
imagelabel
);
}
void
virDomainDefFree
(
virDomainDefPtr
def
)
{
unsigned
int
i
;
...
...
@@ -445,6 +454,8 @@ void virDomainDefFree(virDomainDefPtr def)
VIR_FREE
(
def
->
cpumask
);
VIR_FREE
(
def
->
emulator
);
virSecurityLabelDefFree
(
def
);
VIR_FREE
(
def
);
}
...
...
@@ -1833,6 +1844,34 @@ static int virDomainLifecycleParseXML(virConnectPtr conn,
return
0
;
}
static
int
virSecurityLabelDefParseXML
(
virConnectPtr
conn
,
const
virDomainDefPtr
def
,
xmlXPathContextPtr
ctxt
)
{
char
*
p
;
if
(
virXPathNode
(
conn
,
"./seclabel"
,
ctxt
)
==
NULL
)
return
0
;
p
=
virXPathStringLimit
(
conn
,
"string(./seclabel/label[1])"
,
VIR_SECURITY_LABEL_BUFLEN
-
1
,
ctxt
);
if
(
p
==
NULL
)
goto
error
;
def
->
seclabel
.
label
=
p
;
p
=
virXPathStringLimit
(
conn
,
"string(./seclabel/@model)"
,
VIR_SECURITY_MODEL_BUFLEN
-
1
,
ctxt
);
if
(
p
==
NULL
)
goto
error
;
def
->
seclabel
.
model
=
p
;
return
0
;
error:
virSecurityLabelDefFree
(
def
);
return
-
1
;
}
virDomainDeviceDefPtr
virDomainDeviceDefParse
(
virConnectPtr
conn
,
virCapsPtr
caps
,
...
...
@@ -2418,6 +2457,10 @@ static virDomainDefPtr virDomainDefParseXML(virConnectPtr conn,
}
VIR_FREE
(
nodes
);
/* analysis of security label */
if
(
virSecurityLabelDefParseXML
(
conn
,
def
,
ctxt
)
==
-
1
)
goto
error
;
return
def
;
no_memory:
...
...
@@ -3435,6 +3478,13 @@ char *virDomainDefFormat(virConnectPtr conn,
goto
cleanup
;
virBufferAddLit
(
&
buf
,
" </devices>
\n
"
);
if
(
def
->
seclabel
.
model
)
{
virBufferEscapeString
(
&
buf
,
" <seclabel model='%s'>
\n
"
,
def
->
seclabel
.
model
);
virBufferEscapeString
(
&
buf
,
" <label>%s</label>
\n
"
,
def
->
seclabel
.
label
);
virBufferAddLit
(
&
buf
,
" </seclabel>
\n
"
);
}
virBufferAddLit
(
&
buf
,
"</domain>
\n
"
);
if
(
virBufferError
(
&
buf
))
...
...
This diff is collapsed.
Click to expand it.
src/domain_conf.h
浏览文件 @
8bd1604c
...
...
@@ -410,6 +410,15 @@ struct _virDomainOSDef {
char
*
bootloaderArgs
;
};
/* Security configuration for domain */
typedef
struct
_virSecurityLabelDef
virSecurityLabelDef
;
typedef
virSecurityLabelDef
*
virSecurityLabelDefPtr
;
struct
_virSecurityLabelDef
{
char
*
model
;
/* name of security model */
char
*
label
;
/* security label string */
char
*
imagelabel
;
/* security image label string */
};
#define VIR_DOMAIN_CPUMASK_LEN 1024
/* Guest VM main configuration */
...
...
@@ -467,6 +476,7 @@ struct _virDomainDef {
/* Only 1 */
virDomainChrDefPtr
console
;
virSecurityLabelDef
seclabel
;
};
/* Guest VM runtime state */
...
...
This diff is collapsed.
Click to expand it.
src/libvirt_private.syms
浏览文件 @
8bd1604c
...
...
@@ -247,6 +247,14 @@ qparam_query_parse;
free_qparam_set;
# security.h
virSecurityDriverStartup;
virSecurityDriverInit;
virSecurityDriverSetDOI;
virSecurityDriverGetDOI;
virSecurityDriverGetModel;
# storage_conf.h
virStoragePoolDefFormat;
virStoragePoolDefFree;
...
...
@@ -351,3 +359,4 @@ virXPathNode;
virXPathNodeSet;
virXPathString;
virXMLPropString;
virXPathStringLimit;
This diff is collapsed.
Click to expand it.
src/security.c
0 → 100644
浏览文件 @
8bd1604c
/*
* Copyright (C) 2008 Red Hat, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* Authors:
* James Morris <jmorris@namei.org>
*
*/
#include <config.h>
#include <string.h>
#include "virterror_internal.h"
#include "security.h"
static
virSecurityDriverPtr
security_drivers
[]
=
{
NULL
};
int
virSecurityDriverStartup
(
virSecurityDriverPtr
*
drv
,
const
char
*
name
)
{
unsigned
int
i
;
if
(
name
&&
STREQ
(
name
,
"none"
))
return
-
2
;
for
(
i
=
0
;
security_drivers
[
i
]
!=
NULL
;
i
++
)
{
virSecurityDriverPtr
tmp
=
security_drivers
[
i
];
if
(
name
&&
STRNEQ
(
tmp
->
name
,
name
))
continue
;
switch
(
tmp
->
probe
())
{
case
SECURITY_DRIVER_ENABLE
:
virSecurityDriverInit
(
tmp
);
if
(
tmp
->
open
(
NULL
,
tmp
)
==
-
1
)
{
return
-
1
;
}
else
{
*
drv
=
tmp
;
return
0
;
}
break
;
case
SECURITY_DRIVER_DISABLE
:
break
;
default:
return
-
1
;
}
}
return
-
2
;
}
void
virSecurityReportError
(
virConnectPtr
conn
,
int
code
,
const
char
*
fmt
,
...)
{
va_list
args
;
char
errorMessage
[
1024
];
if
(
fmt
)
{
va_start
(
args
,
fmt
);
vsnprintf
(
errorMessage
,
sizeof
(
errorMessage
)
-
1
,
fmt
,
args
);
va_end
(
args
);
}
else
errorMessage
[
0
]
=
'\0'
;
virRaiseError
(
conn
,
NULL
,
NULL
,
VIR_FROM_SECURITY
,
code
,
VIR_ERR_ERROR
,
NULL
,
NULL
,
NULL
,
-
1
,
-
1
,
"%s"
,
errorMessage
);
}
/*
* Helpers
*/
void
virSecurityDriverInit
(
virSecurityDriverPtr
drv
)
{
memset
(
&
drv
->
_private
,
0
,
sizeof
drv
->
_private
);
}
int
virSecurityDriverSetDOI
(
virConnectPtr
conn
,
virSecurityDriverPtr
drv
,
const
char
*
doi
)
{
if
(
strlen
(
doi
)
>=
VIR_SECURITY_DOI_BUFLEN
)
{
virSecurityReportError
(
conn
,
VIR_ERR_ERROR
,
_
(
"%s: DOI
\'
%s
\'
is "
"longer than the maximum allowed length of %d"
),
__func__
,
doi
,
VIR_SECURITY_DOI_BUFLEN
-
1
);
return
-
1
;
}
strcpy
(
drv
->
_private
.
doi
,
doi
);
return
0
;
}
const
char
*
virSecurityDriverGetDOI
(
virSecurityDriverPtr
drv
)
{
return
drv
->
_private
.
doi
;
}
const
char
*
virSecurityDriverGetModel
(
virSecurityDriverPtr
drv
)
{
return
drv
->
name
;
}
This diff is collapsed.
Click to expand it.
src/security.h
0 → 100644
浏览文件 @
8bd1604c
/*
* Copyright (C) 2008 Red Hat, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* Authors:
* James Morris <jmorris@namei.org>
*
*/
#ifndef __VIR_SECURITY_H__
#define __VIR_SECURITY_H__
#include "internal.h"
#include "domain_conf.h"
/*
* Return values for security driver probing: the driver will determine
* whether it should be enabled or disabled.
*/
typedef
enum
{
SECURITY_DRIVER_ENABLE
=
0
,
SECURITY_DRIVER_ERROR
=
-
1
,
SECURITY_DRIVER_DISABLE
=
-
2
,
}
virSecurityDriverStatus
;
typedef
struct
_virSecurityDriver
virSecurityDriver
;
typedef
virSecurityDriver
*
virSecurityDriverPtr
;
typedef
virSecurityDriverStatus
(
*
virSecurityDriverProbe
)
(
void
);
typedef
int
(
*
virSecurityDriverOpen
)
(
virConnectPtr
conn
,
virSecurityDriverPtr
drv
);
typedef
int
(
*
virSecurityDomainRestoreImageLabel
)
(
virConnectPtr
conn
,
virDomainObjPtr
vm
,
virDomainDeviceDefPtr
dev
);
typedef
int
(
*
virSecurityDomainSetImageLabel
)
(
virConnectPtr
conn
,
virDomainObjPtr
vm
,
virDomainDeviceDefPtr
dev
);
typedef
int
(
*
virSecurityDomainGenLabel
)
(
virDomainObjPtr
sec
);
typedef
int
(
*
virSecurityDomainGetLabel
)
(
virConnectPtr
conn
,
virDomainObjPtr
vm
,
virSecurityLabelPtr
sec
);
typedef
int
(
*
virSecurityDomainRestoreLabel
)
(
virConnectPtr
conn
,
virDomainObjPtr
vm
);
typedef
int
(
*
virSecurityDomainSetLabel
)
(
virConnectPtr
conn
,
virSecurityDriverPtr
drv
,
virDomainObjPtr
vm
);
struct
_virSecurityDriver
{
const
char
*
name
;
virSecurityDriverProbe
probe
;
virSecurityDriverOpen
open
;
virSecurityDomainRestoreImageLabel
domainRestoreSecurityImageLabel
;
virSecurityDomainSetImageLabel
domainSetSecurityImageLabel
;
virSecurityDomainGenLabel
domainGenSecurityLabel
;
virSecurityDomainGetLabel
domainGetSecurityLabel
;
virSecurityDomainSetLabel
domainSetSecurityLabel
;
virSecurityDomainRestoreLabel
domainRestoreSecurityLabel
;
/*
* This is internally managed driver state and should only be accessed
* via helpers below.
*/
struct
{
char
doi
[
VIR_SECURITY_DOI_BUFLEN
];
}
_private
;
};
/* Global methods */
int
virSecurityDriverStartup
(
virSecurityDriverPtr
*
drv
,
const
char
*
name
);
void
virSecurityReportError
(
virConnectPtr
conn
,
int
code
,
const
char
*
fmt
,
...)
ATTRIBUTE_FORMAT
(
printf
,
3
,
4
);
/* Helpers */
void
virSecurityDriverInit
(
virSecurityDriverPtr
drv
);
int
virSecurityDriverSetDOI
(
virConnectPtr
conn
,
virSecurityDriverPtr
drv
,
const
char
*
doi
);
const
char
*
virSecurityDriverGetDOI
(
virSecurityDriverPtr
drv
);
const
char
*
virSecurityDriverGetModel
(
virSecurityDriverPtr
drv
);
#endif
/* __VIR_SECURITY_H__ */
This diff is collapsed.
Click to expand it.
src/storage_backend.c
浏览文件 @
8bd1604c
...
...
@@ -276,6 +276,7 @@ virStorageBackendUpdateVolTargetInfoFD(virConnectPtr conn,
VIR_FREE
(
target
->
perms
.
label
);
#if HAVE_SELINUX
/* XXX: make this a security driver call */
if
(
fgetfilecon
(
fd
,
&
filecon
)
==
-
1
)
{
if
(
errno
!=
ENODATA
&&
errno
!=
ENOTSUP
)
{
virReportSystemError
(
conn
,
errno
,
...
...
This diff is collapsed.
Click to expand it.
src/virterror.c
浏览文件 @
8bd1604c
...
...
@@ -151,6 +151,9 @@ static const char *virErrorDomainName(virErrorDomain domain) {
case
VIR_FROM_UML
:
dom
=
"UML "
;
break
;
case
VIR_FROM_SECURITY
:
dom
=
"Security Labeling "
;
break
;
}
return
(
dom
);
}
...
...
@@ -995,6 +998,12 @@ virErrorMsg(virErrorNumber error, const char *info)
else
errmsg
=
_
(
"Node device not found: %s"
);
break
;
case
VIR_ERR_NO_SECURITY_MODEL
:
if
(
info
==
NULL
)
errmsg
=
_
(
"Security model not found"
);
else
errmsg
=
_
(
"Security model not found: %s"
);
break
;
}
return
(
errmsg
);
}
...
...
This diff is collapsed.
Click to expand it.
src/xml.c
浏览文件 @
8bd1604c
...
...
@@ -76,6 +76,36 @@ virXPathString(virConnectPtr conn,
return
(
ret
);
}
/**
* virXPathStringLimit:
* @xpath: the XPath string to evaluate
* @maxlen: maximum length permittred string
* @ctxt: an XPath context
*
* Wrapper for virXPathString, which validates the length of the returned
* string.
*
* Returns a new string which must be deallocated by the caller or NULL if
* the evaluation failed.
*/
char
*
virXPathStringLimit
(
virConnectPtr
conn
,
const
char
*
xpath
,
size_t
maxlen
,
xmlXPathContextPtr
ctxt
)
{
char
*
tmp
=
virXPathString
(
conn
,
xpath
,
ctxt
);
if
(
tmp
!=
NULL
&&
strlen
(
tmp
)
>=
maxlen
)
{
virXMLError
(
conn
,
VIR_ERR_INTERNAL_ERROR
,
_
(
"
\'
%s
\'
value longer than %Zd bytes in virXPathStringLimit()"
),
xpath
,
maxlen
);
return
NULL
;
}
return
tmp
;
}
/**
* virXPathNumber:
* @xpath: the XPath string to evaluate
...
...
This diff is collapsed.
Click to expand it.
src/xml.h
浏览文件 @
8bd1604c
...
...
@@ -17,6 +17,10 @@ int virXPathBoolean (virConnectPtr conn,
char
*
virXPathString
(
virConnectPtr
conn
,
const
char
*
xpath
,
xmlXPathContextPtr
ctxt
);
char
*
virXPathStringLimit
(
virConnectPtr
conn
,
const
char
*
xpath
,
size_t
maxlen
,
xmlXPathContextPtr
ctxt
);
int
virXPathNumber
(
virConnectPtr
conn
,
const
char
*
xpath
,
xmlXPathContextPtr
ctxt
,
...
...
This diff is collapsed.
Click to expand it.
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录
反馈
建议
客服
返回
顶部