blob: 3b4ae431e17b53fc2124b858ad5773b78d942ead [file] [log] [blame]
Vidyashree Rama0b920732016-03-29 09:52:22 +05301/*
Brian O'Connor5ab426f2016-04-09 01:19:45 -07002 * Copyright 2016-present Open Networking Laboratory
Vidyashree Rama0b920732016-03-29 09:52:22 +05303 *
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.parser.impl.listeners;
18
Mahesh Poojary Huawei46fb4db2016-07-14 12:38:17 +053019import org.onosproject.yangutils.datamodel.YangDecimal64;
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +053020import org.onosproject.yangutils.datamodel.YangDerivedInfo;
Vidyashree Ramaa2f73982016-04-12 23:33:33 +053021import org.onosproject.yangutils.datamodel.YangRangeRestriction;
22import org.onosproject.yangutils.datamodel.YangType;
Gaurav Agrawal95b416c2016-06-07 14:00:26 +053023import org.onosproject.yangutils.datamodel.exceptions.DataModelException;
Bharat saraswal96dfef02016-06-16 00:29:12 +053024import org.onosproject.yangutils.datamodel.utils.Parsable;
Vidyashree Rama0b920732016-03-29 09:52:22 +053025import org.onosproject.yangutils.parser.antlrgencode.GeneratedYangParser;
26import org.onosproject.yangutils.parser.exceptions.ParserException;
27import org.onosproject.yangutils.parser.impl.TreeWalkListener;
28
Mahesh Poojary Huawei46fb4db2016-07-14 12:38:17 +053029import static org.onosproject.yangutils.datamodel.utils.builtindatatype.YangDataTypes.DECIMAL64;
Gaurav Agrawal72cd1b72016-06-30 13:28:14 +053030import static org.onosproject.yangutils.datamodel.utils.builtindatatype.YangDataTypes.DERIVED;
31import static org.onosproject.yangutils.datamodel.utils.builtindatatype.YangDataTypeUtils.isOfRangeRestrictedType;
Gaurav Agrawal95b416c2016-06-07 14:00:26 +053032import static org.onosproject.yangutils.datamodel.utils.RestrictionResolver.processRangeRestriction;
Bharat saraswal96dfef02016-06-16 00:29:12 +053033import static org.onosproject.yangutils.datamodel.utils.YangConstructType.RANGE_DATA;
34import static org.onosproject.yangutils.datamodel.utils.YangConstructType.TYPE_DATA;
Vidyashree Rama0b920732016-03-29 09:52:22 +053035import static org.onosproject.yangutils.parser.impl.parserutils.ListenerErrorLocation.ENTRY;
Vidyashree Rama1db15562016-05-17 16:16:15 +053036import static org.onosproject.yangutils.parser.impl.parserutils.ListenerErrorLocation.EXIT;
Vidyashree Rama0b920732016-03-29 09:52:22 +053037import static org.onosproject.yangutils.parser.impl.parserutils.ListenerErrorMessageConstruction.constructListenerErrorMessage;
38import static org.onosproject.yangutils.parser.impl.parserutils.ListenerErrorType.INVALID_HOLDER;
Vidyashree Rama1db15562016-05-17 16:16:15 +053039import static org.onosproject.yangutils.parser.impl.parserutils.ListenerErrorType.MISSING_CURRENT_HOLDER;
Vidyashree Rama0b920732016-03-29 09:52:22 +053040import static org.onosproject.yangutils.parser.impl.parserutils.ListenerErrorType.MISSING_HOLDER;
Vidyashree Ramaa2f73982016-04-12 23:33:33 +053041import static org.onosproject.yangutils.parser.impl.parserutils.ListenerValidation.checkStackIsNotEmpty;
Vidyashree Rama0b920732016-03-29 09:52:22 +053042
43/*
44 * Reference: RFC6020 and YANG ANTLR Grammar
45 *
46 * ABNF grammar as per RFC6020
47 * range-stmt = range-keyword sep range-arg-str optsep
48 * (";" /
49 * "{" stmtsep
50 * ;; these stmts can appear in any order
51 * [error-message-stmt stmtsep]
52 * [error-app-tag-stmt stmtsep]
53 * [description-stmt stmtsep]
54 * [reference-stmt stmtsep]
55 * "}")
56 *
57 * ANTLR grammar rule
58 * rangeStatement : RANGE_KEYWORD range (STMTEND | LEFT_CURLY_BRACE commonStatements RIGHT_CURLY_BRACE);
59 */
60
61/**
Bharat saraswald9822e92016-04-05 15:13:44 +053062 * Represents listener based call back function corresponding to the "range"
Vidyashree Rama0b920732016-03-29 09:52:22 +053063 * rule defined in ANTLR grammar file for corresponding ABNF rule in RFC 6020.
64 */
65public final class RangeRestrictionListener {
66
Vidyashree Rama0b920732016-03-29 09:52:22 +053067 /**
68 * Creates a new range restriction listener.
69 */
70 private RangeRestrictionListener() {
71 }
72
73 /**
74 * It is called when parser receives an input matching the grammar
75 * rule (range), performs validation and updates the data model
76 * tree.
77 *
Vidyashree Ramaa2f73982016-04-12 23:33:33 +053078 * @param listener listener's object
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +053079 * @param ctx context object of the grammar rule
Vidyashree Rama0b920732016-03-29 09:52:22 +053080 */
81 public static void processRangeRestrictionEntry(TreeWalkListener listener,
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +053082 GeneratedYangParser.RangeStatementContext ctx) {
Vidyashree Rama0b920732016-03-29 09:52:22 +053083
84 // Check for stack to be non empty.
85 checkStackIsNotEmpty(listener, MISSING_HOLDER, RANGE_DATA, ctx.range().getText(), ENTRY);
86
87 Parsable tmpData = listener.getParsedDataStack().peek();
88 if (tmpData.getYangConstructType() == TYPE_DATA) {
89 YangType type = (YangType) tmpData;
Vidyashree Rama1db15562016-05-17 16:16:15 +053090 setRangeRestriction(listener, type, ctx);
Vidyashree Rama0b920732016-03-29 09:52:22 +053091 } else {
92 throw new ParserException(constructListenerErrorMessage(INVALID_HOLDER, RANGE_DATA,
93 ctx.range().getText(), ENTRY));
94 }
95 }
96
97 /**
98 * Sets the range restriction to type.
99 *
Vidyashree Rama1db15562016-05-17 16:16:15 +0530100 * @param listener listener's object
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530101 * @param type YANG type for which range restriction to be added
102 * @param ctx context object of the grammar rule
Vidyashree Rama0b920732016-03-29 09:52:22 +0530103 */
Vidyashree Rama1db15562016-05-17 16:16:15 +0530104 private static void setRangeRestriction(TreeWalkListener listener, YangType type,
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530105 GeneratedYangParser.RangeStatementContext ctx) {
Vidyashree Ramaa2f73982016-04-12 23:33:33 +0530106
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530107 if (type.getDataType() == DERIVED) {
108 ((YangDerivedInfo<YangRangeRestriction>) type.getDataTypeExtendedInfo())
109 .setRangeRestrictionString(ctx.range().getText());
110 ((YangDerivedInfo<YangRangeRestriction>) type.getDataTypeExtendedInfo())
111 .setLineNumber(ctx.getStart().getLine());
112 ((YangDerivedInfo<YangRangeRestriction>) type.getDataTypeExtendedInfo())
113 .setCharPosition(ctx.getStart().getCharPositionInLine());
114 return;
Vidyashree Rama0b920732016-03-29 09:52:22 +0530115 }
116
Mahesh Poojary Huawei46fb4db2016-07-14 12:38:17 +0530117 if (!(isOfRangeRestrictedType(type.getDataType())) && (type.getDataType() != DECIMAL64)) {
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530118 ParserException parserException = new ParserException("YANG file error: Range restriction can't be " +
119 "applied to a given type");
120 parserException.setLine(ctx.getStart().getLine());
121 parserException.setCharPosition(ctx.getStart().getCharPositionInLine());
122 throw parserException;
123 }
124
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530125 YangRangeRestriction rangeRestriction = null;
126 try {
Mahesh Poojary Huawei46fb4db2016-07-14 12:38:17 +0530127 if (type.getDataType() == DECIMAL64) {
128 YangDecimal64 yangDecimal64 = (YangDecimal64) type.getDataTypeExtendedInfo();
129 rangeRestriction = processRangeRestriction(yangDecimal64.getDefaultRangeRestriction(),
130 ctx.getStart().getLine(),
131 ctx.getStart().getCharPositionInLine(),
132 true, ctx.range().getText(), type.getDataType());
133 } else {
134 rangeRestriction = processRangeRestriction(null, ctx.getStart().getLine(),
135 ctx.getStart().getCharPositionInLine(),
136 false, ctx.range().getText(), type.getDataType());
137 }
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530138 } catch (DataModelException e) {
139 ParserException parserException = new ParserException(e.getMessage());
140 parserException.setCharPosition(e.getCharPositionInLine());
141 parserException.setLine(e.getLineNumber());
142 throw parserException;
143 }
Gaurav Agrawalcfa1c412016-05-03 00:41:48 +0530144
Vidyashree Rama0b920732016-03-29 09:52:22 +0530145 if (rangeRestriction != null) {
Mahesh Poojary Huawei46fb4db2016-07-14 12:38:17 +0530146 if (type.getDataType() == DECIMAL64) {
147 ((YangDecimal64<YangRangeRestriction>) type.getDataTypeExtendedInfo())
148 .setRangeRestrictedExtendedInfo(rangeRestriction);
149 } else {
150 type.setDataTypeExtendedInfo(rangeRestriction);
151 }
Vidyashree Rama0b920732016-03-29 09:52:22 +0530152 }
Vidyashree Rama1db15562016-05-17 16:16:15 +0530153 listener.getParsedDataStack().push(rangeRestriction);
154 }
155
156 /**
157 * Performs validation and updates the data model tree.
158 * It is called when parser exits from grammar rule (range).
159 *
160 * @param listener listener's object
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530161 * @param ctx context object of the grammar rule
Vidyashree Rama1db15562016-05-17 16:16:15 +0530162 */
163 public static void processRangeRestrictionExit(TreeWalkListener listener,
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530164 GeneratedYangParser.RangeStatementContext ctx) {
Vidyashree Rama1db15562016-05-17 16:16:15 +0530165
166 // Check for stack to be non empty.
167 checkStackIsNotEmpty(listener, MISSING_HOLDER, RANGE_DATA, ctx.range().getText(), EXIT);
168
169 Parsable tmpData = listener.getParsedDataStack().peek();
170 if (tmpData instanceof YangRangeRestriction) {
171 listener.getParsedDataStack().pop();
172 } else if (tmpData instanceof YangType
173 && ((YangType) tmpData).getDataType() == DERIVED) {
174 // TODO : need to handle in linker
175 } else {
176 throw new ParserException(constructListenerErrorMessage(MISSING_CURRENT_HOLDER, RANGE_DATA,
177 ctx.range().getText(), EXIT));
178 }
Vidyashree Rama0b920732016-03-29 09:52:22 +0530179 }
Gaurav Agrawal95b416c2016-06-07 14:00:26 +0530180}