blob: 84de87693a6f671ef448bc572076d8f248707397 [file] [log] [blame]
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +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
17package org.onosproject.yangutils.linker.impl;
18
Bharat saraswale3175d32016-08-31 17:50:11 +053019import org.onosproject.yangutils.datamodel.DefaultLocationInfo;
Bharat saraswalc2d3be12016-06-16 00:29:12 +053020import org.onosproject.yangutils.datamodel.Resolvable;
janani b0e4e8ae2016-07-13 21:06:41 +053021import org.onosproject.yangutils.datamodel.ResolvableType;
Bharat saraswal9fab16b2016-09-23 23:27:24 +053022import org.onosproject.yangutils.datamodel.RpcNotificationContainer;
Vidyashree Rama72719fa2016-07-15 14:06:56 +053023import org.onosproject.yangutils.datamodel.TraversalType;
janani b0e4e8ae2016-07-13 21:06:41 +053024import org.onosproject.yangutils.datamodel.YangAtomicPath;
Bharat saraswald14cbe82016-07-14 13:26:18 +053025import org.onosproject.yangutils.datamodel.YangAugment;
26import org.onosproject.yangutils.datamodel.YangAugmentableNode;
Shankara-Huawei234cd092016-07-14 11:35:34 +053027import org.onosproject.yangutils.datamodel.YangBase;
Vidyashree Ramab3670472016-08-06 15:49:56 +053028import org.onosproject.yangutils.datamodel.YangCompilerAnnotation;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +053029import org.onosproject.yangutils.datamodel.YangDerivedInfo;
janani bebb143d2016-07-14 19:35:22 +053030import org.onosproject.yangutils.datamodel.YangEntityToResolveInfoImpl;
Vidyashree Rama13b4c552016-06-20 15:12:43 +053031import org.onosproject.yangutils.datamodel.YangFeature;
32import org.onosproject.yangutils.datamodel.YangFeatureHolder;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +053033import org.onosproject.yangutils.datamodel.YangGrouping;
Shankara-Huawei234cd092016-07-14 11:35:34 +053034import org.onosproject.yangutils.datamodel.YangIdentity;
35import org.onosproject.yangutils.datamodel.YangIdentityRef;
Bharat saraswalaf413b82016-07-14 15:18:20 +053036import org.onosproject.yangutils.datamodel.YangIfFeature;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +053037import org.onosproject.yangutils.datamodel.YangImport;
38import org.onosproject.yangutils.datamodel.YangInclude;
janani b0e4e8ae2016-07-13 21:06:41 +053039import org.onosproject.yangutils.datamodel.YangInput;
40import org.onosproject.yangutils.datamodel.YangLeaf;
41import org.onosproject.yangutils.datamodel.YangLeafList;
42import org.onosproject.yangutils.datamodel.YangLeafRef;
Vidyashree Ramab3670472016-08-06 15:49:56 +053043import org.onosproject.yangutils.datamodel.YangList;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +053044import org.onosproject.yangutils.datamodel.YangNode;
Vidyashree Rama13b4c552016-06-20 15:12:43 +053045import org.onosproject.yangutils.datamodel.YangNodeIdentifier;
Gaurav Agrawal58b348e2016-06-07 14:00:26 +053046import org.onosproject.yangutils.datamodel.YangReferenceResolver;
janani b0e4e8ae2016-07-13 21:06:41 +053047import org.onosproject.yangutils.datamodel.YangRelativePath;
Gaurav Agrawal58b348e2016-06-07 14:00:26 +053048import org.onosproject.yangutils.datamodel.YangResolutionInfo;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +053049import org.onosproject.yangutils.datamodel.YangType;
50import org.onosproject.yangutils.datamodel.YangTypeDef;
51import org.onosproject.yangutils.datamodel.YangUses;
Bharat saraswald14cbe82016-07-14 13:26:18 +053052import org.onosproject.yangutils.datamodel.YangXPathResolver;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +053053import org.onosproject.yangutils.datamodel.exceptions.DataModelException;
Bharat saraswalc2d3be12016-06-16 00:29:12 +053054import org.onosproject.yangutils.datamodel.utils.ResolvableStatus;
janani b0e4e8ae2016-07-13 21:06:41 +053055import org.onosproject.yangutils.datamodel.utils.builtindatatype.YangDataTypes;
Bharat saraswald14cbe82016-07-14 13:26:18 +053056import org.onosproject.yangutils.linker.exceptions.LinkerException;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +053057
Bharat saraswal9fab16b2016-09-23 23:27:24 +053058import java.io.Serializable;
59import java.util.Iterator;
60import java.util.LinkedList;
61import java.util.List;
62import java.util.Stack;
63
64import static org.onosproject.yangutils.datamodel.ResolvableType.YANG_IDENTITYREF;
65import static org.onosproject.yangutils.datamodel.ResolvableType.YANG_LEAFREF;
Vidyashree Rama72719fa2016-07-15 14:06:56 +053066import static org.onosproject.yangutils.datamodel.TraversalType.CHILD;
67import static org.onosproject.yangutils.datamodel.TraversalType.PARENT;
68import static org.onosproject.yangutils.datamodel.TraversalType.ROOT;
69import static org.onosproject.yangutils.datamodel.TraversalType.SIBILING;
Bharat saraswal9fab16b2016-09-23 23:27:24 +053070import static org.onosproject.yangutils.datamodel.YangPathArgType.ABSOLUTE_PATH;
71import static org.onosproject.yangutils.datamodel.YangPathArgType.RELATIVE_PATH;
72import static org.onosproject.yangutils.datamodel.exceptions.ErrorMessages.getErrorMsg;
janani bebb143d2016-07-14 19:35:22 +053073import static org.onosproject.yangutils.datamodel.utils.DataModelUtils.addResolutionInfo;
Bharat saraswalc2d3be12016-06-16 00:29:12 +053074import static org.onosproject.yangutils.datamodel.utils.ResolvableStatus.INTER_FILE_LINKED;
75import static org.onosproject.yangutils.datamodel.utils.ResolvableStatus.INTRA_FILE_RESOLVED;
76import static org.onosproject.yangutils.datamodel.utils.ResolvableStatus.LINKED;
77import static org.onosproject.yangutils.datamodel.utils.ResolvableStatus.RESOLVED;
Vidyashree Rama13b4c552016-06-20 15:12:43 +053078import static org.onosproject.yangutils.datamodel.utils.ResolvableStatus.UNDEFINED;
Bharat saraswalc2d3be12016-06-16 00:29:12 +053079import static org.onosproject.yangutils.datamodel.utils.ResolvableStatus.UNRESOLVED;
Bharat saraswal9fab16b2016-09-23 23:27:24 +053080import static org.onosproject.yangutils.datamodel.utils.YangConstructType.PATH_DATA;
Bharat saraswald14cbe82016-07-14 13:26:18 +053081import static org.onosproject.yangutils.linker.impl.YangLinkerUtils.detectCollisionForAugmentedNode;
Bharat saraswal9fab16b2016-09-23 23:27:24 +053082import static org.onosproject.yangutils.linker.impl.YangLinkerUtils.getErrorInfoForLinker;
83import static org.onosproject.yangutils.linker.impl.YangLinkerUtils.getLeafRefErrorInfo;
janani bebb143d2016-07-14 19:35:22 +053084import static org.onosproject.yangutils.linker.impl.YangLinkerUtils.getPathWithAugment;
85import static org.onosproject.yangutils.linker.impl.YangLinkerUtils.getValidNodeIdentifier;
86import static org.onosproject.yangutils.linker.impl.YangLinkerUtils.skipInvalidDataNodes;
janani bebb143d2016-07-14 19:35:22 +053087import static org.onosproject.yangutils.utils.UtilConstants.EMPTY_STRING;
Bharat saraswal9fab16b2016-09-23 23:27:24 +053088import static org.onosproject.yangutils.utils.UtilConstants.FAILED_TO_FIND_ANNOTATION;
89import static org.onosproject.yangutils.utils.UtilConstants.FAILED_TO_FIND_LEAD_INFO_HOLDER;
90import static org.onosproject.yangutils.utils.UtilConstants.FAILED_TO_LINK;
Bharat saraswalaf413b82016-07-14 15:18:20 +053091import static org.onosproject.yangutils.utils.UtilConstants.IDENTITYREF;
Bharat saraswal9fab16b2016-09-23 23:27:24 +053092import static org.onosproject.yangutils.utils.UtilConstants.INVALID_ENTITY;
93import static org.onosproject.yangutils.utils.UtilConstants.INVALID_LINKER_STATE;
94import static org.onosproject.yangutils.utils.UtilConstants.INVALID_RESOLVED_ENTITY;
95import static org.onosproject.yangutils.utils.UtilConstants.INVALID_TARGET;
96import static org.onosproject.yangutils.utils.UtilConstants.INVALID_TREE;
janani b0e4e8ae2016-07-13 21:06:41 +053097import static org.onosproject.yangutils.utils.UtilConstants.LEAFREF;
Bharat saraswal9fab16b2016-09-23 23:27:24 +053098import static org.onosproject.yangutils.utils.UtilConstants.LINKER_ERROR;
janani bebb143d2016-07-14 19:35:22 +053099import static org.onosproject.yangutils.utils.UtilConstants.SLASH_FOR_STRING;
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530100import static org.onosproject.yangutils.utils.UtilConstants.UNRESOLVABLE;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530101
102/**
Gaurav Agrawal58b348e2016-06-07 14:00:26 +0530103 * Represents implementation of resolution object which will be resolved by
104 * linker.
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530105 *
106 * @param <T> type of resolution entity uses / type
107 */
Bharat saraswale3175d32016-08-31 17:50:11 +0530108public class YangResolutionInfoImpl<T> extends DefaultLocationInfo
Bharat saraswalc2d3be12016-06-16 00:29:12 +0530109 implements YangResolutionInfo<T>, Serializable {
110
111 private static final long serialVersionUID = 806201658L;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530112
113 /**
114 * Information about the entity that needs to be resolved.
115 */
Gaurav Agrawal58b348e2016-06-07 14:00:26 +0530116 private YangEntityToResolveInfoImpl<T> entityToResolveInfo;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530117
118 /**
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530119 * Current module/sub-module reference, will be used in inter-file/
120 * inter-jar scenario to get the import/include list.
121 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530122 private YangReferenceResolver curRefResolver;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530123
124 /**
125 * Stack for type/uses is maintained for hierarchical references, this is
126 * used during resolution.
127 */
Gaurav Agrawal58b348e2016-06-07 14:00:26 +0530128 private Stack<YangEntityToResolveInfoImpl<T>> partialResolvedStack;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530129
130 /**
131 * It is private to ensure the overloaded method be invoked to create an
132 * object.
133 */
134 @SuppressWarnings("unused")
Gaurav Agrawal58b348e2016-06-07 14:00:26 +0530135 private YangResolutionInfoImpl() {
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530136 }
137
138 /**
139 * Creates a resolution information object with all the inputs.
140 *
141 * @param dataNode current parsable data node
142 * @param holderNode parent YANG node
143 * @param lineNumber error line number
144 * @param charPositionInLine error character position in line
145 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530146 public YangResolutionInfoImpl(T dataNode, YangNode holderNode, int lineNumber,
147 int charPositionInLine) {
148 entityToResolveInfo = new YangEntityToResolveInfoImpl<>();
149 entityToResolveInfo.setEntityToResolve(dataNode);
150 entityToResolveInfo.setHolderOfEntityToResolve(holderNode);
151 setLineNumber(lineNumber);
152 setCharPosition(charPositionInLine);
153 partialResolvedStack = new Stack<>();
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530154 }
155
Gaurav Agrawal58b348e2016-06-07 14:00:26 +0530156 @Override
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530157 public void resolveLinkingForResolutionInfo(YangReferenceResolver dataModelRootNode)
158 throws DataModelException {
159
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530160 curRefResolver = dataModelRootNode;
161 /*
Shankara-Huawei234cd092016-07-14 11:35:34 +0530162 * Current node to resolve, it can be a YANG type, YANG uses or YANG if-feature or
163 * YANG leafref or YANG base or YANG identityref.
164 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530165 T entityToResolve = entityToResolveInfo.getEntityToResolve();
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530166
167 // Check if linking is already done
168 if (entityToResolve instanceof Resolvable) {
169 Resolvable resolvable = (Resolvable) entityToResolve;
170 if (resolvable.getResolvableStatus() == RESOLVED) {
Bharat saraswal2da23bf2016-08-25 15:28:39 +0530171 /*
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530172 * entity is already resolved, so nothing to do
173 */
174 return;
175 }
176 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530177 throw new DataModelException(LINKER_ERROR);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530178 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530179 // Push the initial entity to resolve in stack.
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530180 addInPartialResolvedStack(entityToResolveInfo);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530181 linkAndResolvePartialResolvedStack();
janani b0e4e8ae2016-07-13 21:06:41 +0530182 addDerivedRefTypeToRefTypeResolutionList();
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530183 }
184
185 /**
186 * Resolves linking with ancestors.
187 *
188 * @throws DataModelException a violation of data model rules
189 */
190 private void linkAndResolvePartialResolvedStack()
191 throws DataModelException {
192
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530193 while (!partialResolvedStack.isEmpty()) {
Bharat saraswal2da23bf2016-08-25 15:28:39 +0530194 /*
Shankara-Huawei234cd092016-07-14 11:35:34 +0530195 * Current node to resolve, it can be a YANG type or YANG uses or
196 * YANG if-feature or YANG leafref or YANG base or YANG identityref.
197 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530198 T entityToResolve = getCurEntityToResolveFromStack();
199 if (!(entityToResolve instanceof Resolvable)) {
200 throw new DataModelException(LINKER_ERROR);
201 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530202 // Check if linking is already done
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530203 Resolvable resolvable = (Resolvable) entityToResolve;
204 switch (resolvable.getResolvableStatus()) {
205 case RESOLVED:
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530206 /*
207 * If the entity is already resolved in the stack, then pop
208 * it and continue with the remaining stack elements to
209 * resolve
210 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530211 partialResolvedStack.pop();
212 break;
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530213
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530214 case LINKED:
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530215 /*
216 * If the top of the stack is already linked then resolve
217 * the references and pop the entity and continue with
218 * remaining stack elements to resolve.
219 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530220 resolveTopOfStack();
221 partialResolvedStack.pop();
222 break;
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530223
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530224 case INTRA_FILE_RESOLVED:
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530225 /*
226 * Pop the top of the stack.
227 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530228 partialResolvedStack.pop();
229 break;
230
231 case UNRESOLVED:
232 linkTopOfStackReferenceUpdateStack();
233
234 if (resolvable.getResolvableStatus() == UNRESOLVED) {
235 // If current entity is still not resolved, then
236 // linking/resolution has failed.
237 DataModelException ex =
238 new DataModelException
239 (getErrorInfoForLinker(resolvable));
240 ex.setLine(getLineNumber());
241 ex.setCharPosition(getCharPosition());
242 throw ex;
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530243 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530244 break;
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530245
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530246 default:
247 throw new DataModelException(INVALID_LINKER_STATE);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530248 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530249 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530250 }
251
252 /**
Shankara-Huawei234cd092016-07-14 11:35:34 +0530253 * Adds the leafref/identityref type to the type, which has derived type referring to
254 * typedef with leafref/identityref type.
janani b0e4e8ae2016-07-13 21:06:41 +0530255 */
VinodKumarS-Huawei423dc9a2016-08-17 22:08:42 +0530256 private void addDerivedRefTypeToRefTypeResolutionList()
257 throws DataModelException {
janani b0e4e8ae2016-07-13 21:06:41 +0530258
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530259 YangNode refNode = entityToResolveInfo.getHolderOfEntityToResolve();
260 YangType yangType = getValidateResolvableType();
janani b0e4e8ae2016-07-13 21:06:41 +0530261
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530262 if (yangType == null) {
janani b0e4e8ae2016-07-13 21:06:41 +0530263 return;
264 }
265
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530266 YangDerivedInfo derivedInfo = (YangDerivedInfo) yangType
267 .getDataTypeExtendedInfo();
janani b0e4e8ae2016-07-13 21:06:41 +0530268
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530269 YangDataTypes dataType = derivedInfo.getEffectiveBuiltInType();
Vidyashree Ramab3670472016-08-06 15:49:56 +0530270 // If the derived types referred type is not leafref/identityref return
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530271 if (dataType != YangDataTypes.LEAFREF &&
272 dataType != YangDataTypes.IDENTITYREF) {
janani b0e4e8ae2016-07-13 21:06:41 +0530273 return;
274 }
275
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530276 T extendedInfo = (T) derivedInfo.getReferredTypeDef()
277 .getTypeDefBaseType().getDataTypeExtendedInfo();
janani b0e4e8ae2016-07-13 21:06:41 +0530278
279 while (extendedInfo instanceof YangDerivedInfo) {
280 YangDerivedInfo derivedInfoFromTypedef = (YangDerivedInfo) extendedInfo;
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530281 extendedInfo = (T) derivedInfoFromTypedef.getReferredTypeDef()
282 .getTypeDefBaseType().getDataTypeExtendedInfo();
janani b0e4e8ae2016-07-13 21:06:41 +0530283 }
Shankara-Huawei234cd092016-07-14 11:35:34 +0530284
janani b0e4e8ae2016-07-13 21:06:41 +0530285 /*
Shankara-Huawei234cd092016-07-14 11:35:34 +0530286 * Backup the derived types leafref/identityref info, delete all the info in current type,
287 * but for resolution status as resolved. Copy the backed up leafref/identityref to types extended info,
288 * create a leafref/identityref resolution info using the current resolution info and
289 * add to leafref/identityref resolution list.
janani b0e4e8ae2016-07-13 21:06:41 +0530290 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530291 if (dataType == YangDataTypes.LEAFREF) {
Shankara-Huawei234cd092016-07-14 11:35:34 +0530292 YangLeafRef leafRefInTypeDef = (YangLeafRef) extendedInfo;
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530293 addRefTypeInfo(YangDataTypes.LEAFREF, LEAFREF, extendedInfo,
294 yangType, refNode, YANG_LEAFREF);
295 leafRefInTypeDef.setParentNodeOfLeafref(refNode);
296 } else {
297 addRefTypeInfo(YangDataTypes.IDENTITYREF, IDENTITYREF, extendedInfo,
298 yangType, refNode, YANG_IDENTITYREF);
Shankara-Huawei234cd092016-07-14 11:35:34 +0530299 }
janani b0e4e8ae2016-07-13 21:06:41 +0530300 }
301
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530302 //Validates entity to resolve for YANG type and returns type
303 private YangType getValidateResolvableType() {
304 YangNode refNode = entityToResolveInfo.getHolderOfEntityToResolve();
305 T entity = entityToResolveInfo.getEntityToResolve();
306 // If holder is typedef return.
307 if (!(refNode instanceof YangTypeDef) && entity instanceof YangType) {
308 YangType yangType = (YangType) entity;
309
310 // If type is not resolved return.
311 if (yangType.getResolvableStatus() == RESOLVED) {
312 return (YangType) entity;
313 }
314 }
315 return null;
316 }
317
318 /**
319 * Adds referred type(leafref/identityref) info to resolution list.
320 *
321 * @param type data type
322 * @param typeName type name
323 * @param info extended info
324 * @param yangType YANG type
325 * @param refNode referred node
326 * @param resType resolution type
327 * @throws DataModelException when fails to do data model operations
328 */
329 private void addRefTypeInfo(YangDataTypes type, String typeName, T info,
330 YangType yangType, YangNode refNode,
331 ResolvableType resType) throws DataModelException {
332 yangType.resetYangType();
333 yangType.setResolvableStatus(RESOLVED);
334 yangType.setDataType(type);
335 yangType.setDataTypeName(typeName);
336 yangType.setDataTypeExtendedInfo(info);
337 ((Resolvable) info).setResolvableStatus(UNRESOLVED);
338 YangResolutionInfoImpl resolutionInfoImpl
339 = new YangResolutionInfoImpl<>(info, refNode,
340 getLineNumber(), getCharPosition());
341 curRefResolver.addToResolutionList(resolutionInfoImpl, resType);
342 curRefResolver.resolveSelfFileLinking(resType);
343 }
344
janani b0e4e8ae2016-07-13 21:06:41 +0530345 /**
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530346 * Resolves the current entity in the stack.
347 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530348 private void resolveTopOfStack()
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530349 throws DataModelException {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530350 T entity = getCurEntityToResolveFromStack();
351 List<T> entityToResolve = (List<T>) ((Resolvable) entity).resolve();
janani bebb143d2016-07-14 19:35:22 +0530352 if (entityToResolve != null && !entityToResolve.isEmpty()) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530353 for (T anEntityToResolve : entityToResolve) {
354 addUnresolvedEntitiesToResolutionList(anEntityToResolve);
janani bebb143d2016-07-14 19:35:22 +0530355 }
356 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530357 if (((Resolvable) entity).getResolvableStatus() != INTRA_FILE_RESOLVED &&
358 ((Resolvable) entity).getResolvableStatus() != UNDEFINED) {
janani b0e4e8ae2016-07-13 21:06:41 +0530359 // Sets the resolution status in inside the type/uses/if-feature/leafref.
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530360 ((Resolvable) entity).setResolvableStatus(RESOLVED);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530361 }
362 }
363
364 /**
janani bebb143d2016-07-14 19:35:22 +0530365 * Adds the unresolved entities to the resolution list.
366 *
367 * @param entityToResolve entity to resolve
368 * @throws DataModelException a violation of data model rules
369 */
VinodKumarS-Huawei423dc9a2016-08-17 22:08:42 +0530370 private void addUnresolvedEntitiesToResolutionList(T entityToResolve)
371 throws DataModelException {
janani bebb143d2016-07-14 19:35:22 +0530372 if (entityToResolve instanceof YangEntityToResolveInfoImpl) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530373 YangEntityToResolveInfoImpl entityToResolveInfo
374 = (YangEntityToResolveInfoImpl) entityToResolve;
janani bebb143d2016-07-14 19:35:22 +0530375 if (entityToResolveInfo.getEntityToResolve() instanceof YangLeafRef) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530376 YangLeafRef leafref = (YangLeafRef) entityToResolveInfo
377 .getEntityToResolve();
378 YangNode parentNodeOfLeafref = entityToResolveInfo
379 .getHolderOfEntityToResolve();
janani bebb143d2016-07-14 19:35:22 +0530380 leafref.setParentNodeOfLeafref(parentNodeOfLeafref);
381 if (leafref.getResolvableStatus() == UNRESOLVED) {
382 leafref.setResolvableStatus(INTRA_FILE_RESOLVED);
383 }
janani bebb143d2016-07-14 19:35:22 +0530384 }
VinodKumarS-Huawei423dc9a2016-08-17 22:08:42 +0530385
386 // Add resolution information to the list.
387 YangResolutionInfoImpl resolutionInfoImpl = new YangResolutionInfoImpl<>(
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530388 entityToResolveInfo.getEntityToResolve(),
389 entityToResolveInfo.getHolderOfEntityToResolve(),
390 entityToResolveInfo.getLineNumber(),
391 entityToResolveInfo.getCharPosition());
VinodKumarS-Huawei423dc9a2016-08-17 22:08:42 +0530392 addResolutionInfo(resolutionInfoImpl);
janani bebb143d2016-07-14 19:35:22 +0530393 }
394 }
395
396 /**
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530397 * Resolves linking for a node child and siblings.
398 *
399 * @throws DataModelException data model error
400 */
401 private void linkTopOfStackReferenceUpdateStack()
402 throws DataModelException {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530403 T entity = getCurEntityToResolveFromStack();
404 if (entity instanceof YangLeafRef) {
405 ((Resolvable) entity).setResolvableStatus(INTRA_FILE_RESOLVED);
janani bebb143d2016-07-14 19:35:22 +0530406 return;
407 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530408 /*
409 * Check if self file reference is there, this will not check for the
410 * scenario when prefix is not present and type/uses is present in
411 * sub-module from include list.
412 */
413 if (!isCandidateForSelfFileReference()) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530414 ((Resolvable) entity).setResolvableStatus(INTRA_FILE_RESOLVED);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530415 return;
416 }
417
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530418 /*
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530419 * Try to resolve the top of the stack and update partial resolved stack
420 * if there is recursive references
421 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530422 YangNode ancestorRefNode = partialResolvedStack.peek()
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530423 .getHolderOfEntityToResolve();
424
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530425 if (entity instanceof YangIfFeature) {
426 resolveSelfFileLinkingForIfFeature(ancestorRefNode);
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530427 return;
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530428 }
429 if (entity instanceof YangIdentityRef || entity instanceof YangBase) {
Shankara-Huawei234cd092016-07-14 11:35:34 +0530430 resolveSelfFileLinkingForBaseAndIdentityref();
431 return;
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530432 }
433 YangType type = null;
434 if (entity instanceof YangType) {
435 type = (YangType) entity;
436 }
437 /*
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530438 * Traverse up in the ancestor tree to check if the referred node is
439 * defined
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530440 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530441 while (ancestorRefNode != null) {
442 /*
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530443 * Check for the referred node defined in a ancestor scope
444 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530445 YangNode curRefNode = ancestorRefNode.getChild();
446 if (isReferredNodeInSiblingListProcessed(curRefNode)) {
447 return;
448 }
449 ancestorRefNode = ancestorRefNode.getParent();
450 if (type != null && ancestorRefNode != null) {
451 if (ancestorRefNode.getParent() == null) {
452 type.setTypeNotResolvedTillRootNode(true);
VinodKumarS-Huawei423dc9a2016-08-17 22:08:42 +0530453 }
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530454 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530455 }
456
457 /*
Gaurav Agrawal8a966b92016-08-20 00:07:27 +0530458 * In case prefix is not present or it's self prefix it's a candidate for inter-file
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530459 * resolution via include list.
460 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530461 if (getRefPrefix() == null ||
462 getRefPrefix().contentEquals(curRefResolver.getPrefix())) {
463 ((Resolvable) entity).setResolvableStatus(INTRA_FILE_RESOLVED);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530464 }
465 }
466
467 /**
Shankara-Huawei234cd092016-07-14 11:35:34 +0530468 * Resolves self file linking for base/identityref.
469 *
470 * @throws DataModelException a violation of data model rules
471 */
472 private void resolveSelfFileLinkingForBaseAndIdentityref()
473 throws DataModelException {
474
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530475 boolean refIdentity = false;
Shankara-Huawei234cd092016-07-14 11:35:34 +0530476 String nodeName = null;
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530477 T entity = getCurEntityToResolveFromStack();
478 if (entity instanceof YangIdentityRef) {
479 nodeName = ((YangIdentityRef) entity).getName();
480 } else if (entity instanceof YangBase) {
481 nodeName = ((YangBase) entity).getBaseIdentifier().getName();
Shankara-Huawei234cd092016-07-14 11:35:34 +0530482 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530483 if (curRefResolver instanceof RpcNotificationContainer) {
Shankara-Huawei234cd092016-07-14 11:35:34 +0530484 // Sends list of nodes for finding the target identity.
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530485 refIdentity = isIdentityReferenceFound(nodeName, (YangNode) curRefResolver);
Shankara-Huawei234cd092016-07-14 11:35:34 +0530486 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530487 if (refIdentity) {
Shankara-Huawei234cd092016-07-14 11:35:34 +0530488 return;
489 }
490
Gaurav Agrawal8a966b92016-08-20 00:07:27 +0530491 /*
492 * In case prefix is not present or it's self prefix it's a candidate for inter-file
493 * resolution via include list.
494 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530495 if (getRefPrefix() == null || getRefPrefix()
496 .contentEquals(curRefResolver.getPrefix())) {
497 ((Resolvable) entity).setResolvableStatus(INTRA_FILE_RESOLVED);
Shankara-Huawei234cd092016-07-14 11:35:34 +0530498 }
499 }
500
501 /**
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530502 * Resolves self file linking for if-feature.
503 *
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530504 * @param ancestorRefNode if-feature holder node
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530505 * @throws DataModelException DataModelException a violation of data model
506 * rules
507 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530508 private void resolveSelfFileLinkingForIfFeature(YangNode ancestorRefNode)
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530509 throws DataModelException {
510
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530511 YangFeatureHolder featureHolder = getFeatureHolder(ancestorRefNode);
512 YangNode curRefNode = (YangNode) featureHolder;
513 if (isReferredNode(curRefNode)) {
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530514
515 // Adds reference link of entity to the node under resolution.
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530516 addReferredEntityLink(curRefNode, LINKED);
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530517
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530518 /*
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530519 * resolve the reference and update the partial resolution stack
520 * with any further recursive references
521 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530522 addUnresolvedRecursiveReferenceToStack(curRefNode);
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530523 return;
524 }
525
526 /*
Gaurav Agrawal8a966b92016-08-20 00:07:27 +0530527 * In case prefix is not present or it's self prefix it's a candidate for inter-file
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530528 * resolution via include list.
529 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530530 if (getRefPrefix() == null || getRefPrefix()
531 .contentEquals(curRefResolver.getPrefix())) {
532 ((Resolvable) getCurEntityToResolveFromStack())
533 .setResolvableStatus(INTRA_FILE_RESOLVED);
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530534 }
535 }
536
janani b0e4e8ae2016-07-13 21:06:41 +0530537 /**
Shankara-Huawei234cd092016-07-14 11:35:34 +0530538 * Returns the status of the referred identity found for base/identityref.
539 *
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530540 * @param nodeName the name of the base node
541 * identifier/identityref node identifier
542 * @param ancestorRefNode the parent node of base/identityref
Shankara-Huawei234cd092016-07-14 11:35:34 +0530543 * @return status of referred base/identityref
544 * @throws DataModelException a violation of data model rules
545 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530546 private boolean isIdentityReferenceFound(String nodeName, YangNode ancestorRefNode)
Shankara-Huawei234cd092016-07-14 11:35:34 +0530547 throws DataModelException {
548
549 // When child is not present return.
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530550 if (ancestorRefNode.getChild() == null) {
Shankara-Huawei234cd092016-07-14 11:35:34 +0530551 return false;
552 }
553
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530554 ancestorRefNode = ancestorRefNode.getChild();
Shankara-Huawei234cd092016-07-14 11:35:34 +0530555
556 // Checks all the siblings under the node and returns the matched node.
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530557 YangNode nodeFound = isReferredNodeInSiblingProcessedForIdentity(ancestorRefNode,
558 nodeName);
Shankara-Huawei234cd092016-07-14 11:35:34 +0530559
560 if (nodeFound != null) {
561 // Adds reference link of entity to the node under resolution.
562 addReferredEntityLink(nodeFound, LINKED);
563
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530564 /*
Shankara-Huawei234cd092016-07-14 11:35:34 +0530565 * resolve the reference and update the partial resolution stack with any further recursive references
566 */
567 addUnresolvedRecursiveReferenceToStack(nodeFound);
568 return true;
569 }
570
571 return false;
572 }
573
574 /**
janani b0e4e8ae2016-07-13 21:06:41 +0530575 * Adds the unresolved constructs to stack which has to be resolved for leafref.
576 *
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530577 * @param leavesInfo YANG leaf or leaf list which holds the type
578 * @param ancestorRefNode holder of the YANG leaf or leaf list
janani b0e4e8ae2016-07-13 21:06:41 +0530579 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530580 private void addUnResolvedLeafRefTypeToStack(T leavesInfo, YangNode ancestorRefNode) {
janani b0e4e8ae2016-07-13 21:06:41 +0530581
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530582 YangType refType;
583 T extendedInfo;
584 if (leavesInfo instanceof YangLeaf) {
585 YangLeaf leaf = (YangLeaf) leavesInfo;
586 refType = leaf.getDataType();
janani b0e4e8ae2016-07-13 21:06:41 +0530587 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530588 YangLeafList leafList = (YangLeafList) leavesInfo;
589 refType = leafList.getDataType();
590 }
591 extendedInfo = (T) refType.getDataTypeExtendedInfo();
592 addUnResolvedTypeDataToStack(refType, ancestorRefNode, extendedInfo);
593 }
594
595 //Adds unresolved type info to stack.
596 private void addUnResolvedTypeDataToStack(YangType refType, YangNode
597 ancestorRefNode, T extendedInfo) {
598 YangEntityToResolveInfoImpl<YangLeafRef<?>> unResolvedLeafRef =
599 new YangEntityToResolveInfoImpl<>();
600 YangEntityToResolveInfoImpl<YangType<?>> unResolvedTypeDef =
601 new YangEntityToResolveInfoImpl<>();
602 if (refType.getDataType() == YangDataTypes.LEAFREF) {
603 unResolvedLeafRef.setEntityToResolve((YangLeafRef<?>) extendedInfo);
604 unResolvedLeafRef.setHolderOfEntityToResolve(ancestorRefNode);
605 addInPartialResolvedStack((YangEntityToResolveInfoImpl<T>) unResolvedLeafRef);
606 } else if (refType.getDataType() == YangDataTypes.DERIVED) {
607 unResolvedTypeDef.setEntityToResolve(refType);
608 unResolvedTypeDef.setHolderOfEntityToResolve(ancestorRefNode);
609 addInPartialResolvedStack((YangEntityToResolveInfoImpl<T>) unResolvedTypeDef);
janani b0e4e8ae2016-07-13 21:06:41 +0530610 }
611 }
612
613 /**
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530614 * Returns feature holder(module/sub-module node) .
615 *
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530616 * @param ancestorRefNode if-feature holder node
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530617 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530618 private YangFeatureHolder getFeatureHolder(YangNode ancestorRefNode) {
619 while (ancestorRefNode != null) {
620 if (ancestorRefNode instanceof YangFeatureHolder) {
621 return (YangFeatureHolder) ancestorRefNode;
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530622 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530623 ancestorRefNode = ancestorRefNode.getParent();
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530624 }
625 return null;
626 }
627
628 /**
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530629 * Checks if the reference in self file or in external file.
630 *
631 * @return true if self file reference, false otherwise
632 * @throws DataModelException a violation of data model rules
633 */
VinodKumarS-Huaweid81eccb2016-06-01 14:30:22 +0530634 private boolean isCandidateForSelfFileReference()
635 throws DataModelException {
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530636 String prefix = getRefPrefix();
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530637 return prefix == null || prefix.contentEquals(curRefResolver.getPrefix());
janani b0e4e8ae2016-07-13 21:06:41 +0530638 }
639
640 /**
Shankara-Huawei234cd092016-07-14 11:35:34 +0530641 * Checks for the referred parent node for the base/identity.
642 *
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530643 * @param refNode potential referred node
644 * @return the referred parent node of base/identity.
Shankara-Huawei234cd092016-07-14 11:35:34 +0530645 * @throws DataModelException data model errors
646 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530647 private YangNode isReferredNodeInSiblingProcessedForIdentity(YangNode refNode,
648 String refName)
VinodKumarS-Huawei423dc9a2016-08-17 22:08:42 +0530649 throws DataModelException {
Shankara-Huawei234cd092016-07-14 11:35:34 +0530650
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530651 while (refNode != null) {
652 if (refNode instanceof YangIdentity) {
Shankara-Huawei234cd092016-07-14 11:35:34 +0530653 // Check if the potential referred node is the actual referred node
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530654 if (isReferredNodeForIdentity(refNode, refName)) {
655 return refNode;
Shankara-Huawei234cd092016-07-14 11:35:34 +0530656 }
657 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530658 refNode = refNode.getNextSibling();
Shankara-Huawei234cd092016-07-14 11:35:34 +0530659 }
660 return null;
661 }
662
663 /**
Shankara-Huawei234cd092016-07-14 11:35:34 +0530664 * Checks if the current reference node name and the name in the base/identityref base are equal.
665 *
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530666 * @param curRefNode the node where the reference is pointed
667 * @param name name of the base in the base/identityref base
Shankara-Huawei234cd092016-07-14 11:35:34 +0530668 * @return status of the match between the name
669 * @throws DataModelException a violation of data model rules
670 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530671 private boolean isReferredNodeForIdentity(YangNode curRefNode, String name)
Shankara-Huawei234cd092016-07-14 11:35:34 +0530672 throws DataModelException {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530673 T entity = getCurEntityToResolveFromStack();
674 if (entity instanceof YangIdentityRef || entity instanceof YangBase) {
Vidyashree Ramab3670472016-08-06 15:49:56 +0530675
676 //Check if name of node name matches with the current reference node.
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530677 return curRefNode.getName().contentEquals(name);
Shankara-Huawei234cd092016-07-14 11:35:34 +0530678 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530679 throw new DataModelException(getErrorMsg(
680 INVALID_ENTITY, curRefNode.getName(), curRefNode.getLineNumber(),
681 curRefNode.getCharPosition(), curRefNode.getFileName()));
Shankara-Huawei234cd092016-07-14 11:35:34 +0530682 }
683 }
684
685 /**
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530686 * Checks for the referred node defined in a ancestor scope.
687 *
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530688 * @param refNode potential referred node
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530689 * @return status of resolution and updating the partial resolved stack with
690 * the any recursive references
janani b0e4e8ae2016-07-13 21:06:41 +0530691 * @throws DataModelException a violation of data model rules
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530692 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530693 private boolean isReferredNodeInSiblingListProcessed(YangNode refNode)
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530694 throws DataModelException {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530695 while (refNode != null) {
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530696
697 // Check if the potential referred node is the actual referred node
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530698 if (isReferredNode(refNode)) {
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530699
700 // Adds reference link of entity to the node under resolution.
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530701 addReferredEntityLink(refNode, LINKED);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530702
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530703 /*
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530704 * resolve the reference and update the partial resolution stack
705 * with any further recursive references
706 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530707 addUnresolvedRecursiveReferenceToStack(refNode);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530708
709 /*
710 * return true, since the reference is linked and any recursive
711 * unresolved references is added to the stack
712 */
713 return true;
714 }
715
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530716 refNode = refNode.getNextSibling();
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530717 }
718 return false;
719 }
720
721 /**
722 * Checks if the potential referred node is the actual referred node.
723 *
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530724 * @param refNode typedef/grouping node
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530725 * @return true if node is of resolve type otherwise false
726 * @throws DataModelException a violation of data model rules
727 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530728 private boolean isReferredNode(YangNode refNode)
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530729 throws DataModelException {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530730 T entity = getCurEntityToResolveFromStack();
731 if (entity instanceof YangType) {
732 if (refNode instanceof YangTypeDef) {
733 return isNodeNameSameAsResolutionInfoName(refNode);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530734 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530735 } else if (entity instanceof YangUses) {
736 if (refNode instanceof YangGrouping) {
737 return isNodeNameSameAsResolutionInfoName(refNode);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530738 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530739 } else if (entity instanceof YangIfFeature) {
740 if (refNode instanceof YangFeatureHolder) {
741 return isNodeNameSameAsResolutionInfoName(refNode);
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530742 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530743 } else if (entity instanceof YangBase || entity instanceof YangIdentityRef) {
744 if (refNode instanceof YangIdentity) {
745 return isNodeNameSameAsResolutionInfoName(refNode);
Shankara-Huawei234cd092016-07-14 11:35:34 +0530746 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530747 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530748 throw new DataModelException(getErrorMsg(
749 LINKER_ERROR, refNode.getName(), refNode.getLineNumber(),
750 refNode.getCharPosition(), refNode.getFileName()));
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530751 }
752 return false;
753 }
754
755 /**
756 * Checks if node name is same as name in resolution info, i.e. name of
757 * typedef/grouping is same as name of type/uses.
758 *
759 * @param node typedef/grouping node
760 * @return true if node name is same as name in resolution info, otherwise
761 * false
762 * @throws DataModelException a violation of data model rules
763 */
764
765 private boolean isNodeNameSameAsResolutionInfoName(YangNode node)
766 throws DataModelException {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530767 T entity = getCurEntityToResolveFromStack();
768 if (entity instanceof YangType) {
769 return node.getName().contentEquals(((YangType<?>) entity)
770 .getDataTypeName());
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530771 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530772 if (entity instanceof YangUses) {
773 return node.getName().contentEquals(((YangUses) entity).getName());
774 }
775 if (entity instanceof YangIfFeature) {
776 return isFeatureDefinedInNode(node);
777 }
778 if (entity instanceof YangBase) {
779 return node.getName().contentEquals(((
780 YangBase) entity).getBaseIdentifier().getName());
781 }
782 if (entity instanceof YangIdentityRef) {
783 return node.getName().contentEquals(((YangIdentityRef) entity).getName());
784 }
785 throw new DataModelException(getErrorMsg(
786 INVALID_RESOLVED_ENTITY, node.getName(), node.getLineNumber(),
787 node.getCharPosition(), node.getFileName()));
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530788 }
789
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530790 private boolean isFeatureDefinedInNode(YangNode node) {
791 T entity = getCurEntityToResolveFromStack();
792 YangNodeIdentifier ifFeature = ((YangIfFeature) entity).getName();
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530793 List<YangFeature> featureList = ((YangFeatureHolder) node).getFeatureList();
794 if (featureList != null && !featureList.isEmpty()) {
795 Iterator<YangFeature> iterator = featureList.iterator();
796 while (iterator.hasNext()) {
797 YangFeature feature = iterator.next();
798 if (ifFeature.getName().equals(feature.getName())) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530799 ((YangIfFeature) entity).setReferredFeature(feature);
800 ((YangIfFeature) entity).setReferredFeatureHolder(node);
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530801 return true;
802 }
803 }
804 }
805 return false;
806 }
807
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530808 /**
809 * Adds reference of grouping/typedef in uses/type.
810 *
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530811 * @param refNode grouping/typedef node being referred
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530812 * @param linkedStatus linked status if success.
813 * @throws DataModelException a violation of data model rules
814 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530815 private void addReferredEntityLink(YangNode refNode, ResolvableStatus linkedStatus)
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530816 throws DataModelException {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530817 T entity = getCurEntityToResolveFromStack();
818 if (entity instanceof YangType) {
819 YangDerivedInfo<?> derivedInfo = (YangDerivedInfo<?>) ((
820 YangType<?>) entity).getDataTypeExtendedInfo();
821 derivedInfo.setReferredTypeDef((YangTypeDef) refNode);
822 } else if (entity instanceof YangUses) {
823 ((YangUses) entity).setRefGroup((YangGrouping) refNode);
824 } else if (entity instanceof YangBase) {
825 ((YangBase) entity).setReferredIdentity((YangIdentity) refNode);
826 } else if (entity instanceof YangIdentityRef) {
827 ((YangIdentityRef) entity).setReferredIdentity((YangIdentity) refNode);
828 } else if (!(entity instanceof YangIfFeature) &&
829 !(entity instanceof YangLeafRef)) {
830 throw new DataModelException(getErrorMsg(
831 LINKER_ERROR, refNode.getName(), refNode.getLineNumber(),
832 refNode.getCharPosition(), refNode.getFileName()));
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530833 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530834 // Sets the resolution status in inside the type/uses.
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530835 ((Resolvable) entity).setResolvableStatus(linkedStatus);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530836 }
837
838 /**
839 * Checks if type/grouping has further reference to typedef/ unresolved
840 * uses. Add it to the partial resolve stack and return the status of
841 * addition to stack.
842 *
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530843 * @param refNode grouping/typedef node
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530844 * @throws DataModelException a violation of data model rules
845 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530846 private void addUnresolvedRecursiveReferenceToStack(YangNode refNode)
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530847 throws DataModelException {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530848 T entity = getCurEntityToResolveFromStack();
849 if (entity instanceof YangType) {
Vidyashree Ramab3670472016-08-06 15:49:56 +0530850
851 //Checks if typedef type is derived
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530852 if (((YangTypeDef) refNode).getTypeDefBaseType()
853 .getDataType() == YangDataTypes.DERIVED) {
854 addEntityToStack((T) ((YangTypeDef) refNode).getTypeDefBaseType(),
855 refNode);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530856 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530857 } else if (entity instanceof YangUses) {
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530858 /*
859 * Search if the grouping has any un resolved uses child, if so
860 * return true, else return false.
861 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530862 addUnResolvedUsesToStack(refNode);
863 } else if (entity instanceof YangIfFeature) {
864 addUnResolvedIfFeatureToStack(refNode);
865 } else if (entity instanceof YangLeafRef) {
janani b0e4e8ae2016-07-13 21:06:41 +0530866 // do nothing , referred node is already set
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530867 throw new DataModelException(getErrorMsg(
868 INVALID_RESOLVED_ENTITY, refNode.getName(), refNode.getLineNumber(),
869 refNode.getCharPosition(), refNode.getFileName()));
870 } else if (entity instanceof YangBase || entity instanceof YangIdentityRef) {
Vidyashree Ramab3670472016-08-06 15:49:56 +0530871
872 //Search if the identity has any un resolved base, if so return true, else return false.
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530873 addUnResolvedBaseToStack(refNode);
Shankara-Huawei234cd092016-07-14 11:35:34 +0530874 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530875 throw new DataModelException(getErrorMsg(
876 LINKER_ERROR, refNode.getName(), refNode.getLineNumber(),
877 refNode.getCharPosition(), refNode.getFileName()));
Bharat saraswale3175d32016-08-31 17:50:11 +0530878
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530879 }
880 }
881
882 /**
883 * Returns if there is any unresolved uses in grouping.
884 *
885 * @param node grouping/typedef node
886 */
887 private void addUnResolvedUsesToStack(YangNode node) {
888
Vidyashree Ramab3670472016-08-06 15:49:56 +0530889 //Search the grouping node's children for presence of uses node.
Vidyashree Rama72719fa2016-07-15 14:06:56 +0530890 TraversalType curTraversal = ROOT;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530891 YangNode curNode = node.getChild();
892 while (curNode != null) {
Vidyashree Rama72719fa2016-07-15 14:06:56 +0530893 if (curNode.getName().equals(node.getName())) {
894 // if we have traversed all the child nodes, then exit from loop
895 return;
896 }
897
898 // if child nodes has uses, then add it to resolution stack
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530899 if (curNode instanceof YangUses) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530900 addEntityToStack((T) curNode, node);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530901 }
Vidyashree Rama72719fa2016-07-15 14:06:56 +0530902
903 // Traversing all the child nodes of grouping
904 if (curTraversal != PARENT && curNode.getChild() != null) {
905 curTraversal = CHILD;
906 curNode = curNode.getChild();
907 } else if (curNode.getNextSibling() != null) {
908 curTraversal = SIBILING;
909 curNode = curNode.getNextSibling();
910 } else {
911 curTraversal = PARENT;
912 curNode = curNode.getParent();
913 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530914 }
915 }
916
917 /**
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530918 * Returns if there is any unresolved if-feature in feature.
919 *
920 * @param node module/submodule node
921 */
922 private void addUnResolvedIfFeatureToStack(YangNode node) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530923 YangFeature refFeature = ((YangIfFeature) getCurEntityToResolveFromStack())
924 .getReferredFeature();
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530925 List<YangIfFeature> ifFeatureList = refFeature.getIfFeatureList();
926 if (ifFeatureList != null && !ifFeatureList.isEmpty()) {
927 Iterator<YangIfFeature> ifFeatureIterator = ifFeatureList.iterator();
928 while (ifFeatureIterator.hasNext()) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530929 addEntityToStack((T) ifFeatureIterator.next(), node);
Vidyashree Rama13b4c552016-06-20 15:12:43 +0530930 }
931 }
932 }
933
934 /**
Shankara-Huawei234cd092016-07-14 11:35:34 +0530935 * Returns if there is any unresolved base in identity.
936 *
937 * @param node module/submodule node
938 */
939 private void addUnResolvedBaseToStack(YangNode node) {
940
941 YangIdentity curNode = (YangIdentity) node;
942 if (curNode.getBaseNode() != null) {
943 if (curNode.getBaseNode().getResolvableStatus() != RESOLVED) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530944 addEntityToStack((T) curNode.getBaseNode(), node);
Shankara-Huawei234cd092016-07-14 11:35:34 +0530945 }
946 }
947 }
948
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530949 private void addEntityToStack(T entity, YangNode holder) {
950 YangEntityToResolveInfoImpl<T> unResolvedEntityInfo =
951 new YangEntityToResolveInfoImpl<>();
952 unResolvedEntityInfo.setEntityToResolve(entity);
953 unResolvedEntityInfo.setHolderOfEntityToResolve(holder);
954 addInPartialResolvedStack(unResolvedEntityInfo);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530955 }
956
957 /**
958 * Sets stack of YANG type with partially resolved YANG construct hierarchy.
959 *
960 * @param partialResolvedInfo partial resolved YANG construct stack
961 */
Gaurav Agrawal58b348e2016-06-07 14:00:26 +0530962 private void addInPartialResolvedStack(YangEntityToResolveInfoImpl<T> partialResolvedInfo) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530963 partialResolvedStack.push(partialResolvedInfo);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530964 }
965
966 /**
967 * Retrieves the next entity in the stack that needs to be resolved. It is
968 * assumed that the caller ensures that the stack is not empty.
969 *
970 * @return next entity in the stack that needs to be resolved
971 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530972 private T getCurEntityToResolveFromStack() {
973 return partialResolvedStack.peek().getEntityToResolve();
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530974 }
975
Gaurav Agrawal58b348e2016-06-07 14:00:26 +0530976 @Override
977 public YangEntityToResolveInfoImpl<T> getEntityToResolveInfo() {
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530978 return entityToResolveInfo;
979 }
980
Gaurav Agrawal58b348e2016-06-07 14:00:26 +0530981 @Override
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530982 public void linkInterFile(YangReferenceResolver dataModelRootNode)
983 throws DataModelException {
984
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530985 curRefResolver = dataModelRootNode;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530986
987 // Current node to resolve, it can be a YANG type or YANG uses.
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530988 T entityToResolve = entityToResolveInfo.getEntityToResolve();
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530989
990 // Check if linking is already done
991 if (entityToResolve instanceof Resolvable) {
992 Resolvable resolvable = (Resolvable) entityToResolve;
993 if (resolvable.getResolvableStatus() == RESOLVED) {
994 return;
995 }
996 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +0530997 throw new DataModelException(UNRESOLVABLE);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +0530998 }
999
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301000 if (entityToResolve instanceof YangXPathResolver &&
1001 !(entityToResolve instanceof YangLeafRef)) {
Bharat saraswald14cbe82016-07-14 13:26:18 +05301002 //Process x-path linking.
janani bebb143d2016-07-14 19:35:22 +05301003 processXPathLinking(entityToResolve, dataModelRootNode);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301004
Bharat saraswald14cbe82016-07-14 13:26:18 +05301005 } else {
Bharat saraswald14cbe82016-07-14 13:26:18 +05301006 // Push the initial entity to resolve in stack.
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301007 addInPartialResolvedStack(entityToResolveInfo);
Bharat saraswald14cbe82016-07-14 13:26:18 +05301008 // Inter file linking and resolution.
1009 linkInterFileAndResolve();
Bharat saraswald14cbe82016-07-14 13:26:18 +05301010 addDerivedRefTypeToRefTypeResolutionList();
1011 }
1012 }
1013
1014 /**
1015 * Process x-path linking for augment and leaf-ref.
1016 *
janani bebb143d2016-07-14 19:35:22 +05301017 * @param entityToResolve entity to resolve
1018 * @param root root node
Bharat saraswald14cbe82016-07-14 13:26:18 +05301019 */
janani bebb143d2016-07-14 19:35:22 +05301020 private void processXPathLinking(T entityToResolve,
Bharat saraswal2da23bf2016-08-25 15:28:39 +05301021 YangReferenceResolver root) {
janani bebb143d2016-07-14 19:35:22 +05301022
Bharat saraswald14cbe82016-07-14 13:26:18 +05301023 YangXpathLinker<T> xPathLinker = new YangXpathLinker<T>();
janani bebb143d2016-07-14 19:35:22 +05301024
Bharat saraswald14cbe82016-07-14 13:26:18 +05301025 if (entityToResolve instanceof YangAugment) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301026 YangNode targetNode;
Bharat saraswald14cbe82016-07-14 13:26:18 +05301027 YangAugment augment = (YangAugment) entityToResolve;
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301028 targetNode = xPathLinker
1029 .processAugmentXpathLinking(augment.getTargetNode(), (YangNode) root);
Bharat saraswald14cbe82016-07-14 13:26:18 +05301030 if (targetNode != null) {
1031 if (targetNode instanceof YangAugmentableNode) {
1032 detectCollisionForAugmentedNode(targetNode, augment);
1033 ((YangAugmentableNode) targetNode).addAugmentation(augment);
1034 augment.setAugmentedNode(targetNode);
Vidyashree Ramab20ba9e2016-09-02 14:12:25 +05301035 setAugmentedFlagInAncestors(targetNode);
Bharat saraswald14cbe82016-07-14 13:26:18 +05301036 Resolvable resolvable = (Resolvable) entityToResolve;
1037 resolvable.setResolvableStatus(RESOLVED);
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301038 if (targetNode instanceof YangInput) {
1039 xPathLinker.addInModuleIfInput(augment, (YangNode) root);
1040 }
Bharat saraswald14cbe82016-07-14 13:26:18 +05301041 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301042 throw new LinkerException(getErrorMsg(
1043 INVALID_TARGET + targetNode.getNodeType(),
1044 augment.getName(), augment.getLineNumber(),
1045 augment.getCharPosition(), augment.getFileName()));
Bharat saraswald14cbe82016-07-14 13:26:18 +05301046 }
1047 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301048 throw new LinkerException(getErrorMsg(
1049 FAILED_TO_LINK, augment.getName(), augment
1050 .getLineNumber(), augment.getCharPosition(),
1051 augment.getFileName()));
Bharat saraswald14cbe82016-07-14 13:26:18 +05301052 }
Vidyashree Ramab3670472016-08-06 15:49:56 +05301053 } else if (entityToResolve instanceof YangCompilerAnnotation) {
1054 YangNode targetNode;
1055 YangCompilerAnnotation ca = (YangCompilerAnnotation) entityToResolve;
Vidyashree Ramab3670472016-08-06 15:49:56 +05301056 targetNode = xPathLinker.processAugmentXpathLinking(ca.getAtomicPathList(),
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301057 (YangNode) root);
Vidyashree Ramab3670472016-08-06 15:49:56 +05301058 if (targetNode != null) {
1059 if (targetNode instanceof YangList) {
1060 ((YangList) targetNode).setCompilerAnnotation(
1061 (YangCompilerAnnotation) entityToResolve);
1062 Resolvable resolvable = (Resolvable) entityToResolve;
1063 resolvable.setResolvableStatus(RESOLVED);
1064 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301065 throw new LinkerException(getErrorMsg(
1066 INVALID_TARGET + targetNode.getNodeType(), ca.getPath(),
1067 ca.getLineNumber(), ca.getCharPosition(), ca.getFileName()));
Vidyashree Ramab3670472016-08-06 15:49:56 +05301068 }
1069 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301070 throw new LinkerException(getErrorMsg(
1071 FAILED_TO_FIND_ANNOTATION, ca.getPath(), ca.getLineNumber(),
1072 ca.getCharPosition(), ca.getFileName()));
Vidyashree Ramab3670472016-08-06 15:49:56 +05301073 }
Bharat saraswald14cbe82016-07-14 13:26:18 +05301074 } else if (entityToResolve instanceof YangLeafRef) {
1075 YangLeafRef leafRef = (YangLeafRef) entityToResolve;
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301076 Object target = xPathLinker.processLeafRefXpathLinking(
1077 leafRef.getAtomicPath(), (YangNode) root, leafRef);
Bharat saraswald14cbe82016-07-14 13:26:18 +05301078 if (target != null) {
Bharat saraswale3175d32016-08-31 17:50:11 +05301079 YangLeaf leaf;
1080 YangLeafList leafList;
Bharat saraswald14cbe82016-07-14 13:26:18 +05301081 leafRef.setReferredLeafOrLeafList(target);
1082 if (target instanceof YangLeaf) {
1083 leaf = (YangLeaf) target;
janani bebb143d2016-07-14 19:35:22 +05301084 leafRef.setResolvableStatus(INTER_FILE_LINKED);
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301085 addUnResolvedLeafRefTypeToStack((T) leaf, entityToResolveInfo
1086 .getHolderOfEntityToResolve());
Bharat saraswald14cbe82016-07-14 13:26:18 +05301087 } else {
1088 leafList = (YangLeafList) target;
janani bebb143d2016-07-14 19:35:22 +05301089 leafRef.setResolvableStatus(INTER_FILE_LINKED);
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301090 addUnResolvedLeafRefTypeToStack(
1091 (T) leafList, entityToResolveInfo.getHolderOfEntityToResolve());
Bharat saraswald14cbe82016-07-14 13:26:18 +05301092 }
Bharat saraswald14cbe82016-07-14 13:26:18 +05301093 //TODO: add logic for leaf-ref for path predicates.
1094 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301095 LinkerException ex = new LinkerException(
1096 FAILED_TO_FIND_LEAD_INFO_HOLDER + leafRef.getPath());
1097 ex.setCharPosition(leafRef.getCharPosition());
1098 ex.setLine(leafRef.getLineNumber());
1099 ex.setFileName(leafRef.getFileName());
1100 throw ex;
Bharat saraswald14cbe82016-07-14 13:26:18 +05301101 }
1102 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301103 }
1104
1105 /**
1106 * Returns the referenced prefix of entity under resolution.
1107 *
1108 * @return referenced prefix of entity under resolution
1109 * @throws DataModelException a violation in data model rule
1110 */
VinodKumarS-Huaweid81eccb2016-06-01 14:30:22 +05301111 private String getRefPrefix()
1112 throws DataModelException {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301113 T entity = getCurEntityToResolveFromStack();
1114 if (entity instanceof YangType) {
1115 return ((YangType<?>) entity).getPrefix();
janani b0e4e8ae2016-07-13 21:06:41 +05301116 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301117 if (entity instanceof YangUses) {
1118 return ((YangUses) entity).getPrefix();
1119 }
1120 if (entity instanceof YangIfFeature) {
1121 return ((YangIfFeature) entity).getPrefix();
1122 }
1123 if (entity instanceof YangBase) {
1124 return ((YangBase) entity).getBaseIdentifier()
1125 .getPrefix();
1126 }
1127 if (entity instanceof YangIdentityRef) {
1128 return ((YangIdentityRef) entity).getPrefix();
1129 }
1130 throw new DataModelException(LINKER_ERROR);
janani b0e4e8ae2016-07-13 21:06:41 +05301131 }
1132
1133 /**
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301134 * Performs inter file linking and resolution.
1135 *
1136 * @throws DataModelException a violation in data model rule
1137 */
1138 private void linkInterFileAndResolve()
1139 throws DataModelException {
1140
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301141 while (!partialResolvedStack.isEmpty()) {
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301142
1143 // Current node to resolve, it can be a YANG type or YANG uses.
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301144 T entityToResolve = getCurEntityToResolveFromStack();
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301145 // Check if linking is already done
1146 if (entityToResolve instanceof Resolvable) {
1147
1148 Resolvable resolvable = (Resolvable) entityToResolve;
1149 switch (resolvable.getResolvableStatus()) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301150 case RESOLVED:
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301151 /*
1152 * If the entity is already resolved in the stack, then pop
1153 * it and continue with the remaining stack elements to
1154 * resolve
1155 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301156 partialResolvedStack.pop();
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301157 break;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301158
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301159 case INTER_FILE_LINKED:
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301160 /*
1161 * If the top of the stack is already linked then resolve
1162 * the references and pop the entity and continue with
1163 * remaining stack elements to resolve
1164 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301165 resolveTopOfStack();
1166 partialResolvedStack.pop();
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301167 break;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301168
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301169 case INTRA_FILE_RESOLVED:
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301170 /*
1171 * If the top of the stack is intra file resolved then check
1172 * if top of stack is linked, if not link it using
1173 * import/include list and push the linked referred entity
1174 * to the stack, otherwise only push it to the stack.
1175 */
1176 linkInterFileTopOfStackRefUpdateStack();
1177 break;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301178
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301179 case UNDEFINED:
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301180 /*
1181 * In case of if-feature resolution, if referred "feature" is not
1182 * defined then the resolvable status will be undefined.
1183 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301184 partialResolvedStack.pop();
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301185 break;
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301186
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301187 default:
1188 throw new DataModelException(INVALID_LINKER_STATE);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301189 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301190 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301191 throw new DataModelException(INVALID_RESOLVED_ENTITY);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301192 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301193 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301194 }
1195
1196 /**
1197 * Links the top of the stack if it's inter-file and update stack.
1198 *
1199 * @throws DataModelException data model error
1200 */
VinodKumarS-Huaweid81eccb2016-06-01 14:30:22 +05301201 private void linkInterFileTopOfStackRefUpdateStack()
1202 throws DataModelException {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301203 T entity = getCurEntityToResolveFromStack();
1204 if (entity instanceof YangLeafRef) {
janani bebb143d2016-07-14 19:35:22 +05301205 // When leafref path comes with relative path, it will be converted to absolute path.
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301206 setAbsolutePathFromRelativePathInLeafref(entity);
1207 processXPathLinking(entity, curRefResolver);
janani bebb143d2016-07-14 19:35:22 +05301208 return;
1209 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301210 /*
1211 * Obtain the referred node of top of stack entity under resolution
1212 */
1213 T referredNode = getRefNode();
1214
1215 /*
1216 * Check for null for scenario when it's not linked and inter-file
1217 * linking is required.
1218 */
1219 if (referredNode == null) {
1220
1221 /*
Bharat saraswalc2d3be12016-06-16 00:29:12 +05301222 * Check if prefix is null or not, to identify whether to search in
1223 * import list or include list.
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301224 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301225 if (getRefPrefix() != null && !getRefPrefix()
1226 .contentEquals(curRefResolver.getPrefix())) {
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301227 if (resolveWithImport()) {
1228 return;
1229 }
1230 } else {
1231 if (resolveWithInclude()) {
1232 return;
1233 }
1234 }
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301235
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301236 if (entity instanceof YangIfFeature) {
1237 ((YangIfFeature) entity).setResolvableStatus(UNDEFINED);
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301238 return;
1239 }
janani b0e4e8ae2016-07-13 21:06:41 +05301240 // If current entity is still not resolved, then
1241 // linking/resolution has failed.
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301242
1243 DataModelException ex = new DataModelException(
1244 getErrorInfoForLinker(entity));
1245 ex.setLine(getLineNumber());
1246 ex.setCharPosition(getCharPosition());
1247 throw ex;
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301248 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301249 ((Resolvable) entity).setResolvableStatus(INTER_FILE_LINKED);
janani bebb143d2016-07-14 19:35:22 +05301250 addUnresolvedRecursiveReferenceToStack((YangNode) referredNode);
1251 }
1252 }
1253
1254 /**
1255 * Sets the leafref with absolute path from the relative path.
1256 *
1257 * @param resolutionInfo information about the YANG construct which has to be resolved
1258 * @throws DataModelException a violation of data model rules
1259 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301260 private void setAbsolutePathFromRelativePathInLeafref(T resolutionInfo)
VinodKumarS-Huawei423dc9a2016-08-17 22:08:42 +05301261 throws DataModelException {
janani bebb143d2016-07-14 19:35:22 +05301262 if (resolutionInfo instanceof YangLeafRef) {
1263
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301264 YangNode leafParent = ((YangLeafRef) resolutionInfo)
1265 .getParentNodeOfLeafref();
janani bebb143d2016-07-14 19:35:22 +05301266 YangLeafRef leafref = (YangLeafRef) resolutionInfo;
1267
1268 // Checks if the leafref has relative path in it.
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301269 if (leafref.getPathType() == RELATIVE_PATH) {
janani bebb143d2016-07-14 19:35:22 +05301270 YangRelativePath relativePath = leafref.getRelativePath();
1271 List<YangAtomicPath> absoluteInRelative = relativePath.getAtomicPathList();
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301272 int ancestorCount = relativePath.getAncestorNodeCount();
janani bebb143d2016-07-14 19:35:22 +05301273
1274 // Gets the root node from the ancestor count.
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301275 T nodeOrAugmentList =
1276 getRootNodeWithAncestorCountForLeafref(ancestorCount, leafParent,
1277 leafref);
janani bebb143d2016-07-14 19:35:22 +05301278 if (nodeOrAugmentList instanceof YangNode) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301279 StringBuilder name = new StringBuilder();
1280 StringBuilder prefix = new StringBuilder();
janani bebb143d2016-07-14 19:35:22 +05301281 YangNode rootNode = (YangNode) nodeOrAugmentList;
1282 // Forms a new absolute path from the relative path
1283 while (!(rootNode instanceof YangReferenceResolver)) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301284 name.append(rootNode.getName());
1285 prefix.append(SLASH_FOR_STRING).append(name.reverse());
1286 name.delete(0, name.length());
janani bebb143d2016-07-14 19:35:22 +05301287 rootNode = rootNode.getParent();
1288 if (rootNode == null) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301289 throw new DataModelException(INVALID_TREE);
janani bebb143d2016-07-14 19:35:22 +05301290 }
1291 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301292 prefix.reverse();
1293 fillAbsolutePathValuesInLeafref(leafref, prefix.toString(),
1294 absoluteInRelative);
janani bebb143d2016-07-14 19:35:22 +05301295 } else {
1296 List<String> listOfAugment = (List<String>) nodeOrAugmentList;
1297 Iterator<String> listOfAugmentIterator = listOfAugment.listIterator();
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301298 StringBuilder augment = new StringBuilder(EMPTY_STRING);
janani bebb143d2016-07-14 19:35:22 +05301299 while (listOfAugmentIterator.hasNext()) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301300 augment.append(SLASH_FOR_STRING)
1301 .append(listOfAugmentIterator.next());
janani bebb143d2016-07-14 19:35:22 +05301302 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301303 fillAbsolutePathValuesInLeafref(leafref, augment.toString(),
1304 absoluteInRelative);
janani b0e4e8ae2016-07-13 21:06:41 +05301305 }
janani b0e4e8ae2016-07-13 21:06:41 +05301306 }
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301307 }
1308 }
1309
1310 /**
janani bebb143d2016-07-14 19:35:22 +05301311 * Fills the absolute path values in the leafref from relative path.
1312 *
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301313 * @param leafref instance of YANG leafref
1314 * @param path path name which has to be prefixed to relative path
1315 * @param relative atomic paths in relative
janani bebb143d2016-07-14 19:35:22 +05301316 * @throws DataModelException a violation of data model rules
1317 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301318 private void fillAbsolutePathValuesInLeafref(YangLeafRef leafref, String path,
1319 List<YangAtomicPath> relative)
VinodKumarS-Huawei423dc9a2016-08-17 22:08:42 +05301320 throws DataModelException {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301321 leafref.setPathType(ABSOLUTE_PATH);
janani bebb143d2016-07-14 19:35:22 +05301322 String[] pathName = new String[0];
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301323 if (path != null && !path.equals(EMPTY_STRING)) {
1324 pathName = path.split(SLASH_FOR_STRING);
janani bebb143d2016-07-14 19:35:22 +05301325 }
1326 List<YangAtomicPath> finalListForAbsolute = new LinkedList<>();
1327 for (String value : pathName) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301328 if (value != null && !value.isEmpty() && !value.equals(EMPTY_STRING)) {
1329 YangNodeIdentifier nodeId = getValidNodeIdentifier(value, PATH_DATA);
janani bebb143d2016-07-14 19:35:22 +05301330 YangAtomicPath atomicPath = new YangAtomicPath();
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301331 atomicPath.setNodeIdentifier(nodeId);
janani bebb143d2016-07-14 19:35:22 +05301332 finalListForAbsolute.add(atomicPath);
1333 }
1334 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301335 if (relative != null && !relative.isEmpty()) {
1336 Iterator<YangAtomicPath> pathIt = relative.listIterator();
1337 while (pathIt.hasNext()) {
1338 YangAtomicPath yangAtomicPath = pathIt.next();
janani bebb143d2016-07-14 19:35:22 +05301339 finalListForAbsolute.add(yangAtomicPath);
1340 }
1341 leafref.setAtomicPath(finalListForAbsolute);
1342 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301343 DataModelException ex = new DataModelException(getLeafRefErrorInfo(leafref));
1344 ex.setCharPosition(leafref.getCharPosition());
1345 ex.setLine(leafref.getLineNumber());
1346 ex.setFileName(leafref.getFileName());
1347 throw ex;
janani bebb143d2016-07-14 19:35:22 +05301348 }
1349 }
1350
1351 /**
1352 * Returns the root parent with respect to the ancestor count from leafref.
1353 *
1354 * @param ancestorCount count of node where parent node can be reached
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301355 * @param curParent current parent node
janani bebb143d2016-07-14 19:35:22 +05301356 * @param leafref instance of YANG leafref
1357 * @return node where the ancestor count stops or augment path name list
1358 * @throws DataModelException a violation of data model rules
1359 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301360 private T getRootNodeWithAncestorCountForLeafref(
1361 int ancestorCount, YangNode curParent, YangLeafRef leafref)
janani bebb143d2016-07-14 19:35:22 +05301362 throws DataModelException {
1363
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301364 int curParentCount = 1;
1365 curParent = skipInvalidDataNodes(curParent, leafref);
1366 if (curParent instanceof YangAugment) {
1367 YangAugment augment = (YangAugment) curParent;
1368 List<String> valueInAugment = getPathWithAugment(augment,
1369 ancestorCount - curParentCount);
janani bebb143d2016-07-14 19:35:22 +05301370 return (T) valueInAugment;
1371 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301372 while (curParentCount < ancestorCount) {
1373 YangNode currentSkippedParent = skipInvalidDataNodes(curParent, leafref);
1374 if (currentSkippedParent == curParent) {
1375 if (curParent.getParent() == null) {
1376 throw new DataModelException(getLeafRefErrorInfo(leafref));
janani bebb143d2016-07-14 19:35:22 +05301377 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301378 curParent = curParent.getParent();
janani bebb143d2016-07-14 19:35:22 +05301379 } else {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301380 curParent = currentSkippedParent;
janani bebb143d2016-07-14 19:35:22 +05301381 continue;
1382 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301383 curParentCount = curParentCount + 1;
1384 if (curParent instanceof YangAugment) {
1385 YangAugment augment = (YangAugment) curParent;
1386 List<String> valueInAugment = getPathWithAugment(
1387 augment, ancestorCount - curParentCount);
janani bebb143d2016-07-14 19:35:22 +05301388 return (T) valueInAugment;
1389 }
1390 }
1391 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301392 return (T) curParent;
janani bebb143d2016-07-14 19:35:22 +05301393 }
1394
1395 /**
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301396 * Finds and resolves with include list.
1397 *
1398 * @return true if resolved, false otherwise
1399 * @throws DataModelException a violation in data model rule
1400 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301401 private boolean resolveWithInclude() throws DataModelException {
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301402 /*
1403 * Run through all the nodes in include list and search for referred
1404 * typedef/grouping at the root level.
1405 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301406 for (YangInclude yangInclude : curRefResolver.getIncludeList()) {
1407 YangNode linkedNode = getLinkedNode(yangInclude.getIncludedNode());
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301408 if (linkedNode != null) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301409 return addUnResolvedRefToStack(linkedNode);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301410 }
1411 }
1412 // If referred node can't be found return false.
1413 return false;
1414 }
1415
1416 /**
1417 * Finds and resolves with import list.
1418 *
1419 * @return true if resolved, false otherwise
1420 * @throws DataModelException a violation in data model rule
1421 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301422 private boolean resolveWithImport() throws DataModelException {
Vidyashree Ramab3670472016-08-06 15:49:56 +05301423
1424 // Run through import list to find the referred typedef/grouping.
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301425 for (YangImport yangImport : curRefResolver.getImportList()) {
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301426 /*
1427 * Match the prefix attached to entity under resolution with the
1428 * imported/included module/sub-module's prefix. If found, search
1429 * for the referred typedef/grouping at the root level.
1430 */
1431 if (yangImport.getPrefixId().contentEquals(getRefPrefix())) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301432 YangNode linkedNode = getLinkedNode(yangImport.getImportedNode());
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301433 if (linkedNode != null) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301434 return addUnResolvedRefToStack(linkedNode);
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301435 }
1436 /*
1437 * If referred node can't be found at root level break for loop,
1438 * and return false.
1439 */
1440 break;
1441 }
1442 }
1443 // If referred node can't be found return false.
1444 return false;
1445 }
1446
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301447 //Add unresolved constructs to stack.
1448 private boolean addUnResolvedRefToStack(YangNode linkedNode)
1449 throws DataModelException {
1450 // Add the link to external entity.
1451 addReferredEntityLink(linkedNode, INTER_FILE_LINKED);
1452
1453 // Add the type/uses of referred typedef/grouping to the stack.
1454 addUnresolvedRecursiveReferenceToStack(linkedNode);
1455 return true;
1456 }
1457
1458 //Returns linked node from entity of stack.
1459 private YangNode getLinkedNode(YangNode node) {
1460 T entity = getCurEntityToResolveFromStack();
1461 if (entity instanceof YangType) {
1462 return findRefTypedef(node);
1463 }
1464 if (entity instanceof YangUses) {
1465 return findRefGrouping(node);
1466 }
1467 if (entity instanceof YangIfFeature) {
1468 return findRefFeature(node);
1469 }
1470 if (entity instanceof YangBase) {
1471 return findRefIdentity(node);
1472 }
1473 if (entity instanceof YangIdentityRef) {
1474 return findRefIdentityRef(node);
1475 }
1476 return null;
1477 }
1478
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301479 /**
1480 * Returns referred typedef/grouping node.
1481 *
1482 * @return referred typedef/grouping node
1483 * @throws DataModelException a violation in data model rule
1484 */
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301485 private T getRefNode() throws DataModelException {
1486 T entity = getCurEntityToResolveFromStack();
1487 if (entity instanceof YangType) {
1488 YangDerivedInfo<?> derivedInfo = (YangDerivedInfo<?>)
1489 ((YangType<?>) entity).getDataTypeExtendedInfo();
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301490 return (T) derivedInfo.getReferredTypeDef();
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301491 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301492 if (entity instanceof YangUses) {
1493 return (T) ((YangUses) entity).getRefGroup();
1494 }
1495 if (entity instanceof YangIfFeature) {
1496 return (T) ((YangIfFeature) entity).getReferredFeatureHolder();
1497 }
1498 if (entity instanceof YangLeafRef) {
1499 return (T) ((YangLeafRef) entity).getReferredLeafOrLeafList();
1500 }
1501 if (entity instanceof YangBase) {
1502 return (T) ((YangBase) entity).getReferredIdentity();
1503 }
1504 if (entity instanceof YangIdentityRef) {
1505 return (T) ((YangIdentityRef) entity).getReferredIdentity();
1506 }
1507 throw new DataModelException(LINKER_ERROR);
1508
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301509 }
1510
1511 /**
1512 * Finds the referred grouping node at the root level of imported/included node.
1513 *
1514 * @param refNode module/sub-module node
1515 * @return referred grouping
1516 */
1517 private YangNode findRefGrouping(YangNode refNode) {
1518 YangNode tmpNode = refNode.getChild();
1519 while (tmpNode != null) {
1520 if (tmpNode instanceof YangGrouping) {
1521 if (tmpNode.getName()
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301522 .equals(((YangUses) getCurEntityToResolveFromStack())
1523 .getName())) {
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301524 return tmpNode;
1525 }
1526 }
1527 tmpNode = tmpNode.getNextSibling();
1528 }
1529 return null;
1530 }
1531
1532 /**
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301533 * Finds the referred feature node at the root level of imported/included node.
1534 *
1535 * @param refNode module/sub-module node
1536 * @return referred feature
1537 */
1538 private YangNode findRefFeature(YangNode refNode) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301539 T entity = getCurEntityToResolveFromStack();
1540 YangNodeIdentifier ifFeature = ((YangIfFeature) entity).getName();
1541 List<YangFeature> featureList = ((YangFeatureHolder) refNode)
1542 .getFeatureList();
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301543 if (featureList != null && !featureList.isEmpty()) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301544 for (YangFeature feature : featureList) {
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301545 if (ifFeature.getName().equals(feature.getName())) {
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301546 ((YangIfFeature) entity).setReferredFeature(feature);
Vidyashree Rama13b4c552016-06-20 15:12:43 +05301547 return refNode;
1548 }
1549 }
1550 }
1551 return null;
1552 }
1553
1554 /**
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301555 * Finds the referred typedef node at the root level of imported/included node.
1556 *
1557 * @param refNode module/sub-module node
1558 * @return referred typedef
1559 */
1560 private YangNode findRefTypedef(YangNode refNode) {
1561 YangNode tmpNode = refNode.getChild();
1562 while (tmpNode != null) {
1563 if (tmpNode instanceof YangTypeDef) {
1564 if (tmpNode.getName()
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301565 .equals(((YangType) getCurEntityToResolveFromStack())
1566 .getDataTypeName())) {
Gaurav Agrawalab7c4bd2016-05-17 18:06:38 +05301567 return tmpNode;
1568 }
1569 }
1570 tmpNode = tmpNode.getNextSibling();
1571 }
1572 return null;
1573 }
Shankara-Huawei234cd092016-07-14 11:35:34 +05301574
1575 /**
1576 * Finds the referred identity node at the root level of imported/included node.
1577 *
1578 * @param refNode module/sub-module node
1579 * @return referred identity
1580 */
1581 private YangNode findRefIdentity(YangNode refNode) {
1582 YangNode tmpNode = refNode.getChild();
1583 while (tmpNode != null) {
1584 if (tmpNode instanceof YangIdentity) {
1585 if (tmpNode.getName()
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301586 .equals(((YangBase) getCurEntityToResolveFromStack())
1587 .getBaseIdentifier().getName())) {
Shankara-Huawei234cd092016-07-14 11:35:34 +05301588 return tmpNode;
1589 }
1590 }
1591 tmpNode = tmpNode.getNextSibling();
1592 }
1593 return null;
1594 }
1595
1596 /**
1597 * Finds the referred identity node at the root level of imported/included node.
1598 *
1599 * @param refNode module/sub-module node
1600 * @return referred identity
1601 */
1602 private YangNode findRefIdentityRef(YangNode refNode) {
1603 YangNode tmpNode = refNode.getChild();
1604 while (tmpNode != null) {
1605 if (tmpNode instanceof YangIdentity) {
1606 if (tmpNode.getName()
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301607 .equals(((YangIdentityRef) getCurEntityToResolveFromStack())
1608 .getBaseIdentity().getName())) {
Shankara-Huawei234cd092016-07-14 11:35:34 +05301609 return tmpNode;
1610 }
1611 }
1612 tmpNode = tmpNode.getNextSibling();
1613 }
1614 return null;
1615 }
Bharat saraswal2da23bf2016-08-25 15:28:39 +05301616
Vidyashree Ramab20ba9e2016-09-02 14:12:25 +05301617 /**
1618 * Sets descendant node augmented flag in ancestors.
1619 *
1620 * @param targetNode augmented YANG node
1621 */
1622 private void setAugmentedFlagInAncestors(YangNode targetNode) {
1623 targetNode = targetNode.getParent();
1624 while (targetNode != null) {
1625 targetNode.setDescendantNodeAugmented(true);
1626 targetNode = targetNode.getParent();
1627 }
1628 }
Bharat saraswal9fab16b2016-09-23 23:27:24 +05301629}