1/* 2 * Copyright (c) 2011-2014, Intel Corporation 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without modification, 6 * are permitted provided that the following conditions are met: 7 * 8 * 1. Redistributions of source code must retain the above copyright notice, this 9 * list of conditions and the following disclaimer. 10 * 11 * 2. Redistributions in binary form must reproduce the above copyright notice, 12 * this list of conditions and the following disclaimer in the documentation and/or 13 * other materials provided with the distribution. 14 * 15 * 3. Neither the name of the copyright holder nor the names of its contributors 16 * may be used to endorse or promote products derived from this software without 17 * specific prior written permission. 18 * 19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 20 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 21 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 22 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR 23 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 24 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 25 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON 26 * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 28 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 29 */ 30#include "SelectionCriterionRule.h" 31#include "SelectionCriterion.h" 32#include "XmlDomainSerializingContext.h" 33#include "XmlDomainImportContext.h" 34#include "SelectionCriteriaDefinition.h" 35#include "SelectionCriterionTypeInterface.h" 36#include "RuleParser.h" 37#include <assert.h> 38 39#define base CRule 40 41using std::string; 42 43const CSelectionCriterionRule::SMatchingRuleDescription CSelectionCriterionRule::_astMatchesWhen[CSelectionCriterionRule::ENbMatchesWhen] = { 44 { "Is", true }, 45 { "IsNot", true }, 46 { "Includes", false }, 47 { "Excludes", false } 48}; 49 50CSelectionCriterionRule::CSelectionCriterionRule() : _pSelectionCriterion(NULL), _eMatchesWhen(CSelectionCriterionRule::EIs), _iMatchValue(0) 51{ 52} 53 54// Class kind 55string CSelectionCriterionRule::getKind() const 56{ 57 return "SelectionCriterionRule"; 58} 59 60// Content dumping 61void CSelectionCriterionRule::logValue(string& strValue, CErrorContext& errorContext) const 62{ 63 (void)errorContext; 64 65 // Dump rule 66 dump(strValue); 67} 68 69// Parse 70bool CSelectionCriterionRule::parse(CRuleParser& ruleParser, string& strError) 71{ 72 // Criterion 73 _pSelectionCriterion = ruleParser.getSelectionCriteriaDefinition()->getSelectionCriterion(ruleParser.getType()); 74 75 // Check existence 76 if (!_pSelectionCriterion) { 77 78 strError = "Couldn't find selection criterion " + ruleParser.getType(); 79 80 return false; 81 } 82 83 // Verb 84 string strMatchesWhen; 85 86 if (!ruleParser.next(strMatchesWhen, strError)) { 87 88 return false; 89 } 90 // Value 91 string strValue; 92 93 if (!ruleParser.next(strValue, strError)) { 94 95 return false; 96 } 97 98 // Matches when 99 if (!setMatchesWhen(strMatchesWhen, strError)) { 100 101 strError = "Verb error: " + strError; 102 103 return false; 104 } 105 106 // Value 107 if (!_pSelectionCriterion->getCriterionType()->getNumericalValue(strValue, _iMatchValue)) { 108 109 strError = "Value error: \"" + strValue + "\" is not part of criterion \"" + 110 _pSelectionCriterion->getCriterionName() + "\""; 111 112 return false; 113 } 114 115 return true; 116} 117 118// Dump 119void CSelectionCriterionRule::dump(string& strResult) const 120{ 121 // Criterion 122 strResult += _pSelectionCriterion->getName(); 123 strResult += " "; 124 // Verb 125 strResult += _astMatchesWhen[_eMatchesWhen].pcMatchesWhen; 126 strResult += " "; 127 // Value 128 string strValue; 129 _pSelectionCriterion->getCriterionType()->getLiteralValue(_iMatchValue, strValue); 130 strResult += strValue; 131} 132 133// Rule check 134bool CSelectionCriterionRule::matches() const 135{ 136 assert(_pSelectionCriterion); 137 138 switch(_eMatchesWhen) { 139 case EIs: 140 return _pSelectionCriterion->is(_iMatchValue); 141 case EIsNot: 142 return _pSelectionCriterion->isNot(_iMatchValue); 143 case EIncludes: 144 return _pSelectionCriterion->includes(_iMatchValue); 145 case EExcludes: 146 return _pSelectionCriterion->excludes(_iMatchValue); 147 default: 148 assert(0); 149 return false; 150 } 151} 152 153// From IXmlSink 154bool CSelectionCriterionRule::fromXml(const CXmlElement& xmlElement, CXmlSerializingContext& serializingContext) 155{ 156 // Retrieve actual context 157 CXmlDomainImportContext& xmlDomainImportContext = static_cast<CXmlDomainImportContext&>(serializingContext); 158 159 // Get selection criterion 160 string strSelectionCriterion = xmlElement.getAttributeString("SelectionCriterion"); 161 162 _pSelectionCriterion = xmlDomainImportContext.getSelectionCriteriaDefinition()->getSelectionCriterion(strSelectionCriterion); 163 164 // Check existence 165 if (!_pSelectionCriterion) { 166 167 xmlDomainImportContext.setError("Couldn't find selection criterion " + strSelectionCriterion + " in " + getKind() + " " + xmlElement.getPath()); 168 169 return false; 170 } 171 172 // Get MatchesWhen 173 string strMatchesWhen = xmlElement.getAttributeString("MatchesWhen"); 174 string strError; 175 176 if (!setMatchesWhen(strMatchesWhen, strError)) { 177 178 xmlDomainImportContext.setError("Wrong MatchesWhen attribute " + strMatchesWhen + " in " + getKind() + " " + xmlElement.getPath() + ": " + strError); 179 180 return false; 181 } 182 183 // Get Value 184 string strValue = xmlElement.getAttributeString("Value"); 185 186 if (!_pSelectionCriterion->getCriterionType()->getNumericalValue(strValue, _iMatchValue)) { 187 188 xmlDomainImportContext.setError("Wrong Value attribute value " + strValue + " in " + getKind() + " " + xmlElement.getPath()); 189 190 return false; 191 } 192 193 // Done 194 return true; 195} 196 197// From IXmlSource 198void CSelectionCriterionRule::toXml(CXmlElement& xmlElement, CXmlSerializingContext& serializingContext) const 199{ 200 (void)serializingContext; 201 202 assert(_pSelectionCriterion); 203 204 // Set selection criterion 205 xmlElement.setAttributeString("SelectionCriterion", _pSelectionCriterion->getName()); 206 207 // Set MatchesWhen 208 xmlElement.setAttributeString("MatchesWhen", _astMatchesWhen[_eMatchesWhen].pcMatchesWhen); 209 210 // Set Value 211 string strValue; 212 213 _pSelectionCriterion->getCriterionType()->getLiteralValue(_iMatchValue, strValue); 214 215 xmlElement.setAttributeString("Value", strValue); 216} 217 218// XML MatchesWhen attribute parsing 219bool CSelectionCriterionRule::setMatchesWhen(const string& strMatchesWhen, string& strError) 220{ 221 uint32_t uiMatchesWhen; 222 223 for (uiMatchesWhen = 0; uiMatchesWhen < ENbMatchesWhen; uiMatchesWhen++) { 224 225 const SMatchingRuleDescription* pstMatchingRuleDescription = &_astMatchesWhen[uiMatchesWhen]; 226 227 if (strMatchesWhen == pstMatchingRuleDescription->pcMatchesWhen) { 228 229 // Found it! 230 231 // Get Type 232 const ISelectionCriterionTypeInterface* pSelectionCriterionType = _pSelectionCriterion->getCriterionType(); 233 234 // Check compatibility if relevant 235 if (!pSelectionCriterionType->isTypeInclusive() && !pstMatchingRuleDescription->bExclusiveTypeCompatible) { 236 237 strError = "Value incompatible with exclusive kind of type"; 238 239 return false; 240 } 241 242 // Store 243 _eMatchesWhen = (MatchesWhen)uiMatchesWhen; 244 245 return true; 246 } 247 } 248 249 strError = "Value not found"; 250 251 return false; 252} 253