bump product version to 6.4.0.3
[LibreOffice.git] / idlc / source / errorhandler.cxx
blobb31340ef5ee890b76ff091f1286d5f41a8735867
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #include <errorhandler.hxx>
21 #include <astinterface.hxx>
23 static const sal_Char* errorCodeToMessage(ErrorCode eCode)
25 switch (eCode)
27 case ErrorCode::SyntaxError:
28 return "";
29 case ErrorCode::RedefScope:
30 return "illegal redefinition in scope ";
31 case ErrorCode::CoercionFailure:
32 return "coercion failure ";
33 case ErrorCode::ScopeConflict:
34 return "definition scope is different than fwd declare scope, ";
35 case ErrorCode::IllegalAdd:
36 return "illegal add operation, ";
37 case ErrorCode::IllegalRaises:
38 return "non-exception type in raises(..) clause, ";
39 case ErrorCode::CantInherit:
40 return "cannot inherit ";
41 case ErrorCode::IdentNotFound:
42 return "error in lookup of symbol: ";
43 case ErrorCode::CannotInheritFromForward:
44 return "";
45 case ErrorCode::ExpectedConstant:
46 return "constant expected: ";
47 case ErrorCode::Eval:
48 return "expression evaluation error: ";
49 case ErrorCode::ForwardDeclLookup:
50 return "";
51 case ErrorCode::RecursiveType:
52 return "illegal recursive use of type: ";
53 case ErrorCode::NotAType:
54 return "specified symbol is not a type: ";
55 case ErrorCode::InterfaceMemberLookup:
56 return "error in lookup of symbol, expected interface is not defined and no forward exists: ";
57 case ErrorCode::ServiceMemberLookup:
58 return "error in lookup of symbol, expected service is not defined: ";
59 case ErrorCode::DefinedAttributeFlag:
60 return "flag is already set: ";
61 case ErrorCode::WrongAttributeKeyword:
62 return "keyword not allowed: ";
63 case ErrorCode::MissingAttributeKeyword:
64 return "missing keyword: ";
65 case ErrorCode::BadAttributeFlags:
66 return
67 "the 'attribute' flag is mandatory, and only the 'bound' and"
68 " 'readonly' optional flags are accepted: ";
69 case ErrorCode::ExpectedOptional:
70 return "only the 'optional' flag is accepted: ";
71 case ErrorCode::MixedInheritance:
72 return "interface inheritance declarations cannot appear in both an"
73 " interface's header and its body";
74 case ErrorCode::DoubleInheritance:
75 return
76 "interface is (directly or indirectly) inherited more than once: ";
77 case ErrorCode::DoubleMember:
78 return
79 "member is (directly or indirectly) declared more than once: ";
80 case ErrorCode::ConstructorParameterNotIn:
81 return
82 "a service constructor parameter may not be an out or inout"
83 " parameter";
84 case ErrorCode::ConstructorRestParameterNotFirst:
85 return
86 "no parameters may precede a rest parameter in a service"
87 " constructor";
88 case ErrorCode::RestParameterNotLast:
89 return "no parameters may follow a rest parameter";
90 case ErrorCode::RestParameterNotAny:
91 return "a rest parameter must be of type any";
92 case ErrorCode::MethodHasRestParameter:
93 return "a rest parameter may not be used on an interface method";
94 case ErrorCode::ReadOnlyAttributeSetExceptions:
95 return "a readonly attribute may not have a setter raises clause";
96 case ErrorCode::UnsignedTypeArgument:
97 return "an unsigned type cannot be used as a type argument";
98 case ErrorCode::WrongNumberOfTypeArguments:
99 return
100 "the number of given type arguments does not match the expected"
101 " number of type parameters";
102 case ErrorCode::InstantiatedStructTypeTypedef:
103 return
104 "an instantiated polymorphic struct type cannot be used in a"
105 " typedef";
106 case ErrorCode::IdenticalTypeParameters:
107 return "two type parameters have the same name";
108 case ErrorCode::StructTypeTemplateWithBase:
109 return "a polymorphic struct type template may not have a base type";
110 case ErrorCode::PublishedForward:
111 return
112 "a published forward declaration of an interface type cannot be"
113 " followed by an unpublished declaration of that type";
114 case ErrorCode::PublishedusesUnpublished:
115 return
116 "an unpublished entity cannot be used in the declaration of a"
117 " published entity: ";
118 case ErrorCode::SimilarConstructors:
119 return "two constructors have identical lists of parameter types";
121 return "unknown error";
124 static const sal_Char* warningCodeToMessage(WarningCode wCode)
126 switch (wCode)
128 case WarningCode::WrongNamingConvention:
129 return "type or identifier doesn't fulfill the UNO naming convention: ";
131 return "unknown warning";
134 static const sal_Char* parseStateToMessage(ParseState state)
136 switch (state)
138 case PS_NoState:
139 return "Statement can not be parsed";
140 case PS_TypeDeclSeen:
141 return "Malformed type declaration";
142 case PS_ConstantDeclSeen:
143 return "Malformed const declaration";
144 case PS_ExceptionDeclSeen:
145 return "Malformed exception declaration";
146 case PS_InterfaceDeclSeen:
147 return "Malformed interface declaration";
148 case PS_ServiceDeclSeen:
149 return "Malformed service declaration";
150 case PS_ModuleDeclSeen:
151 return "Malformed module declaration";
152 case PS_AttributeDeclSeen:
153 return "Malformed attribute declaration";
154 case PS_PropertyDeclSeen:
155 return "Malformed property declaration";
156 case PS_OperationDeclSeen:
157 return "Malformed operation declaration";
158 case PS_InterfaceInheritanceDeclSeen:
159 return "Malformed interface inheritance declaration";
160 case PS_ConstantsDeclSeen:
161 return "Malformed constants declaration";
162 case PS_ServiceSeen:
163 return "Missing service identifier following SERVICE keyword";
164 case PS_ServiceIDSeen:
165 return "Missing '{' or illegal syntax following service identifier";
166 case PS_ServiceSqSeen:
167 return "Illegal syntax following service '{' opener";
168 case PS_ServiceBodySeen:
169 return "Illegal syntax following service '}' closer";
170 case PS_ServiceMemberSeen:
171 return "Illegal syntax following service member declaration";
172 case PS_ServiceIFHeadSeen:
173 return "Illegal syntax following header of an interface member";
174 case PS_ServiceSHeadSeen:
175 return "Illegal syntax following header of a service member";
176 case PS_ModuleSeen:
177 return "Missing module identifier following MODULE keyword";
178 case PS_ModuleIDSeen:
179 return "Missing '{' or illegal syntax following module identifier";
180 case PS_ModuleSqSeen:
181 return "Illegal syntax following module '{' opener";
182 case PS_ModuleQsSeen:
183 return "Illegal syntax following module '}' closer";
184 case PS_ModuleBodySeen:
185 return "Illegal syntax following module export(s)";
186 case PS_ConstantsSeen:
187 return "Missing constants identifier following CONSTANTS keyword";
188 case PS_ConstantsIDSeen:
189 return "Missing '{' or illegal syntax following constants identifier";
190 case PS_ConstantsSqSeen:
191 return "Illegal syntax following module '{' opener";
192 case PS_ConstantsQsSeen:
193 return "Illegal syntax following module '}' closer";
194 case PS_ConstantsBodySeen:
195 return "Illegal syntax following constants export(s)";
196 case PS_InterfaceSeen:
197 return "Missing interface identifier following INTERFACE keyword";
198 case PS_InterfaceIDSeen:
199 return "Illegal syntax following interface identifier";
200 case PS_InterfaceHeadSeen:
201 return "Illegal syntax following interface head";
202 case PS_InheritSpecSeen:
203 return "Missing '{' or illegal syntax following inheritance spec";
204 case PS_ForwardDeclSeen:
205 return "Missing ';' following forward interface declaration";
206 case PS_InterfaceSqSeen:
207 return "Illegal syntax following interface '{' opener";
208 case PS_InterfaceQsSeen:
209 return "Illegal syntax following interface '}' closer";
210 case PS_InterfaceBodySeen:
211 return "Illegal syntax following interface export(s)";
212 case PS_InheritColonSeen:
213 return "Illegal syntax following ':' starting inheritance list";
214 case PS_SNListCommaSeen:
215 return "Found illegal scoped name in scoped name list";
216 case PS_ScopedNameSeen:
217 return "Missing ',' following scoped name in scoped name list";
218 case PS_SN_IDSeen:
219 return "Illegal component in scoped name";
220 case PS_ScopeDelimSeen:
221 return "Illegal component in scoped name following '::'";
222 case PS_ConstSeen:
223 return "Missing type or illegal syntax following CONST keyword";
224 case PS_ConstTypeSeen:
225 return "Missing identifier or illegal syntax following const type";
226 case PS_ConstIDSeen:
227 return "Missing '=' or illegal syntax after const identifier";
228 case PS_ConstAssignSeen:
229 return "Missing value expr or illegal syntax following '='";
230 case PS_ConstExprSeen:
231 return "Missing ';' or illegal syntax following value expr in const";
232 case PS_TypedefSeen:
233 return "Missing type or illegal syntax following TYPEDEF keyword";
234 case PS_TypeSpecSeen:
235 return "Missing declarators or illegal syntax following type spec";
236 case PS_DeclaratorsSeen:
237 return "Illegal syntax following declarators in TYPEDEF declaration";
238 case PS_StructSeen:
239 return "Missing struct identifier following STRUCT keyword";
240 case PS_StructHeaderSeen:
241 return "Missing '{' or illegal syntax following struct inheritance spec";
242 case PS_StructIDSeen:
243 return "Missing '{' or illegal syntax following struct identifier";
244 case PS_StructSqSeen:
245 return "Illegal syntax following struct '{' opener";
246 case PS_StructQsSeen:
247 return "Illegal syntax following struct '}' closer";
248 case PS_StructBodySeen:
249 return "Illegal syntax following struct member(s)";
250 case PS_MemberTypeSeen:
251 return "Illegal syntax or missing identifier following member type";
252 case PS_MemberDeclsSeen:
253 return "Illegal syntax following member declarator(s)";
254 case PS_MemberDeclsCompleted:
255 return "Missing ',' between member decls of same type(?)";
256 case PS_EnumSeen:
257 return "Illegal syntax or missing identifier following ENUM keyword";
258 case PS_EnumIDSeen:
259 return "Illegal syntax or missing '{' following enum identifier";
260 case PS_EnumSqSeen:
261 return "Illegal syntax following enum '{' opener";
262 case PS_EnumQsSeen:
263 return "Illegal syntax following enum '}' closer";
264 case PS_EnumBodySeen:
265 return "Illegal syntax following enum enumerator(s)";
266 case PS_EnumCommaSeen:
267 return "Illegal syntax or missing identifier following ',' in enum";
268 case PS_SequenceSeen:
269 return "Illegal syntax or missing '<' following SEQUENCE keyword";
270 case PS_SequenceSqSeen:
271 return "Illegal syntax or missing type following '<' in sequence";
272 case PS_SequenceQsSeen:
273 return "Illegal syntax following '>' in sequence";
274 case PS_SequenceTypeSeen:
275 return "Illegal syntax following sequence type declaration";
276 case PS_FlagHeaderSeen:
277 return "Illegal syntax after flags";
278 case PS_AttrSeen:
279 return "Illegal syntax after ATTRIBUTE keyword";
280 case PS_AttrTypeSeen:
281 return "Illegal syntax after type in attribute declaration";
282 case PS_AttrCompleted:
283 return "Illegal syntax after attribute declaration";
284 case PS_ReadOnlySeen:
285 return "Illegal syntax after READONLY keyword";
286 case PS_OptionalSeen:
287 return "Illegal syntax after OPTIONAL keyword";
288 case PS_MayBeVoidSeen:
289 return "Illegal syntax after MAYBEVOID keyword";
290 case PS_BoundSeen:
291 return "Illegal syntax after BOUND keyword";
292 case PS_ConstrainedSeen:
293 return "Illegal syntax after CONSTRAINED keyword";
294 case PS_TransientSeen:
295 return "Illegal syntax after TRANSIENT keyword";
296 case PS_MayBeAmbigiousSeen:
297 return "Illegal syntax after MAYBEAMBIGIOUS keyword";
298 case PS_MayBeDefaultSeen:
299 return "Illegal syntax after MAYBEDEFAULT keyword";
300 case PS_RemoveableSeen:
301 return "Illegal syntax after REMOVABLE keyword";
302 case PS_PropertySeen:
303 return "Illegal syntax after PROPERTY keyword";
304 case PS_PropertyTypeSeen:
305 return "Illegal syntax after type in property declaration";
306 case PS_PropertyCompleted:
307 return "Illegal syntax after property declaration";
308 case PS_ExceptSeen:
309 return "Illegal syntax or missing identifier after EXCEPTION keyword";
310 case PS_ExceptHeaderSeen:
311 return "Missing '{' or illegal syntax following exception inheritance spec";
312 case PS_ExceptIDSeen:
313 return "Illegal syntax or missing '{' after exception identifier";
314 case PS_ExceptSqSeen:
315 return "Illegal syntax after exception '{' opener";
316 case PS_ExceptQsSeen:
317 return "Illegal syntax after exception '}' closer";
318 case PS_ExceptBodySeen:
319 return "Illegal syntax after exception member(s)";
320 case PS_OpTypeSeen:
321 return "Illegal syntax or missing identifier after operation type";
322 case PS_OpIDSeen:
323 return "Illegal syntax or missing '(' after operation identifier";
324 case PS_OpParsCompleted:
325 return "Illegal syntax after operation parameter list";
326 case PS_OpSqSeen:
327 return "Illegal syntax after operation parameter list '(' opener";
328 case PS_OpQsSeen:
329 return "Illegal syntax after operation parameter list ')' closer";
330 case PS_OpParCommaSeen:
331 return "Illegal syntax or missing direction in parameter declaration";
332 case PS_OpParDirSeen:
333 return "Illegal syntax or missing type in parameter declaration";
334 case PS_OpParTypeSeen:
335 return "Illegal syntax or missing declarator in parameter declaration";
336 case PS_OpParDeclSeen:
337 return "Illegal syntax following parameter declarator";
338 case PS_RaiseSeen:
339 return "Illegal syntax or missing '(' after RAISES keyword";
340 case PS_RaiseSqSeen:
341 return "Illegal syntax after RAISES '(' opener";
342 case PS_RaiseQsSeen:
343 return "Illegal syntax after RAISES ')' closer";
344 case PS_DeclsCommaSeen:
345 return "Illegal syntax after ',' in declarators list";
346 case PS_DeclsDeclSeen:
347 return "Illegal syntax after declarator in declarators list";
348 default:
349 return "no wider described syntax error";
353 static OString flagToString(sal_uInt32 flag)
355 OString flagStr;
356 if ( (flag & AF_READONLY) == AF_READONLY )
357 flagStr += "'readonly'";
358 if ( (flag & AF_OPTIONAL) == AF_OPTIONAL )
359 flagStr += "'optional'";
360 if ( (flag & AF_MAYBEVOID) == AF_MAYBEVOID )
361 flagStr += "'maybevoid'";
362 if ( (flag & AF_BOUND) == AF_BOUND )
363 flagStr += "'bound'";
364 if ( (flag & AF_CONSTRAINED) == AF_CONSTRAINED )
365 flagStr += "'constrained'";
366 if ( (flag & AF_TRANSIENT) == AF_TRANSIENT )
367 flagStr += "'transient'";
368 if ( (flag & AF_MAYBEAMBIGUOUS) == AF_MAYBEAMBIGUOUS )
369 flagStr += "'maybeambiguous'";
370 if ( (flag & AF_MAYBEDEFAULT) == AF_MAYBEDEFAULT )
371 flagStr += "'maybedefault'";
372 if ( (flag & AF_REMOVABLE) == AF_REMOVABLE )
373 flagStr += "'removable'";
374 if ( (flag & AF_ATTRIBUTE) == AF_ATTRIBUTE )
375 flagStr += "'attribute'";
376 if ( (flag & AF_PROPERTY) == AF_PROPERTY )
377 flagStr += "'property'";
378 if ( flagStr.isEmpty() )
379 flagStr += "'unknown'";
381 return flagStr;
384 static void errorHeader(ErrorCode eCode, sal_Int32 lineNumber, sal_uInt32 start, sal_uInt32 end)
386 OString file;
387 if ( idlc()->getFileName() == idlc()->getRealFileName() )
388 file = idlc()->getMainFileName();
389 else
390 file = idlc()->getFileName();
392 fprintf(stderr, "%s:%lu [%lu:%lu] : %s", file.getStr(),
393 sal::static_int_cast< unsigned long >(lineNumber),
394 sal::static_int_cast< unsigned long >(start),
395 sal::static_int_cast< unsigned long >(end),
396 errorCodeToMessage(eCode));
399 static void errorHeader(ErrorCode eCode, sal_uInt32 lineNumber)
401 errorHeader(eCode, lineNumber,
402 idlc()->getOffsetStart(), idlc()->getOffsetEnd());
405 static void errorHeader(ErrorCode eCode)
407 errorHeader(eCode, idlc()->getLineNumber(),
408 idlc()->getOffsetStart(), idlc()->getOffsetEnd());
411 static void warningHeader(WarningCode wCode)
413 OString file;
414 if ( idlc()->getFileName() == idlc()->getRealFileName() )
415 file = idlc()->getMainFileName();
416 else
417 file = idlc()->getFileName();
419 fprintf(stderr, "%s(%lu) : WARNING, %s", file.getStr(),
420 sal::static_int_cast< unsigned long >(idlc()->getLineNumber()),
421 warningCodeToMessage(wCode));
424 void ErrorHandler::error0(ErrorCode e)
426 errorHeader(e);
427 fprintf(stderr, "\n");
428 idlc()->incErrorCount();
431 void ErrorHandler::error1(ErrorCode e, AstDeclaration const * d)
433 errorHeader(e);
434 fprintf(stderr, "'%s'\n", d->getScopedName().getStr());
435 idlc()->incErrorCount();
438 void ErrorHandler::error2(
439 ErrorCode e, AstDeclaration const * d1, AstDeclaration const * d2)
441 errorHeader(e);
442 fprintf(stderr, "'%s', '%s'\n", d1->getScopedName().getStr(),
443 d2->getScopedName().getStr());
444 idlc()->incErrorCount();
447 void ErrorHandler::error3(ErrorCode e, AstDeclaration const * d1, AstDeclaration const * d2, AstDeclaration const * d3)
449 errorHeader(e);
450 fprintf(stderr, "'%s', '%s', '%s'\n", d1->getScopedName().getStr(),
451 d2->getScopedName().getStr(), d3->getScopedName().getStr());
452 idlc()->incErrorCount();
455 void ErrorHandler::warning0(WarningCode w, const sal_Char* warningmsg)
457 if ( idlc()->getOptions()->isValid("-w") || idlc()->getOptions()->isValid("-we") ) {
458 warningHeader(w);
459 fprintf(stderr, "%s\n", warningmsg);
462 if ( idlc()->getOptions()->isValid("-we") )
463 idlc()->incErrorCount();
464 else
465 idlc()->incWarningCount();
468 void ErrorHandler::syntaxError(ParseState ps, sal_Int32 lineNumber, const sal_Char* errmsg)
470 errorHeader(ErrorCode::SyntaxError, lineNumber);
471 fprintf(stderr, "%s: %s\n", parseStateToMessage(ps), errmsg);
472 idlc()->incErrorCount();
475 void ErrorHandler::coercionError(AstExpression *pExpr, ExprType et)
477 errorHeader(ErrorCode::CoercionFailure);
478 fprintf(stderr, "'%s' to '%s'\n", pExpr->toString().getStr(),
479 exprTypeToString(et));
480 idlc()->incErrorCount();
483 void ErrorHandler::lookupError(const OString& n)
485 errorHeader(ErrorCode::IdentNotFound);
486 fprintf(stderr, "'%s'\n", n.getStr());
487 idlc()->incErrorCount();
490 void ErrorHandler::lookupError(ErrorCode e, const OString& n, AstDeclaration const * pScope)
492 errorHeader(e);
493 fprintf(stderr, "'%s' in '%s'\n", n.getStr(), pScope->getFullName().getStr());
494 idlc()->incErrorCount();
497 void ErrorHandler::flagError(ErrorCode e, sal_uInt32 flag)
499 errorHeader(e);
500 fprintf(stderr, "'%s'\n", flagToString(flag).getStr());
501 idlc()->incErrorCount();
504 void ErrorHandler::noTypeError(AstDeclaration const * pDecl)
506 errorHeader(ErrorCode::NotAType);
507 fprintf(stderr, "'%s'\n", pDecl->getScopedName().getStr());
508 idlc()->incErrorCount();
511 namespace {
513 char const * nodeTypeName(NodeType nodeType) {
514 switch (nodeType) {
515 case NT_interface:
516 return "interface";
518 case NT_exception:
519 return "exception";
521 case NT_struct:
522 return "struct";
524 default:
525 return "";
531 void ErrorHandler::inheritanceError(NodeType nodeType, const OString* name, AstDeclaration const * pDecl)
533 if ( nodeType == NT_interface &&
534 (pDecl->getNodeType() == NT_interface) &&
535 !(static_cast<AstInterface const *>(pDecl)->isDefined()) )
537 errorHeader(ErrorCode::CannotInheritFromForward);
538 fprintf(stderr, "interface '%s' cannot inherit from forward declared interface '%s'\n",
539 name->getStr(), pDecl->getScopedName().getStr());
540 } else
542 errorHeader(ErrorCode::CantInherit);
543 fprintf(stderr, "%s '%s' from '%s'\n",
544 nodeTypeName(nodeType), name->getStr(),
545 pDecl->getScopedName().getStr());
547 idlc()->incErrorCount();
550 void ErrorHandler::forwardLookupError(const AstDeclaration* pForward,
551 const OString& name)
553 errorHeader(ErrorCode::ForwardDeclLookup);
554 fprintf(stderr, "trying to look up '%s' in undefined forward declared interface '%s'\n",
555 pForward->getScopedName().getStr(), name.getStr());
556 idlc()->incErrorCount();
559 void ErrorHandler::constantExpected(AstDeclaration const * pDecl,
560 const OString& name)
562 errorHeader(ErrorCode::ExpectedConstant);
563 fprintf(stderr, "'%s' is bound to '%s'\n", name.getStr(), pDecl->getScopedName().getStr());
564 idlc()->incErrorCount();
567 void ErrorHandler::evalError(AstExpression* pExpr)
569 errorHeader(ErrorCode::Eval);
570 fprintf(stderr, "'%s'\n", pExpr->toString().getStr());
571 idlc()->incErrorCount();
574 bool ErrorHandler::checkPublished(AstDeclaration const * decl, bool bOptional) {
575 if (idlc()->isPublished() && !decl->isPublished() && !bOptional) {
576 error1(ErrorCode::PublishedusesUnpublished, decl);
577 return false;
578 } else {
579 return true;
583 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */