in XmlProfileParser/XmlProfileParser.cpp [1221:1313]
HRESULT XmlProfileParser::_ParseDistribution(IXMLDOMNode *pXmlNode, Target *pTarget)
{
HRESULT hr = S_OK;
for (auto& type : distributionTypes)
{
CComPtr<IXMLDOMNodeList> spNodeList = nullptr;
CComVariant query(type.xPath);
hr = pXmlNode->selectNodes(query.bstrVal, &spNodeList);
if (SUCCEEDED(hr))
{
long cNodes;
hr = spNodeList->get_length(&cNodes);
if (SUCCEEDED(hr) && cNodes != 0)
{
UINT64 targetBase = 0, targetSpan;
UINT32 ioBase = 0, ioSpan;
vector<DistributionRange> v;
for (int i = 0; i < cNodes; i++)
{
// target span from the element
// note that this is the same 64bit int for both distribution types,
// it is the interpretation at the time the effective is calculated
// that makes the distinction. XSD covers range validations.
CComPtr<IXMLDOMNode> spNode = nullptr;
hr = spNodeList->get_item(i, &spNode);
if (SUCCEEDED(hr))
{
BSTR bstrText;
hr = spNode->get_text(&bstrText);
if (SUCCEEDED(hr))
{
targetSpan = _wtoi64((wchar_t *)bstrText);
SysFreeString(bstrText);
}
}
if (SUCCEEDED(hr))
{
// io span from the attribute
CComPtr<IXMLDOMNamedNodeMap> spNamedNodeMap = nullptr;
CComBSTR attr("IO");
hr = spNode->get_attributes(&spNamedNodeMap);
if (SUCCEEDED(hr) && (hr != S_FALSE))
{
CComPtr<IXMLDOMNode> spAttrNode = nullptr;
HRESULT hr = spNamedNodeMap->getNamedItem(attr, &spAttrNode);
if (SUCCEEDED(hr) && (hr != S_FALSE))
{
BSTR bstrText;
hr = spAttrNode->get_text(&bstrText);
if (SUCCEEDED(hr))
{
ioSpan = _wtoi((wchar_t *)bstrText);
SysFreeString(bstrText);
}
}
}
}
if (SUCCEEDED(hr) && (hr != S_FALSE))
{
v.emplace_back(ioBase, ioSpan,
make_pair(targetBase, targetSpan));
ioBase += ioSpan;
targetBase += targetSpan;
}
// failed during parse
else
{
break;
}
//
// Note that we are aware here whether we got to 100% IO specification.
// This validation is delayed to the common path for XML/cmdline.
//
}
if (SUCCEEDED(hr) && (hr != S_FALSE))
{
pTarget->SetDistributionRange(v, type.t);
}
// if we parsed into the element, we are done (success or failure) - only one type is possible.
return hr;
}
}
}
return hr;
}