1 /* 2 * Copyright (C) 2015, The Android Open Source Project 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 17 #include "ast_java.h" 18 19 #include "code_writer.h" 20 #include "type_java.h" 21 22 using std::vector; 23 using std::string; 24 25 namespace android { 26 namespace aidl { 27 namespace java { 28 29 void WriteModifiers(CodeWriter* to, int mod, int mask) { 30 int m = mod & mask; 31 32 if (m & OVERRIDE) { 33 to->Write("@Override "); 34 } 35 36 if ((m & SCOPE_MASK) == PUBLIC) { 37 to->Write("public "); 38 } else if ((m & SCOPE_MASK) == PRIVATE) { 39 to->Write("private "); 40 } else if ((m & SCOPE_MASK) == PROTECTED) { 41 to->Write("protected "); 42 } 43 44 if (m & STATIC) { 45 to->Write("static "); 46 } 47 48 if (m & FINAL) { 49 to->Write("final "); 50 } 51 52 if (m & ABSTRACT) { 53 to->Write("abstract "); 54 } 55 } 56 57 void WriteArgumentList(CodeWriter* to, const vector<Expression*>& arguments) { 58 size_t N = arguments.size(); 59 for (size_t i = 0; i < N; i++) { 60 arguments[i]->Write(to); 61 if (i != N - 1) { 62 to->Write(", "); 63 } 64 } 65 } 66 67 Field::Field(int m, Variable* v) : ClassElement(), modifiers(m), variable(v) {} 68 69 void Field::Write(CodeWriter* to) const { 70 if (this->comment.length() != 0) { 71 to->Write("%s\n", this->comment.c_str()); 72 } 73 WriteModifiers(to, this->modifiers, SCOPE_MASK | STATIC | FINAL | OVERRIDE); 74 to->Write("%s %s", this->variable->type->JavaType().c_str(), 75 this->variable->name.c_str()); 76 if (this->value.length() != 0) { 77 to->Write(" = %s", this->value.c_str()); 78 } 79 to->Write(";\n"); 80 } 81 82 LiteralExpression::LiteralExpression(const string& v) : value(v) {} 83 84 void LiteralExpression::Write(CodeWriter* to) const { 85 to->Write("%s", this->value.c_str()); 86 } 87 88 StringLiteralExpression::StringLiteralExpression(const string& v) : value(v) {} 89 90 void StringLiteralExpression::Write(CodeWriter* to) const { 91 to->Write("\"%s\"", this->value.c_str()); 92 } 93 94 Variable::Variable(const Type* t, const string& n) 95 : type(t), name(n), dimension(0) {} 96 97 Variable::Variable(const Type* t, const string& n, int d) 98 : type(t), name(n), dimension(d) {} 99 100 void Variable::WriteDeclaration(CodeWriter* to) const { 101 string dim; 102 for (int i = 0; i < this->dimension; i++) { 103 dim += "[]"; 104 } 105 to->Write("%s%s %s", this->type->JavaType().c_str(), dim.c_str(), 106 this->name.c_str()); 107 } 108 109 void Variable::Write(CodeWriter* to) const { to->Write("%s", name.c_str()); } 110 111 FieldVariable::FieldVariable(Expression* o, const string& n) 112 : object(o), clazz(NULL), name(n) {} 113 114 FieldVariable::FieldVariable(const Type* c, const string& n) 115 : object(NULL), clazz(c), name(n) {} 116 117 void FieldVariable::Write(CodeWriter* to) const { 118 if (this->object != NULL) { 119 this->object->Write(to); 120 } else if (this->clazz != NULL) { 121 to->Write("%s", this->clazz->JavaType().c_str()); 122 } 123 to->Write(".%s", name.c_str()); 124 } 125 126 void StatementBlock::Write(CodeWriter* to) const { 127 to->Write("{\n"); 128 int N = this->statements.size(); 129 for (int i = 0; i < N; i++) { 130 this->statements[i]->Write(to); 131 } 132 to->Write("}\n"); 133 } 134 135 void StatementBlock::Add(Statement* statement) { 136 this->statements.push_back(statement); 137 } 138 139 void StatementBlock::Add(Expression* expression) { 140 this->statements.push_back(new ExpressionStatement(expression)); 141 } 142 143 ExpressionStatement::ExpressionStatement(Expression* e) : expression(e) {} 144 145 void ExpressionStatement::Write(CodeWriter* to) const { 146 this->expression->Write(to); 147 to->Write(";\n"); 148 } 149 150 Assignment::Assignment(Variable* l, Expression* r) 151 : lvalue(l), rvalue(r), cast(NULL) {} 152 153 Assignment::Assignment(Variable* l, Expression* r, const Type* c) 154 : lvalue(l), rvalue(r), cast(c) {} 155 156 void Assignment::Write(CodeWriter* to) const { 157 this->lvalue->Write(to); 158 to->Write(" = "); 159 if (this->cast != NULL) { 160 to->Write("(%s)", this->cast->JavaType().c_str()); 161 } 162 this->rvalue->Write(to); 163 } 164 165 MethodCall::MethodCall(const string& n) : name(n) {} 166 167 MethodCall::MethodCall(const string& n, int argc = 0, ...) : name(n) { 168 va_list args; 169 va_start(args, argc); 170 init(argc, args); 171 va_end(args); 172 } 173 174 MethodCall::MethodCall(Expression* o, const string& n) : obj(o), name(n) {} 175 176 MethodCall::MethodCall(const Type* t, const string& n) : clazz(t), name(n) {} 177 178 MethodCall::MethodCall(Expression* o, const string& n, int argc = 0, ...) 179 : obj(o), name(n) { 180 va_list args; 181 va_start(args, argc); 182 init(argc, args); 183 va_end(args); 184 } 185 186 MethodCall::MethodCall(const Type* t, const string& n, int argc = 0, ...) 187 : clazz(t), name(n) { 188 va_list args; 189 va_start(args, argc); 190 init(argc, args); 191 va_end(args); 192 } 193 194 void MethodCall::init(int n, va_list args) { 195 for (int i = 0; i < n; i++) { 196 Expression* expression = (Expression*)va_arg(args, void*); 197 this->arguments.push_back(expression); 198 } 199 } 200 201 void MethodCall::Write(CodeWriter* to) const { 202 if (this->obj != NULL) { 203 this->obj->Write(to); 204 to->Write("."); 205 } else if (this->clazz != NULL) { 206 to->Write("%s.", this->clazz->JavaType().c_str()); 207 } 208 to->Write("%s(", this->name.c_str()); 209 WriteArgumentList(to, this->arguments); 210 to->Write(")"); 211 } 212 213 Comparison::Comparison(Expression* l, const string& o, Expression* r) 214 : lvalue(l), op(o), rvalue(r) {} 215 216 void Comparison::Write(CodeWriter* to) const { 217 to->Write("("); 218 this->lvalue->Write(to); 219 to->Write("%s", this->op.c_str()); 220 this->rvalue->Write(to); 221 to->Write(")"); 222 } 223 224 NewExpression::NewExpression(const Type* t) : type(t) {} 225 226 NewExpression::NewExpression(const Type* t, int argc = 0, ...) : type(t) { 227 va_list args; 228 va_start(args, argc); 229 init(argc, args); 230 va_end(args); 231 } 232 233 void NewExpression::init(int n, va_list args) { 234 for (int i = 0; i < n; i++) { 235 Expression* expression = (Expression*)va_arg(args, void*); 236 this->arguments.push_back(expression); 237 } 238 } 239 240 void NewExpression::Write(CodeWriter* to) const { 241 to->Write("new %s(", this->type->InstantiableName().c_str()); 242 WriteArgumentList(to, this->arguments); 243 to->Write(")"); 244 } 245 246 NewArrayExpression::NewArrayExpression(const Type* t, Expression* s) 247 : type(t), size(s) {} 248 249 void NewArrayExpression::Write(CodeWriter* to) const { 250 to->Write("new %s[", this->type->JavaType().c_str()); 251 size->Write(to); 252 to->Write("]"); 253 } 254 255 Ternary::Ternary(Expression* a, Expression* b, Expression* c) 256 : condition(a), ifpart(b), elsepart(c) {} 257 258 void Ternary::Write(CodeWriter* to) const { 259 to->Write("(("); 260 this->condition->Write(to); 261 to->Write(")?("); 262 this->ifpart->Write(to); 263 to->Write("):("); 264 this->elsepart->Write(to); 265 to->Write("))"); 266 } 267 268 Cast::Cast(const Type* t, Expression* e) : type(t), expression(e) {} 269 270 void Cast::Write(CodeWriter* to) const { 271 to->Write("((%s)", this->type->JavaType().c_str()); 272 expression->Write(to); 273 to->Write(")"); 274 } 275 276 VariableDeclaration::VariableDeclaration(Variable* l, Expression* r, 277 const Type* c) 278 : lvalue(l), cast(c), rvalue(r) {} 279 280 VariableDeclaration::VariableDeclaration(Variable* l) : lvalue(l) {} 281 282 void VariableDeclaration::Write(CodeWriter* to) const { 283 this->lvalue->WriteDeclaration(to); 284 if (this->rvalue != NULL) { 285 to->Write(" = "); 286 if (this->cast != NULL) { 287 to->Write("(%s)", this->cast->JavaType().c_str()); 288 } 289 this->rvalue->Write(to); 290 } 291 to->Write(";\n"); 292 } 293 294 void IfStatement::Write(CodeWriter* to) const { 295 if (this->expression != NULL) { 296 to->Write("if ("); 297 this->expression->Write(to); 298 to->Write(") "); 299 } 300 this->statements->Write(to); 301 if (this->elseif != NULL) { 302 to->Write("else "); 303 this->elseif->Write(to); 304 } 305 } 306 307 ReturnStatement::ReturnStatement(Expression* e) : expression(e) {} 308 309 void ReturnStatement::Write(CodeWriter* to) const { 310 to->Write("return "); 311 this->expression->Write(to); 312 to->Write(";\n"); 313 } 314 315 void TryStatement::Write(CodeWriter* to) const { 316 to->Write("try "); 317 this->statements->Write(to); 318 } 319 320 CatchStatement::CatchStatement(Variable* e) 321 : statements(new StatementBlock), exception(e) {} 322 323 void CatchStatement::Write(CodeWriter* to) const { 324 to->Write("catch "); 325 if (this->exception != NULL) { 326 to->Write("("); 327 this->exception->WriteDeclaration(to); 328 to->Write(") "); 329 } 330 this->statements->Write(to); 331 } 332 333 void FinallyStatement::Write(CodeWriter* to) const { 334 to->Write("finally "); 335 this->statements->Write(to); 336 } 337 338 Case::Case(const string& c) { cases.push_back(c); } 339 340 void Case::Write(CodeWriter* to) const { 341 int N = this->cases.size(); 342 if (N > 0) { 343 for (int i = 0; i < N; i++) { 344 string s = this->cases[i]; 345 if (s.length() != 0) { 346 to->Write("case %s:\n", s.c_str()); 347 } else { 348 to->Write("default:\n"); 349 } 350 } 351 } else { 352 to->Write("default:\n"); 353 } 354 statements->Write(to); 355 } 356 357 SwitchStatement::SwitchStatement(Expression* e) : expression(e) {} 358 359 void SwitchStatement::Write(CodeWriter* to) const { 360 to->Write("switch ("); 361 this->expression->Write(to); 362 to->Write(")\n{\n"); 363 int N = this->cases.size(); 364 for (int i = 0; i < N; i++) { 365 this->cases[i]->Write(to); 366 } 367 to->Write("}\n"); 368 } 369 370 void Break::Write(CodeWriter* to) const { to->Write("break;\n"); } 371 372 void Method::Write(CodeWriter* to) const { 373 size_t N, i; 374 375 if (this->comment.length() != 0) { 376 to->Write("%s\n", this->comment.c_str()); 377 } 378 379 WriteModifiers(to, this->modifiers, 380 SCOPE_MASK | STATIC | ABSTRACT | FINAL | OVERRIDE); 381 382 if (this->returnType != NULL) { 383 string dim; 384 for (i = 0; i < this->returnTypeDimension; i++) { 385 dim += "[]"; 386 } 387 to->Write("%s%s ", this->returnType->JavaType().c_str(), dim.c_str()); 388 } 389 390 to->Write("%s(", this->name.c_str()); 391 392 N = this->parameters.size(); 393 for (i = 0; i < N; i++) { 394 this->parameters[i]->WriteDeclaration(to); 395 if (i != N - 1) { 396 to->Write(", "); 397 } 398 } 399 400 to->Write(")"); 401 402 N = this->exceptions.size(); 403 for (i = 0; i < N; i++) { 404 if (i == 0) { 405 to->Write(" throws "); 406 } else { 407 to->Write(", "); 408 } 409 to->Write("%s", this->exceptions[i]->JavaType().c_str()); 410 } 411 412 if (this->statements == NULL) { 413 to->Write(";\n"); 414 } else { 415 to->Write("\n"); 416 this->statements->Write(to); 417 } 418 } 419 420 void IntConstant::Write(CodeWriter* to) const { 421 WriteModifiers(to, STATIC | FINAL | PUBLIC, ALL_MODIFIERS); 422 to->Write("int %s = %d;\n", name.c_str(), value); 423 } 424 425 void StringConstant::Write(CodeWriter* to) const { 426 WriteModifiers(to, STATIC | FINAL | PUBLIC, ALL_MODIFIERS); 427 to->Write("String %s = %s;\n", name.c_str(), value.c_str()); 428 } 429 430 void Class::Write(CodeWriter* to) const { 431 size_t N, i; 432 433 if (this->comment.length() != 0) { 434 to->Write("%s\n", this->comment.c_str()); 435 } 436 437 WriteModifiers(to, this->modifiers, ALL_MODIFIERS); 438 439 if (this->what == Class::CLASS) { 440 to->Write("class "); 441 } else { 442 to->Write("interface "); 443 } 444 445 string name = this->type->JavaType(); 446 size_t pos = name.rfind('.'); 447 if (pos != string::npos) { 448 name = name.c_str() + pos + 1; 449 } 450 451 to->Write("%s", name.c_str()); 452 453 if (this->extends != NULL) { 454 to->Write(" extends %s", this->extends->JavaType().c_str()); 455 } 456 457 N = this->interfaces.size(); 458 if (N != 0) { 459 if (this->what == Class::CLASS) { 460 to->Write(" implements"); 461 } else { 462 to->Write(" extends"); 463 } 464 for (i = 0; i < N; i++) { 465 to->Write(" %s", this->interfaces[i]->JavaType().c_str()); 466 } 467 } 468 469 to->Write("\n"); 470 to->Write("{\n"); 471 472 N = this->elements.size(); 473 for (i = 0; i < N; i++) { 474 this->elements[i]->Write(to); 475 } 476 477 to->Write("}\n"); 478 } 479 480 static string escape_backslashes(const string& str) { 481 string result; 482 const size_t I = str.length(); 483 for (size_t i = 0; i < I; i++) { 484 char c = str[i]; 485 if (c == '\\') { 486 result += "\\\\"; 487 } else { 488 result += c; 489 } 490 } 491 return result; 492 } 493 494 Document::Document(const std::string& comment, 495 const std::string& package, 496 const std::string& original_src, 497 std::unique_ptr<Class> clazz) 498 : comment_(comment), 499 package_(package), 500 original_src_(original_src), 501 clazz_(std::move(clazz)) { 502 } 503 504 void Document::Write(CodeWriter* to) const { 505 if (!comment_.empty()) { 506 to->Write("%s\n", comment_.c_str()); 507 } 508 to->Write( 509 "/*\n" 510 " * This file is auto-generated. DO NOT MODIFY.\n" 511 " * Original file: %s\n" 512 " */\n", 513 escape_backslashes(original_src_).c_str()); 514 if (!package_.empty()) { 515 to->Write("package %s;\n", package_.c_str()); 516 } 517 518 if (clazz_) { 519 clazz_->Write(to); 520 } 521 } 522 523 } // namespace java 524 } // namespace aidl 525 } // namespace android 526