esx: Make esxVI_*_Deserialize dynamically dispatched

This will be used to deserialize the response from a call
to esxVI_SearchDatastore_Task properly.
This commit is contained in:
Matthias Bolte 2010-07-06 17:27:05 +02:00
parent 9af989fabc
commit 8aa08ea873
2 changed files with 115 additions and 12 deletions

View File

@ -469,18 +469,21 @@ class Object:
return source
def generate_dynamic_cast_code(self):
def generate_dynamic_cast_code(self, is_first = True):
global objects_by_name
source = ""
if self.extended_by is not None:
if not is_first:
source += "\n"
source += " /* %s */\n" % self.name
for extended_by in self.extended_by:
source += " ESX_VI__TEMPLATE__DYNAMIC_CAST__ACCEPT(%s)\n" % extended_by
for extended_by in self.extended_by:
source += objects_by_name[extended_by].generate_dynamic_cast_code()
source += objects_by_name[extended_by].generate_dynamic_cast_code(False)
return source
@ -820,18 +823,38 @@ class Object:
source += "ESX_VI__TEMPLATE__LIST__SERIALIZE(%s)\n\n" % self.name
# deserilaize
if self.features & Object.FEATURE__DESERIALIZE:
source += "/* esxVI_%s_Deserialize */\n" % self.name
source += "ESX_VI__TEMPLATE__DESERIALIZE(%s,\n" % self.name
source += "{\n"
if self.extended_by is None:
if self.features & Object.FEATURE__DESERIALIZE:
source += "/* esxVI_%s_Deserialize */\n" % self.name
source += "ESX_VI__TEMPLATE__DESERIALIZE(%s,\n" % self.name
source += "{\n"
source += self.generate_deserialize_code()
source += self.generate_deserialize_code()
source += "})\n\n"
source += "})\n\n"
if self.features & Object.FEATURE__LIST:
source += "/* esxVI_%s_DeserializeList */\n" % self.name
source += "ESX_VI__TEMPLATE__LIST__DESERIALIZE(%s)\n\n" % self.name
if self.features & Object.FEATURE__LIST:
source += "/* esxVI_%s_DeserializeList */\n" % self.name
source += "ESX_VI__TEMPLATE__LIST__DESERIALIZE(%s)\n\n" % self.name
else:
if self.features & Object.FEATURE__DESERIALIZE:
source += "/* esxVI_%s_Deserialize */\n" % self.name
source += "ESX_VI__TEMPLATE__DYNAMIC_DESERIALIZE(%s,\n" % self.name
source += "{\n"
for extended_by in self.extended_by:
source += " ESX_VI__TEMPLATE__DISPATCH__DESERIALIZE(%s)\n" % extended_by
source += "},\n"
source += "{\n"
source += self.generate_deserialize_code()
source += "})\n\n"
if self.features & Object.FEATURE__LIST:
source += "/* esxVI_%s_DeserializeList */\n" % self.name
source += "ESX_VI__TEMPLATE__LIST__DESERIALIZE(%s)\n\n" % self.name
source += "\n\n"

View File

@ -250,12 +250,14 @@
#define ESX_VI__TEMPLATE__DESERIALIZE(_type, _deserialize) \
#define ESX_VI__TEMPLATE__DESERIALIZE_EXTRA(_type, _extra, _deserialize) \
int \
esxVI_##_type##_Deserialize(xmlNodePtr node, esxVI_##_type **ptrptr) \
{ \
xmlNodePtr childNode = NULL; \
\
_extra \
\
if (ptrptr == NULL || *ptrptr != NULL) { \
ESX_VI_ERROR(VIR_ERR_INTERNAL_ERROR, "%s", \
_("Invalid argument")); \
@ -293,6 +295,11 @@
#define ESX_VI__TEMPLATE__DESERIALIZE(_type, _deserialize) \
ESX_VI__TEMPLATE__DESERIALIZE_EXTRA(_type, /* nothing */, _deserialize)
#define ESX_VI__TEMPLATE__DESERIALIZE_NUMBER(_type, _xsdType, _min, _max) \
int \
esxVI_##_type##_Deserialize(xmlNodePtr node, esxVI_##_type **number) \
@ -544,6 +551,12 @@
#define ESX_VI__TEMPLATE__DISPATCH__DESERIALIZE(_type) \
case esxVI_Type_##_type: \
return esxVI_##_type##_Deserialize(node, (esxVI_##_type **)ptrptr);
#define ESX_VI__TEMPLATE__DYNAMIC_FREE(__type, _dispatch, _body) \
ESX_VI__TEMPLATE__FREE(__type, \
ESX_VI__TEMPLATE__DISPATCH(__type, _dispatch, /* nothing */) \
@ -584,6 +597,73 @@
#define ESX_VI__TEMPLATE__DYNAMIC_DESERIALIZE(__type, _dispatch, \
_deserialize) \
ESX_VI__TEMPLATE__DESERIALIZE_EXTRA(__type, \
esxVI_Type type = esxVI_Type_Undefined; \
\
if (esxVI_GetActualObjectType(node, esxVI_Type_##__type, &type) < 0) { \
return -1; \
} \
\
switch (type) { \
_dispatch \
\
case esxVI_Type_##__type: \
break; \
\
default: \
ESX_VI_ERROR(VIR_ERR_INTERNAL_ERROR, \
_("Call to %s for unexpected type '%s'"), \
__FUNCTION__, esxVI_Type_ToString(type)); \
return -1; \
}, \
_deserialize)
static int
esxVI_GetActualObjectType(xmlNodePtr node, esxVI_Type baseType,
esxVI_Type *actualType)
{
int result = -1;
char *type = NULL;
if (actualType == NULL || *actualType != esxVI_Type_Undefined) {
ESX_VI_ERROR(VIR_ERR_INTERNAL_ERROR, "%s", _("Invalid argument"));
return -1;
}
type = (char *)xmlGetNsProp
(node, BAD_CAST "type",
BAD_CAST "http://www.w3.org/2001/XMLSchema-instance");
if (type == NULL) {
ESX_VI_ERROR(VIR_ERR_INTERNAL_ERROR,
_("%s is missing 'type' property"),
esxVI_Type_ToString(baseType));
return -1;
}
*actualType = esxVI_Type_FromString(type);
if (*actualType == esxVI_Type_Undefined) {
ESX_VI_ERROR(VIR_ERR_INTERNAL_ERROR,
_("Unknown value '%s' for %s 'type' property"),
type, esxVI_Type_ToString(baseType));
goto cleanup;
}
result = 0;
cleanup:
VIR_FREE(type);
return result;
}
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
* XSI: Type
*/