blob: c9863c05d0ca3ddfc4b6d58585156fe30b8f053c [file] [log] [blame]
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +05301/*
2 * Copyright 2016-present Open Networking Laboratory
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
Gaurav Agrawal95b416c2016-06-07 14:00:26 +053017package org.onosproject.yangutils.datamodel.utils;
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +053018
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +053019import static org.onosproject.yangutils.datamodel.YangDataTypes.DECIMAL64;
20import static org.onosproject.yangutils.datamodel.YangDataTypes.INT16;
21import static org.onosproject.yangutils.datamodel.YangDataTypes.INT32;
22import static org.onosproject.yangutils.datamodel.YangDataTypes.INT64;
23import static org.onosproject.yangutils.datamodel.YangDataTypes.INT8;
24import static org.onosproject.yangutils.datamodel.YangDataTypes.UINT16;
25import static org.onosproject.yangutils.datamodel.YangDataTypes.UINT32;
26import static org.onosproject.yangutils.datamodel.YangDataTypes.UINT64;
27import static org.onosproject.yangutils.datamodel.YangDataTypes.UINT8;
Bharat saraswal96dfef02016-06-16 00:29:12 +053028import static org.onosproject.yangutils.datamodel.utils.YangConstructType.LENGTH_DATA;
29import static org.onosproject.yangutils.datamodel.utils.YangConstructType.RANGE_DATA;
Gaurav Agrawal95b416c2016-06-07 14:00:26 +053030import static org.onosproject.yangutils.datamodel.utils.builtindatatype.BuiltInTypeObjectFactory.getDataObjectFromString;
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +053031
Bharat saraswal96dfef02016-06-16 00:29:12 +053032import java.util.regex.Pattern;
33
34import org.onosproject.yangutils.datamodel.YangDataTypes;
35import org.onosproject.yangutils.datamodel.YangRangeInterval;
36import org.onosproject.yangutils.datamodel.YangRangeRestriction;
37import org.onosproject.yangutils.datamodel.exceptions.DataModelException;
38import org.onosproject.yangutils.datamodel.utils.builtindatatype.YangBuiltInDataTypeInfo;
39
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +053040/**
41 * Represents restriction resolver which provide common utility used by parser
42 * and during linking for restriction resolution.
43 */
44public final class RestrictionResolver {
45
46 private static final String PIPE = "|";
Bharat saraswal96dfef02016-06-16 00:29:12 +053047 private static final String ADD = "+";
48 private static final String EMPTY_STRING = "";
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +053049 private static final String INTERVAL = "..";
50 private static final int MAX_RANGE_BOUNDARY = 2;
51 private static final int MIN_RANGE_BOUNDARY = 1;
52 private static final String MIN_KEYWORD = "min";
53 private static final String MAX_KEYWORD = "max";
54
55 /**
56 * Creates a restriction resolver.
57 */
58 private RestrictionResolver() {
59 }
60
61 /**
62 * Processes the range restriction for parser and linker.
63 *
64 * @param refRangeRestriction range restriction of referred typedef
65 * @param lineNumber error line number
66 * @param charPositionInLine error character position in line
67 * @param hasReferredRestriction whether has referred restriction
68 * @param curRangeString caller type's range string
69 * @param effectiveType effective type, when called from linker
70 * @return YANG range restriction
Gaurav Agrawal95b416c2016-06-07 14:00:26 +053071 * @throws DataModelException a violation in data model rule
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +053072 */
73 public static YangRangeRestriction processRangeRestriction(YangRangeRestriction refRangeRestriction,
Bharat saraswal96dfef02016-06-16 00:29:12 +053074 int lineNumber, int charPositionInLine,
75 boolean hasReferredRestriction,
76 String curRangeString, YangDataTypes effectiveType)
Gaurav Agrawal95b416c2016-06-07 14:00:26 +053077 throws DataModelException {
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +053078 YangBuiltInDataTypeInfo<?> startValue;
79 YangBuiltInDataTypeInfo<?> endValue;
80 YangRangeRestriction rangeRestriction = new YangRangeRestriction();
81
82 String rangeArgument = removeQuotesAndHandleConcat(curRangeString);
83 String[] rangeArguments = rangeArgument.trim().split(Pattern.quote(PIPE));
84
85 for (String rangePart : rangeArguments) {
86 String startInterval;
87 String endInterval;
88 YangRangeInterval rangeInterval = new YangRangeInterval();
89 String[] rangeBoundary = rangePart.trim().split(Pattern.quote(INTERVAL));
90
91 if (rangeBoundary.length > MAX_RANGE_BOUNDARY) {
Gaurav Agrawal95b416c2016-06-07 14:00:26 +053092 DataModelException dataModelException = new DataModelException("YANG file error : " +
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +053093 YangConstructType.getYangConstructType(RANGE_DATA) + " " + rangeArgument +
94 " is not valid.");
Gaurav Agrawal95b416c2016-06-07 14:00:26 +053095 dataModelException.setLine(lineNumber);
96 dataModelException.setCharPosition(charPositionInLine);
97 throw dataModelException;
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +053098 }
99
100 if (rangeBoundary.length == MIN_RANGE_BOUNDARY) {
janani bdd1314f2016-05-19 17:39:50 +0530101 startInterval = rangeBoundary[0].trim();
102 endInterval = rangeBoundary[0].trim();
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530103 } else {
janani bdd1314f2016-05-19 17:39:50 +0530104 startInterval = rangeBoundary[0].trim();
105 endInterval = rangeBoundary[1].trim();
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530106 }
107
108 try {
109 if (hasReferredRestriction && startInterval.equals(MIN_KEYWORD)
110 && refRangeRestriction.getMinRestrictedvalue() != null) {
111 startValue = refRangeRestriction.getMinRestrictedvalue();
112 } else if (hasReferredRestriction && startInterval.equals(MAX_KEYWORD)
113 && refRangeRestriction.getMaxRestrictedvalue() != null) {
114 startValue = refRangeRestriction.getMaxRestrictedvalue();
115 } else {
116 startValue = getDataObjectFromString(startInterval, effectiveType);
117 }
118 if (hasReferredRestriction && endInterval.equals(MIN_KEYWORD)
119 && refRangeRestriction.getMinRestrictedvalue() != null) {
120 endValue = refRangeRestriction.getMinRestrictedvalue();
121 } else if (hasReferredRestriction && endInterval.equals(MAX_KEYWORD)
122 && refRangeRestriction.getMaxRestrictedvalue() != null) {
123 endValue = refRangeRestriction.getMaxRestrictedvalue();
124 } else {
125 endValue = getDataObjectFromString(endInterval, effectiveType);
126 }
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530127 } catch (Exception e) {
128 DataModelException dataModelException = new DataModelException(e.getMessage());
129 dataModelException.setLine(lineNumber);
130 dataModelException.setCharPosition(charPositionInLine);
131 throw dataModelException;
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530132 }
133
134 rangeInterval.setStartValue(startValue);
135 rangeInterval.setEndValue(endValue);
136
137 try {
138 rangeRestriction.addRangeRestrictionInterval(rangeInterval);
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530139 } catch (DataModelException dataModelException) {
140 dataModelException.setLine(lineNumber);
141 dataModelException.setCharPosition(charPositionInLine);
142 throw dataModelException;
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530143 }
144 }
145 return rangeRestriction;
146 }
147
148 /**
149 * Processes the length restriction for parser and linker.
150 *
151 * @param refLengthRestriction length restriction of referred typedef
152 * @param lineNumber error line number
153 * @param charPositionInLine error character position in line
154 * @param hasReferredRestriction whether has referred restriction
155 * @param curLengthString caller type's length string
156 * @return YANG range restriction
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530157 * @throws DataModelException a violation in data model rule
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530158 */
159 public static YangRangeRestriction processLengthRestriction(YangRangeRestriction refLengthRestriction,
Bharat saraswal96dfef02016-06-16 00:29:12 +0530160 int lineNumber, int charPositionInLine,
161 boolean hasReferredRestriction,
162 String curLengthString) throws DataModelException {
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530163
164 YangBuiltInDataTypeInfo<?> startValue;
165 YangBuiltInDataTypeInfo<?> endValue;
166 YangRangeRestriction lengthRestriction = new YangRangeRestriction<>();
167
168 String rangeArgument = removeQuotesAndHandleConcat(curLengthString);
169 String[] rangeArguments = rangeArgument.trim().split(Pattern.quote(PIPE));
170
171 for (String rangePart : rangeArguments) {
172 String startInterval;
173 String endInterval;
174 YangRangeInterval rangeInterval = new YangRangeInterval<>();
175 String[] rangeBoundary = rangePart.trim().split(Pattern.quote(INTERVAL));
176
177 if (rangeBoundary.length > MAX_RANGE_BOUNDARY) {
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530178 DataModelException dataModelException = new DataModelException("YANG file error : " +
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530179 YangConstructType.getYangConstructType(LENGTH_DATA) + " " + rangeArgument +
180 " is not valid.");
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530181 dataModelException.setLine(lineNumber);
182 dataModelException.setCharPosition(charPositionInLine);
183 throw dataModelException;
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530184 }
185
186 if (rangeBoundary.length == MIN_RANGE_BOUNDARY) {
janani bdd1314f2016-05-19 17:39:50 +0530187 startInterval = rangeBoundary[0].trim();
188 endInterval = rangeBoundary[0].trim();
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530189 } else {
janani bdd1314f2016-05-19 17:39:50 +0530190 startInterval = rangeBoundary[0].trim();
191 endInterval = rangeBoundary[1].trim();
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530192 }
193
194 try {
195 if (hasReferredRestriction && startInterval.equals(MIN_KEYWORD)
196 && refLengthRestriction.getMinRestrictedvalue() != null) {
197 startValue = refLengthRestriction.getMinRestrictedvalue();
198 } else if (hasReferredRestriction && startInterval.equals(MAX_KEYWORD)
199 && refLengthRestriction.getMaxRestrictedvalue() != null) {
200 startValue = refLengthRestriction.getMaxRestrictedvalue();
201 } else {
202 startValue = getDataObjectFromString(startInterval, YangDataTypes.UINT64);
203 }
204 if (hasReferredRestriction && endInterval.equals(MIN_KEYWORD)
205 && refLengthRestriction.getMinRestrictedvalue() != null) {
206 endValue = refLengthRestriction.getMinRestrictedvalue();
207 } else if (hasReferredRestriction && endInterval.equals(MAX_KEYWORD)
208 && refLengthRestriction.getMaxRestrictedvalue() != null) {
209 endValue = refLengthRestriction.getMaxRestrictedvalue();
210 } else {
211 endValue = getDataObjectFromString(endInterval, YangDataTypes.UINT64);
212 }
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530213 } catch (Exception e) {
214 DataModelException dataModelException = new DataModelException(e.getMessage());
215 dataModelException.setLine(lineNumber);
216 dataModelException.setCharPosition(charPositionInLine);
217 throw dataModelException;
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530218 }
219
220 rangeInterval.setStartValue(startValue);
221 rangeInterval.setEndValue(endValue);
222
223 try {
224 lengthRestriction.addRangeRestrictionInterval(rangeInterval);
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530225 } catch (DataModelException dataModelException) {
226 dataModelException.setLine(lineNumber);
227 dataModelException.setCharPosition(charPositionInLine);
228 throw dataModelException;
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530229 }
230 }
231 return lengthRestriction;
232 }
233
234 /**
235 * Returns whether the data type is of range restricted type.
236 *
237 * @param dataType data type to be checked
238 * @return true, if data type can have range restrictions, false otherwise
239 */
240 public static boolean isOfRangeRestrictedType(YangDataTypes dataType) {
Bharat saraswal96dfef02016-06-16 00:29:12 +0530241 return dataType == INT8
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530242 || dataType == INT16
243 || dataType == INT32
244 || dataType == INT64
245 || dataType == UINT8
246 || dataType == UINT16
247 || dataType == UINT32
248 || dataType == UINT64
Bharat saraswal96dfef02016-06-16 00:29:12 +0530249 || dataType == DECIMAL64;
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530250 }
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530251
252 /**
253 * Removes doubles quotes and concatenates if string has plus symbol.
254 *
255 * @param yangStringData string from yang file
256 * @return concatenated string after removing double quotes
257 */
258 private static String removeQuotesAndHandleConcat(String yangStringData) {
259
260 yangStringData = yangStringData.replace("\"", EMPTY_STRING);
261 String[] tmpData = yangStringData.split(Pattern.quote(ADD));
262 StringBuilder builder = new StringBuilder();
263 for (String yangString : tmpData) {
264 builder.append(yangString);
265 }
266 return builder.toString();
267 }
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530268}