using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Text;
using System.Xml;
using System.Net;
using System.IO;
namespace Intel.Management.Wsman
{
class ManagedReference : IManagedReference
{
private WsmanConnection _conn;
private XmlDocument _document;
private XmlNamespaceManager _ns;
public ManagedReference(WsmanConnection conn, string resourceUri)
{
_conn = conn;
_document = new XmlDocument();
bool isExisting = false;
if (resourceUri.StartsWith("<"))
{
isExisting = true;
_document.LoadXml(resourceUri);
}
else if (resourceUri.ToLower().StartsWith("select * from "))
{
IManagedReference objRef = conn.GetReferenceFromSQL(resourceUri);
_document.LoadXml(objRef.Xml);
}
else if (resourceUri.IndexOf("/") > 0)
{
_document.LoadXml(string.Format(WsmanResources.EPR_XML, resourceUri));
}
else
{
string name = resourceUri;
int pos = name.IndexOf('_');
if (pos > 0)
name = _conn.ResolveNamespace(name.Substring(0, pos));
else if (name.Equals("*"))
name = _conn.ResolveNamespace("*");
if (name != null)
{
if (pos > 0)
name = name + resourceUri;
}
else
{
throw new
IndexOutOfRangeException(
string.Format(WsmanResources.NS_NOT_FOUND,
resourceUri));
}
_document.LoadXml(string.Format(WsmanResources.EPR_XML, name));
// assign the addreess
if (!isExisting)
{
LoadNamespaces();
if (_document.DocumentElement != null)
{
XmlNode node = _document.DocumentElement.SelectSingleNode("wsa:Address", _ns);
if (node != null)
node.InnerText = _conn.Address;
}
}
if (name.Equals(string.Empty))
{
LoadNamespaces();
//XmlNode node = _document.DocumentElement.SelectSingleNode("wsa:ReferenceParameters", _ns);
//XmlNode node = _document.DocumentElement.SelectSingleNode("wsa:ReferenceParameters/wsman:SelectorSet", _ns);
//node.ParentNode.RemoveChild(node);
}
}
}
public ManagedReference(WsmanConnection conn, XmlDocument document)
{
_conn = conn;
_document = document;
_ns = null;
}
public string Xml
{
get
{
return _document.InnerXml;
}
set
{
_document.LoadXml(value);
}
}
public string ResourceUri
{
get
{
LoadNamespaces();
if (_document.DocumentElement != null)
{
XmlNode node = _document.DocumentElement.SelectSingleNode("wsa:ReferenceParameters/wsman:ResourceURI", _ns);
if (node != null)
return node.InnerText;
}
return string.Empty;
}
}
public string SimpleName
{
get
{
string result = ResourceUri;
if(result != null)
{
int pos = result.LastIndexOf("/");
if (pos > 0)
result = result.Substring(pos+1);
}
return result;
}
}
public string Address
{
get
{
LoadNamespaces();
if (_document.DocumentElement != null)
{
XmlNode node = _document.DocumentElement.SelectSingleNode("wsa:Address", _ns);
if (node != null)
return node.InnerText;
}
return string.Empty;
}
}
public IWsmanConnection Connection
{
get
{
return _conn;
}
}
public void AddSelector(string name, object value)
{
LoadNamespaces();
XmlNode refNode = _document.DocumentElement.SelectSingleNode("wsa:ReferenceParameters", _ns);
XmlNode setNode = null;
XmlNode uriNode = null;
if (refNode!=null)
{
setNode = refNode.SelectSingleNode("wsman:SelectorSet",_ns);
uriNode = refNode.SelectSingleNode("wsman:ResourceURI", _ns);
}
if (setNode==null && refNode!=null && uriNode!=null)
{
setNode = _document.CreateElement(uriNode.Prefix,"SelectorSet",uriNode.NamespaceURI);
refNode.AppendChild(setNode);
}
if (setNode!=null)
{
XmlElement elt = _document.CreateElement(setNode.Prefix, "Selector", setNode.NamespaceURI);
setNode.AppendChild(elt);
elt.SetAttribute("Name", name);
if (value is IManagedReference)
elt.InnerXml = ((IManagedReference)value).Xml;
else if (value is string)
elt.InnerText = value.ToString();
}
}
public IManagedInstance CreateMethodInput(string methodName)
{
return new ManagedInstance(_conn,
string.Format(WsmanResources.INPUT_INSTANCE,
methodName,ResourceUri));
}
public IManagedInstance Get()
{
IManagedInstance instance = null;
try
{
instance = (IManagedInstance)_conn.SubmitRequest(WsmanResources.GET_XML, this,null);
}
catch (Exception e)
{
// In AMT version latest then 5.0 if there is no instance- the machine throw an exception- so we catch it and return null.
if(e.Message.Contains("No route can be determined to reach the destination role defined by the WSAddressing To"))
instance = null;
else
throw;
}
return instance;
}
public IManagedInstance Put(object inputObj)
{
IManagedInstance input = (IManagedInstance)inputObj;
return (IManagedInstance)_conn.SubmitRequest(WsmanResources.PUT_XML, this,input);
}
public void Delete()
{
_conn.SubmitRequest(WsmanResources.DELETE_XML, this, null);
}
public IWsmanEnumeration Enumerate()
{
return Enumerate(string.Empty, string.Empty);
}
public IWsmanEnumeration Enumerate(object input, string mode)
{
StringBuilder builder = new StringBuilder();
if (input != null && input is ManagedInstance)
{
builder.Append("");
builder.Append(((ManagedInstance)input).Xml);
builder.Append("");
}
else if (input != null && input is string && !input.Equals(string.Empty))
{
string filter = (string)input;
if (filter.ToLower().StartsWith("associators where "))
{
IManagedReference objRef = new ManagedReference(_conn, "http://schemas.dmtf.org/wbem/wscim/1/*");
BuildAssociation(filter, builder);
return objRef.Enumerate(builder, mode);
}
else if (filter.Equals("http://schemas.dmtf.org/wbem/wsman/1/wsman/SelectorFilter"))
{
LoadNamespaces();
builder.Append("");
XmlNode node = _document.DocumentElement.SelectSingleNode("wsa:ReferenceParameters/wsman:SelectorSet", _ns);
if (node!=null)
{
builder.Append(node.OuterXml);
}
builder.Append("");
}
}
else if (input is StringBuilder stringBuilder)
{
builder = stringBuilder;
}
if (mode != null && !mode.Equals(string.Empty))
{
//Modes EnumerateObjectAndEPR
//EnumerateEPR
builder.Append("");
builder.Append(mode);
builder.Append("");
}
return (IWsmanEnumeration)_conn.SubmitRequest(
string.Format(WsmanResources.ENUM_XML,string.Empty,//_conn.Options.MaxElements.ToString(),
builder.ToString()),
this,null);
}
public IManagedInstance InvokeMethod(object inputObj)
{
IManagedInstance input = (IManagedInstance)inputObj;
return (IManagedInstance)_conn.SubmitRequest(
string.Format(WsmanResources.INVOKE_XML,
input.ResourceUri + "/" + input.MethodName),
this, input);
}
public IManagedReference Subscribe(string mode, string to)
{
StringBuilder builder = new StringBuilder();
StringBuilder secBuilder = new StringBuilder();
//:@:/
if (to.Trim().TrimStart().StartsWith("<"))
{
XmlDocumentFragment frag = _document.CreateDocumentFragment();
frag.InnerXml = to;
XmlNode addrNode=frag.SelectSingleNode("Address");
XmlNode authNode = frag.SelectSingleNode("Auth");
XmlNode userNode = frag.SelectSingleNode("Username");
XmlNode passwordNode = frag.SelectSingleNode("Password");
XmlNode refNode = frag.SelectSingleNode("ReferenceParameters");
builder.Append("");
builder.Append("");
if(addrNode != null)
{
builder.Append("");
builder.Append(addrNode.InnerText);
builder.Append("");
}
if (authNode != null)
{
builder.Append("");
}
if (userNode != null && passwordNode != null)
{
_document.DocumentElement.SetAttribute("xmlns:wst",
"http://schemas.xmlsoap.org/ws/2005/02/trust");
_document.DocumentElement.SetAttribute("xmlns:wsse",
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd");
secBuilder.Append("");
secBuilder.Append("");
secBuilder.Append("");
secBuilder.Append("http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-username-token-profile-1.0#UsernameToken");
secBuilder.Append("");
secBuilder.Append("");
secBuilder.Append("");
secBuilder.Append("");
secBuilder.Append(userNode.InnerText);
secBuilder.Append("");
secBuilder.Append("");
secBuilder.Append(passwordNode.InnerText);
secBuilder.Append("");
secBuilder.Append("");
secBuilder.Append("");
secBuilder.Append("");
secBuilder.Append("");
if (authNode == null)
{
builder.Append("");
}
}
if (refNode != null)
{
StringBuilder refParam = new StringBuilder("" + refNode.InnerXml + "");
ValidateRefParms(refNode.InnerXml);
builder.Append(refParam.ToString());
}
builder.Append("");
builder.Append("");
}
else
{
builder.Append("");
builder.Append("");
builder.Append("");
builder.Append(to);
builder.Append("");
builder.Append("");
builder.Append("");
}
return (IManagedReference)_conn.SubmitRequest(
string.Format(WsmanResources.SUBSCRIBE_XML, secBuilder.ToString(),
builder.ToString()),
this, null);
}
public void Unsubscribe()
{
_conn.SubmitRequest(WsmanResources.UNSUBSCRIBE_XML, this, null);
}
public string ToString(string format)
{
LoadNamespaces();
if (format.Equals("Selectors"))
{
XmlNode setNode = _document.DocumentElement.SelectSingleNode(
"wsa:ReferenceParameters/wsman:SelectorSet", _ns);
if(setNode != null)
return setNode.InnerXml;
}
else if (format.Equals("Address"))
{
return _document.DocumentElement.InnerXml;
}
throw new FormatException();
}
public static IManagedReference GetEmbeddedRef(WsmanConnection conn, XmlNode node, XmlNamespaceManager ns)
{
IManagedReference result = null;
XmlNode addrNode = null;
XmlNode refNode = null;
XmlNode uriNode = null;
if (node.HasChildNodes &&
node.ChildNodes.Count > 1)
addrNode = node.SelectSingleNode("wsa:Address", ns);
if (addrNode != null)
refNode = node.SelectSingleNode("wsa:ReferenceParameters", ns);
if (refNode != null)
uriNode = refNode.SelectSingleNode("wsman:ResourceURI", ns);
if (addrNode != null && refNode != null && uriNode!=null )
{
XmlDocument doc = new XmlDocument();
object[] parms = {addrNode.Prefix,addrNode.NamespaceURI,
uriNode.Prefix,uriNode.NamespaceURI};
doc.LoadXml(string.Format(WsmanResources.EPR_INSTANCE, parms));
doc.DocumentElement.InnerXml = addrNode.OuterXml + refNode.OuterXml;
result = new ManagedReference(conn,
doc);
}
return result;
}
private void LoadNamespaces()
{
if (_document !=null && _ns == null)
{
_ns = new XmlNamespaceManager(_document.NameTable);
_ns.AddNamespace("wsa", WsmanResources.ADDRESSING_NS);
_ns.AddNamespace("wsman", WsmanResources.WSMAN_NS);
}
}
private void BuildAssociation(string query, StringBuilder builder)
{
XmlDocument doc = new XmlDocument();
string assocClass=null;
string resultClass=null;
string resultRole=null;
string role = null;
string objectEpr = _document.DocumentElement.InnerXml;
// remove xmlnamespaces
//look for AssocClass
int pos = query.ToLower().IndexOf("assocclass=");
query = query.Substring(pos+"assocclass=".Length);
pos = query.IndexOf(" ");
if (pos > 0)
assocClass = query.Substring(0, pos);
else
assocClass = query;
//look for ResultClass
pos = query.ToLower().IndexOf("resultclass=");
query = query.Substring(pos + "resultclass=".Length);
pos = query.IndexOf(" ");
if (pos > 0)
resultClass = query.Substring(0, pos);
else
resultClass = query;
builder.Append("");
builder.Append("");
builder.Append("");
builder.Append(objectEpr);
builder.Append("");
if (assocClass!=null)
{
builder.Append("");
builder.Append(assocClass);
builder.Append("");
}
if (resultRole != null)
{
builder.Append("");
builder.Append(role);
builder.Append("");
}
if (resultClass != null)
{
builder.Append("");
builder.Append(resultClass);
builder.Append("");
}
if (resultRole != null)
{
builder.Append("");
builder.Append(resultRole);
builder.Append("");
}
builder.Append("");
builder.Append("");
}
//Validate the reference paramters
//the reference parmeters are limited to 256 chars and supported from Intel AMT 5.1
private void ValidateRefParms(string ReferenceParameters)
{
if (ReferenceParameters.Length > 256)
throw new FormatException("The length of the reference parmeters is limited to 256 characters");
}
public override bool Equals(Object obj)
{
if (ReferenceEquals(null, obj)) return false;
if (ReferenceEquals(this, obj)) return true;
if (obj.GetType() != typeof (ManagedReference)) return false;
return Equals((ManagedReference) obj);
}
public bool Equals(ManagedReference other)
{
if (ReferenceEquals(null, other)) return false;
if (ReferenceEquals(this, other)) return true;
return Equals(other._conn, _conn) && Equals(other._document, _document);
}
public override int GetHashCode()
{
unchecked
{
int result = (_conn != null ? _conn.GetHashCode() : 0);
result = (result*397) ^ (_document != null ? _document.GetHashCode() : 0);
return result;
}
}
}
}