Merge "Remove the aidl tool"
This commit is contained in:
@@ -1,912 +0,0 @@
|
||||
#include "AST.h"
|
||||
#include "Type.h"
|
||||
|
||||
void
|
||||
WriteModifiers(FILE* to, int mod, int mask)
|
||||
{
|
||||
int m = mod & mask;
|
||||
|
||||
if (m & OVERRIDE) {
|
||||
fprintf(to, "@Override ");
|
||||
}
|
||||
|
||||
if ((m & SCOPE_MASK) == PUBLIC) {
|
||||
fprintf(to, "public ");
|
||||
}
|
||||
else if ((m & SCOPE_MASK) == PRIVATE) {
|
||||
fprintf(to, "private ");
|
||||
}
|
||||
else if ((m & SCOPE_MASK) == PROTECTED) {
|
||||
fprintf(to, "protected ");
|
||||
}
|
||||
|
||||
if (m & STATIC) {
|
||||
fprintf(to, "static ");
|
||||
}
|
||||
|
||||
if (m & FINAL) {
|
||||
fprintf(to, "final ");
|
||||
}
|
||||
|
||||
if (m & ABSTRACT) {
|
||||
fprintf(to, "abstract ");
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
WriteArgumentList(FILE* to, const vector<Expression*>& arguments)
|
||||
{
|
||||
size_t N = arguments.size();
|
||||
for (size_t i=0; i<N; i++) {
|
||||
arguments[i]->Write(to);
|
||||
if (i != N-1) {
|
||||
fprintf(to, ", ");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ClassElement::ClassElement()
|
||||
{
|
||||
}
|
||||
|
||||
ClassElement::~ClassElement()
|
||||
{
|
||||
}
|
||||
|
||||
Field::Field()
|
||||
:ClassElement(),
|
||||
modifiers(0),
|
||||
variable(NULL)
|
||||
{
|
||||
}
|
||||
|
||||
Field::Field(int m, Variable* v)
|
||||
:ClassElement(),
|
||||
modifiers(m),
|
||||
variable(v)
|
||||
{
|
||||
}
|
||||
|
||||
Field::~Field()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
Field::GatherTypes(set<Type*>* types) const
|
||||
{
|
||||
types->insert(this->variable->type);
|
||||
}
|
||||
|
||||
void
|
||||
Field::Write(FILE* to)
|
||||
{
|
||||
if (this->comment.length() != 0) {
|
||||
fprintf(to, "%s\n", this->comment.c_str());
|
||||
}
|
||||
WriteModifiers(to, this->modifiers, SCOPE_MASK | STATIC | FINAL | OVERRIDE);
|
||||
fprintf(to, "%s %s", this->variable->type->QualifiedName().c_str(),
|
||||
this->variable->name.c_str());
|
||||
if (this->value.length() != 0) {
|
||||
fprintf(to, " = %s", this->value.c_str());
|
||||
}
|
||||
fprintf(to, ";\n");
|
||||
}
|
||||
|
||||
Expression::~Expression()
|
||||
{
|
||||
}
|
||||
|
||||
LiteralExpression::LiteralExpression(const string& v)
|
||||
:value(v)
|
||||
{
|
||||
}
|
||||
|
||||
LiteralExpression::~LiteralExpression()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
LiteralExpression::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "%s", this->value.c_str());
|
||||
}
|
||||
|
||||
StringLiteralExpression::StringLiteralExpression(const string& v)
|
||||
:value(v)
|
||||
{
|
||||
}
|
||||
|
||||
StringLiteralExpression::~StringLiteralExpression()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
StringLiteralExpression::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "\"%s\"", this->value.c_str());
|
||||
}
|
||||
|
||||
Variable::Variable()
|
||||
:type(NULL),
|
||||
name(),
|
||||
dimension(0)
|
||||
{
|
||||
}
|
||||
|
||||
Variable::Variable(Type* t, const string& n)
|
||||
:type(t),
|
||||
name(n),
|
||||
dimension(0)
|
||||
{
|
||||
}
|
||||
|
||||
Variable::Variable(Type* t, const string& n, int d)
|
||||
:type(t),
|
||||
name(n),
|
||||
dimension(d)
|
||||
{
|
||||
}
|
||||
|
||||
Variable::~Variable()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
Variable::GatherTypes(set<Type*>* types) const
|
||||
{
|
||||
types->insert(this->type);
|
||||
}
|
||||
|
||||
void
|
||||
Variable::WriteDeclaration(FILE* to)
|
||||
{
|
||||
string dim;
|
||||
for (int i=0; i<this->dimension; i++) {
|
||||
dim += "[]";
|
||||
}
|
||||
fprintf(to, "%s%s %s", this->type->QualifiedName().c_str(), dim.c_str(),
|
||||
this->name.c_str());
|
||||
}
|
||||
|
||||
void
|
||||
Variable::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "%s", name.c_str());
|
||||
}
|
||||
|
||||
FieldVariable::FieldVariable(Expression* o, const string& n)
|
||||
:object(o),
|
||||
clazz(NULL),
|
||||
name(n)
|
||||
{
|
||||
}
|
||||
|
||||
FieldVariable::FieldVariable(Type* c, const string& n)
|
||||
:object(NULL),
|
||||
clazz(c),
|
||||
name(n)
|
||||
{
|
||||
}
|
||||
|
||||
FieldVariable::~FieldVariable()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
FieldVariable::Write(FILE* to)
|
||||
{
|
||||
if (this->object != NULL) {
|
||||
this->object->Write(to);
|
||||
}
|
||||
else if (this->clazz != NULL) {
|
||||
fprintf(to, "%s", this->clazz->QualifiedName().c_str());
|
||||
}
|
||||
fprintf(to, ".%s", name.c_str());
|
||||
}
|
||||
|
||||
|
||||
Statement::~Statement()
|
||||
{
|
||||
}
|
||||
|
||||
StatementBlock::StatementBlock()
|
||||
{
|
||||
}
|
||||
|
||||
StatementBlock::~StatementBlock()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
StatementBlock::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "{\n");
|
||||
int N = this->statements.size();
|
||||
for (int i=0; i<N; i++) {
|
||||
this->statements[i]->Write(to);
|
||||
}
|
||||
fprintf(to, "}\n");
|
||||
}
|
||||
|
||||
void
|
||||
StatementBlock::Add(Statement* statement)
|
||||
{
|
||||
this->statements.push_back(statement);
|
||||
}
|
||||
|
||||
void
|
||||
StatementBlock::Add(Expression* expression)
|
||||
{
|
||||
this->statements.push_back(new ExpressionStatement(expression));
|
||||
}
|
||||
|
||||
ExpressionStatement::ExpressionStatement(Expression* e)
|
||||
:expression(e)
|
||||
{
|
||||
}
|
||||
|
||||
ExpressionStatement::~ExpressionStatement()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
ExpressionStatement::Write(FILE* to)
|
||||
{
|
||||
this->expression->Write(to);
|
||||
fprintf(to, ";\n");
|
||||
}
|
||||
|
||||
Assignment::Assignment(Variable* l, Expression* r)
|
||||
:lvalue(l),
|
||||
rvalue(r),
|
||||
cast(NULL)
|
||||
{
|
||||
}
|
||||
|
||||
Assignment::Assignment(Variable* l, Expression* r, Type* c)
|
||||
:lvalue(l),
|
||||
rvalue(r),
|
||||
cast(c)
|
||||
{
|
||||
}
|
||||
|
||||
Assignment::~Assignment()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
Assignment::Write(FILE* to)
|
||||
{
|
||||
this->lvalue->Write(to);
|
||||
fprintf(to, " = ");
|
||||
if (this->cast != NULL) {
|
||||
fprintf(to, "(%s)", this->cast->QualifiedName().c_str());
|
||||
}
|
||||
this->rvalue->Write(to);
|
||||
}
|
||||
|
||||
MethodCall::MethodCall(const string& n)
|
||||
:obj(NULL),
|
||||
clazz(NULL),
|
||||
name(n)
|
||||
{
|
||||
}
|
||||
|
||||
MethodCall::MethodCall(const string& n, int argc = 0, ...)
|
||||
:obj(NULL),
|
||||
clazz(NULL),
|
||||
name(n)
|
||||
{
|
||||
va_list args;
|
||||
va_start(args, argc);
|
||||
init(argc, args);
|
||||
va_end(args);
|
||||
}
|
||||
|
||||
MethodCall::MethodCall(Expression* o, const string& n)
|
||||
:obj(o),
|
||||
clazz(NULL),
|
||||
name(n)
|
||||
{
|
||||
}
|
||||
|
||||
MethodCall::MethodCall(Type* t, const string& n)
|
||||
:obj(NULL),
|
||||
clazz(t),
|
||||
name(n)
|
||||
{
|
||||
}
|
||||
|
||||
MethodCall::MethodCall(Expression* o, const string& n, int argc = 0, ...)
|
||||
:obj(o),
|
||||
clazz(NULL),
|
||||
name(n)
|
||||
{
|
||||
va_list args;
|
||||
va_start(args, argc);
|
||||
init(argc, args);
|
||||
va_end(args);
|
||||
}
|
||||
|
||||
MethodCall::MethodCall(Type* t, const string& n, int argc = 0, ...)
|
||||
:obj(NULL),
|
||||
clazz(t),
|
||||
name(n)
|
||||
{
|
||||
va_list args;
|
||||
va_start(args, argc);
|
||||
init(argc, args);
|
||||
va_end(args);
|
||||
}
|
||||
|
||||
MethodCall::~MethodCall()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
MethodCall::init(int n, va_list args)
|
||||
{
|
||||
for (int i=0; i<n; i++) {
|
||||
Expression* expression = (Expression*)va_arg(args, void*);
|
||||
this->arguments.push_back(expression);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
MethodCall::Write(FILE* to)
|
||||
{
|
||||
if (this->obj != NULL) {
|
||||
this->obj->Write(to);
|
||||
fprintf(to, ".");
|
||||
}
|
||||
else if (this->clazz != NULL) {
|
||||
fprintf(to, "%s.", this->clazz->QualifiedName().c_str());
|
||||
}
|
||||
fprintf(to, "%s(", this->name.c_str());
|
||||
WriteArgumentList(to, this->arguments);
|
||||
fprintf(to, ")");
|
||||
}
|
||||
|
||||
Comparison::Comparison(Expression* l, const string& o, Expression* r)
|
||||
:lvalue(l),
|
||||
op(o),
|
||||
rvalue(r)
|
||||
{
|
||||
}
|
||||
|
||||
Comparison::~Comparison()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
Comparison::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "(");
|
||||
this->lvalue->Write(to);
|
||||
fprintf(to, "%s", this->op.c_str());
|
||||
this->rvalue->Write(to);
|
||||
fprintf(to, ")");
|
||||
}
|
||||
|
||||
NewExpression::NewExpression(Type* t)
|
||||
:type(t)
|
||||
{
|
||||
}
|
||||
|
||||
NewExpression::NewExpression(Type* t, int argc = 0, ...)
|
||||
:type(t)
|
||||
{
|
||||
va_list args;
|
||||
va_start(args, argc);
|
||||
init(argc, args);
|
||||
va_end(args);
|
||||
}
|
||||
|
||||
NewExpression::~NewExpression()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
NewExpression::init(int n, va_list args)
|
||||
{
|
||||
for (int i=0; i<n; i++) {
|
||||
Expression* expression = (Expression*)va_arg(args, void*);
|
||||
this->arguments.push_back(expression);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
NewExpression::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "new %s(", this->type->InstantiableName().c_str());
|
||||
WriteArgumentList(to, this->arguments);
|
||||
fprintf(to, ")");
|
||||
}
|
||||
|
||||
NewArrayExpression::NewArrayExpression(Type* t, Expression* s)
|
||||
:type(t),
|
||||
size(s)
|
||||
{
|
||||
}
|
||||
|
||||
NewArrayExpression::~NewArrayExpression()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
NewArrayExpression::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "new %s[", this->type->QualifiedName().c_str());
|
||||
size->Write(to);
|
||||
fprintf(to, "]");
|
||||
}
|
||||
|
||||
Ternary::Ternary()
|
||||
:condition(NULL),
|
||||
ifpart(NULL),
|
||||
elsepart(NULL)
|
||||
{
|
||||
}
|
||||
|
||||
Ternary::Ternary(Expression* a, Expression* b, Expression* c)
|
||||
:condition(a),
|
||||
ifpart(b),
|
||||
elsepart(c)
|
||||
{
|
||||
}
|
||||
|
||||
Ternary::~Ternary()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
Ternary::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "((");
|
||||
this->condition->Write(to);
|
||||
fprintf(to, ")?(");
|
||||
this->ifpart->Write(to);
|
||||
fprintf(to, "):(");
|
||||
this->elsepart->Write(to);
|
||||
fprintf(to, "))");
|
||||
}
|
||||
|
||||
Cast::Cast()
|
||||
:type(NULL),
|
||||
expression(NULL)
|
||||
{
|
||||
}
|
||||
|
||||
Cast::Cast(Type* t, Expression* e)
|
||||
:type(t),
|
||||
expression(e)
|
||||
{
|
||||
}
|
||||
|
||||
Cast::~Cast()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
Cast::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "((%s)", this->type->QualifiedName().c_str());
|
||||
expression->Write(to);
|
||||
fprintf(to, ")");
|
||||
}
|
||||
|
||||
VariableDeclaration::VariableDeclaration(Variable* l, Expression* r, Type* c)
|
||||
:lvalue(l),
|
||||
cast(c),
|
||||
rvalue(r)
|
||||
{
|
||||
}
|
||||
|
||||
VariableDeclaration::VariableDeclaration(Variable* l)
|
||||
:lvalue(l),
|
||||
cast(NULL),
|
||||
rvalue(NULL)
|
||||
{
|
||||
}
|
||||
|
||||
VariableDeclaration::~VariableDeclaration()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
VariableDeclaration::Write(FILE* to)
|
||||
{
|
||||
this->lvalue->WriteDeclaration(to);
|
||||
if (this->rvalue != NULL) {
|
||||
fprintf(to, " = ");
|
||||
if (this->cast != NULL) {
|
||||
fprintf(to, "(%s)", this->cast->QualifiedName().c_str());
|
||||
}
|
||||
this->rvalue->Write(to);
|
||||
}
|
||||
fprintf(to, ";\n");
|
||||
}
|
||||
|
||||
IfStatement::IfStatement()
|
||||
:expression(NULL),
|
||||
statements(new StatementBlock),
|
||||
elseif(NULL)
|
||||
{
|
||||
}
|
||||
|
||||
IfStatement::~IfStatement()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
IfStatement::Write(FILE* to)
|
||||
{
|
||||
if (this->expression != NULL) {
|
||||
fprintf(to, "if (");
|
||||
this->expression->Write(to);
|
||||
fprintf(to, ") ");
|
||||
}
|
||||
this->statements->Write(to);
|
||||
if (this->elseif != NULL) {
|
||||
fprintf(to, "else ");
|
||||
this->elseif->Write(to);
|
||||
}
|
||||
}
|
||||
|
||||
ReturnStatement::ReturnStatement(Expression* e)
|
||||
:expression(e)
|
||||
{
|
||||
}
|
||||
|
||||
ReturnStatement::~ReturnStatement()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
ReturnStatement::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "return ");
|
||||
this->expression->Write(to);
|
||||
fprintf(to, ";\n");
|
||||
}
|
||||
|
||||
TryStatement::TryStatement()
|
||||
:statements(new StatementBlock)
|
||||
{
|
||||
}
|
||||
|
||||
TryStatement::~TryStatement()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
TryStatement::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "try ");
|
||||
this->statements->Write(to);
|
||||
}
|
||||
|
||||
CatchStatement::CatchStatement(Variable* e)
|
||||
:statements(new StatementBlock),
|
||||
exception(e)
|
||||
{
|
||||
}
|
||||
|
||||
CatchStatement::~CatchStatement()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
CatchStatement::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "catch ");
|
||||
if (this->exception != NULL) {
|
||||
fprintf(to, "(");
|
||||
this->exception->WriteDeclaration(to);
|
||||
fprintf(to, ") ");
|
||||
}
|
||||
this->statements->Write(to);
|
||||
}
|
||||
|
||||
FinallyStatement::FinallyStatement()
|
||||
:statements(new StatementBlock)
|
||||
{
|
||||
}
|
||||
|
||||
FinallyStatement::~FinallyStatement()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
FinallyStatement::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "finally ");
|
||||
this->statements->Write(to);
|
||||
}
|
||||
|
||||
Case::Case()
|
||||
:statements(new StatementBlock)
|
||||
{
|
||||
}
|
||||
|
||||
Case::Case(const string& c)
|
||||
:statements(new StatementBlock)
|
||||
{
|
||||
cases.push_back(c);
|
||||
}
|
||||
|
||||
Case::~Case()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
Case::Write(FILE* to)
|
||||
{
|
||||
int N = this->cases.size();
|
||||
if (N > 0) {
|
||||
for (int i=0; i<N; i++) {
|
||||
string s = this->cases[i];
|
||||
if (s.length() != 0) {
|
||||
fprintf(to, "case %s:\n", s.c_str());
|
||||
} else {
|
||||
fprintf(to, "default:\n");
|
||||
}
|
||||
}
|
||||
} else {
|
||||
fprintf(to, "default:\n");
|
||||
}
|
||||
statements->Write(to);
|
||||
}
|
||||
|
||||
SwitchStatement::SwitchStatement(Expression* e)
|
||||
:expression(e)
|
||||
{
|
||||
}
|
||||
|
||||
SwitchStatement::~SwitchStatement()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
SwitchStatement::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "switch (");
|
||||
this->expression->Write(to);
|
||||
fprintf(to, ")\n{\n");
|
||||
int N = this->cases.size();
|
||||
for (int i=0; i<N; i++) {
|
||||
this->cases[i]->Write(to);
|
||||
}
|
||||
fprintf(to, "}\n");
|
||||
}
|
||||
|
||||
Break::Break()
|
||||
{
|
||||
}
|
||||
|
||||
Break::~Break()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
Break::Write(FILE* to)
|
||||
{
|
||||
fprintf(to, "break;\n");
|
||||
}
|
||||
|
||||
Method::Method()
|
||||
:ClassElement(),
|
||||
modifiers(0),
|
||||
returnType(NULL), // (NULL means constructor)
|
||||
returnTypeDimension(0),
|
||||
statements(NULL)
|
||||
{
|
||||
}
|
||||
|
||||
Method::~Method()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
Method::GatherTypes(set<Type*>* types) const
|
||||
{
|
||||
size_t N, i;
|
||||
|
||||
if (this->returnType) {
|
||||
types->insert(this->returnType);
|
||||
}
|
||||
|
||||
N = this->parameters.size();
|
||||
for (i=0; i<N; i++) {
|
||||
this->parameters[i]->GatherTypes(types);
|
||||
}
|
||||
|
||||
N = this->exceptions.size();
|
||||
for (i=0; i<N; i++) {
|
||||
types->insert(this->exceptions[i]);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
Method::Write(FILE* to)
|
||||
{
|
||||
size_t N, i;
|
||||
|
||||
if (this->comment.length() != 0) {
|
||||
fprintf(to, "%s\n", this->comment.c_str());
|
||||
}
|
||||
|
||||
WriteModifiers(to, this->modifiers, SCOPE_MASK | STATIC | ABSTRACT | FINAL | OVERRIDE);
|
||||
|
||||
if (this->returnType != NULL) {
|
||||
string dim;
|
||||
for (i=0; i<this->returnTypeDimension; i++) {
|
||||
dim += "[]";
|
||||
}
|
||||
fprintf(to, "%s%s ", this->returnType->QualifiedName().c_str(),
|
||||
dim.c_str());
|
||||
}
|
||||
|
||||
fprintf(to, "%s(", this->name.c_str());
|
||||
|
||||
N = this->parameters.size();
|
||||
for (i=0; i<N; i++) {
|
||||
this->parameters[i]->WriteDeclaration(to);
|
||||
if (i != N-1) {
|
||||
fprintf(to, ", ");
|
||||
}
|
||||
}
|
||||
|
||||
fprintf(to, ")");
|
||||
|
||||
N = this->exceptions.size();
|
||||
for (i=0; i<N; i++) {
|
||||
if (i == 0) {
|
||||
fprintf(to, " throws ");
|
||||
} else {
|
||||
fprintf(to, ", ");
|
||||
}
|
||||
fprintf(to, "%s", this->exceptions[i]->QualifiedName().c_str());
|
||||
}
|
||||
|
||||
if (this->statements == NULL) {
|
||||
fprintf(to, ";\n");
|
||||
} else {
|
||||
fprintf(to, "\n");
|
||||
this->statements->Write(to);
|
||||
}
|
||||
}
|
||||
|
||||
Class::Class()
|
||||
:modifiers(0),
|
||||
what(CLASS),
|
||||
type(NULL),
|
||||
extends(NULL)
|
||||
{
|
||||
}
|
||||
|
||||
Class::~Class()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
Class::GatherTypes(set<Type*>* types) const
|
||||
{
|
||||
int N, i;
|
||||
|
||||
types->insert(this->type);
|
||||
if (this->extends != NULL) {
|
||||
types->insert(this->extends);
|
||||
}
|
||||
|
||||
N = this->interfaces.size();
|
||||
for (i=0; i<N; i++) {
|
||||
types->insert(this->interfaces[i]);
|
||||
}
|
||||
|
||||
N = this->elements.size();
|
||||
for (i=0; i<N; i++) {
|
||||
this->elements[i]->GatherTypes(types);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
Class::Write(FILE* to)
|
||||
{
|
||||
size_t N, i;
|
||||
|
||||
if (this->comment.length() != 0) {
|
||||
fprintf(to, "%s\n", this->comment.c_str());
|
||||
}
|
||||
|
||||
WriteModifiers(to, this->modifiers, ALL_MODIFIERS);
|
||||
|
||||
if (this->what == Class::CLASS) {
|
||||
fprintf(to, "class ");
|
||||
} else {
|
||||
fprintf(to, "interface ");
|
||||
}
|
||||
|
||||
string name = this->type->Name();
|
||||
size_t pos = name.rfind('.');
|
||||
if (pos != string::npos) {
|
||||
name = name.c_str() + pos + 1;
|
||||
}
|
||||
|
||||
fprintf(to, "%s", name.c_str());
|
||||
|
||||
if (this->extends != NULL) {
|
||||
fprintf(to, " extends %s", this->extends->QualifiedName().c_str());
|
||||
}
|
||||
|
||||
N = this->interfaces.size();
|
||||
if (N != 0) {
|
||||
if (this->what == Class::CLASS) {
|
||||
fprintf(to, " implements");
|
||||
} else {
|
||||
fprintf(to, " extends");
|
||||
}
|
||||
for (i=0; i<N; i++) {
|
||||
fprintf(to, " %s", this->interfaces[i]->QualifiedName().c_str());
|
||||
}
|
||||
}
|
||||
|
||||
fprintf(to, "\n");
|
||||
fprintf(to, "{\n");
|
||||
|
||||
N = this->elements.size();
|
||||
for (i=0; i<N; i++) {
|
||||
this->elements[i]->Write(to);
|
||||
}
|
||||
|
||||
fprintf(to, "}\n");
|
||||
|
||||
}
|
||||
|
||||
Document::Document()
|
||||
{
|
||||
}
|
||||
|
||||
Document::~Document()
|
||||
{
|
||||
}
|
||||
|
||||
static string
|
||||
escape_backslashes(const string& str)
|
||||
{
|
||||
string result;
|
||||
const size_t I=str.length();
|
||||
for (size_t i=0; i<I; i++) {
|
||||
char c = str[i];
|
||||
if (c == '\\') {
|
||||
result += "\\\\";
|
||||
} else {
|
||||
result += c;
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
void
|
||||
Document::Write(FILE* to)
|
||||
{
|
||||
size_t N, i;
|
||||
|
||||
if (this->comment.length() != 0) {
|
||||
fprintf(to, "%s\n", this->comment.c_str());
|
||||
}
|
||||
fprintf(to, "/*\n"
|
||||
" * This file is auto-generated. DO NOT MODIFY.\n"
|
||||
" * Original file: %s\n"
|
||||
" */\n", escape_backslashes(this->originalSrc).c_str());
|
||||
if (this->package.length() != 0) {
|
||||
fprintf(to, "package %s;\n", this->package.c_str());
|
||||
}
|
||||
|
||||
N = this->classes.size();
|
||||
for (i=0; i<N; i++) {
|
||||
Class* c = this->classes[i];
|
||||
c->Write(to);
|
||||
}
|
||||
}
|
||||
|
||||
373
tools/aidl/AST.h
373
tools/aidl/AST.h
@@ -1,373 +0,0 @@
|
||||
#ifndef AIDL_AST_H_
|
||||
#define AIDL_AST_H_
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <set>
|
||||
#include <stdarg.h>
|
||||
#include <stdio.h>
|
||||
|
||||
using std::set;
|
||||
using std::string;
|
||||
using std::vector;
|
||||
|
||||
class Type;
|
||||
|
||||
enum {
|
||||
PACKAGE_PRIVATE = 0x00000000,
|
||||
PUBLIC = 0x00000001,
|
||||
PRIVATE = 0x00000002,
|
||||
PROTECTED = 0x00000003,
|
||||
SCOPE_MASK = 0x00000003,
|
||||
|
||||
STATIC = 0x00000010,
|
||||
FINAL = 0x00000020,
|
||||
ABSTRACT = 0x00000040,
|
||||
|
||||
OVERRIDE = 0x00000100,
|
||||
|
||||
ALL_MODIFIERS = 0xffffffff
|
||||
};
|
||||
|
||||
// Write the modifiers that are set in both mod and mask
|
||||
void WriteModifiers(FILE* to, int mod, int mask);
|
||||
|
||||
struct ClassElement
|
||||
{
|
||||
ClassElement();
|
||||
virtual ~ClassElement();
|
||||
|
||||
virtual void GatherTypes(set<Type*>* types) const = 0;
|
||||
virtual void Write(FILE* to) = 0;
|
||||
};
|
||||
|
||||
struct Expression
|
||||
{
|
||||
virtual ~Expression();
|
||||
virtual void Write(FILE* to) = 0;
|
||||
};
|
||||
|
||||
struct LiteralExpression : public Expression
|
||||
{
|
||||
string value;
|
||||
|
||||
LiteralExpression(const string& value);
|
||||
virtual ~LiteralExpression();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
// TODO: also escape the contents. not needed for now
|
||||
struct StringLiteralExpression : public Expression
|
||||
{
|
||||
string value;
|
||||
|
||||
StringLiteralExpression(const string& value);
|
||||
virtual ~StringLiteralExpression();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct Variable : public Expression
|
||||
{
|
||||
Type* type;
|
||||
string name;
|
||||
int dimension;
|
||||
|
||||
Variable();
|
||||
Variable(Type* type, const string& name);
|
||||
Variable(Type* type, const string& name, int dimension);
|
||||
virtual ~Variable();
|
||||
|
||||
virtual void GatherTypes(set<Type*>* types) const;
|
||||
void WriteDeclaration(FILE* to);
|
||||
void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct FieldVariable : public Expression
|
||||
{
|
||||
Expression* object;
|
||||
Type* clazz;
|
||||
string name;
|
||||
|
||||
FieldVariable(Expression* object, const string& name);
|
||||
FieldVariable(Type* clazz, const string& name);
|
||||
virtual ~FieldVariable();
|
||||
|
||||
void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct Field : public ClassElement
|
||||
{
|
||||
string comment;
|
||||
int modifiers;
|
||||
Variable *variable;
|
||||
string value;
|
||||
|
||||
Field();
|
||||
Field(int modifiers, Variable* variable);
|
||||
virtual ~Field();
|
||||
|
||||
virtual void GatherTypes(set<Type*>* types) const;
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct Statement
|
||||
{
|
||||
virtual ~Statement();
|
||||
virtual void Write(FILE* to) = 0;
|
||||
};
|
||||
|
||||
struct StatementBlock : public Statement
|
||||
{
|
||||
vector<Statement*> statements;
|
||||
|
||||
StatementBlock();
|
||||
virtual ~StatementBlock();
|
||||
virtual void Write(FILE* to);
|
||||
|
||||
void Add(Statement* statement);
|
||||
void Add(Expression* expression);
|
||||
};
|
||||
|
||||
struct ExpressionStatement : public Statement
|
||||
{
|
||||
Expression* expression;
|
||||
|
||||
ExpressionStatement(Expression* expression);
|
||||
virtual ~ExpressionStatement();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct Assignment : public Expression
|
||||
{
|
||||
Variable* lvalue;
|
||||
Expression* rvalue;
|
||||
Type* cast;
|
||||
|
||||
Assignment(Variable* lvalue, Expression* rvalue);
|
||||
Assignment(Variable* lvalue, Expression* rvalue, Type* cast);
|
||||
virtual ~Assignment();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct MethodCall : public Expression
|
||||
{
|
||||
Expression* obj;
|
||||
Type* clazz;
|
||||
string name;
|
||||
vector<Expression*> arguments;
|
||||
vector<string> exceptions;
|
||||
|
||||
MethodCall(const string& name);
|
||||
MethodCall(const string& name, int argc, ...);
|
||||
MethodCall(Expression* obj, const string& name);
|
||||
MethodCall(Type* clazz, const string& name);
|
||||
MethodCall(Expression* obj, const string& name, int argc, ...);
|
||||
MethodCall(Type* clazz, const string& name, int argc, ...);
|
||||
virtual ~MethodCall();
|
||||
virtual void Write(FILE* to);
|
||||
|
||||
private:
|
||||
void init(int n, va_list args);
|
||||
};
|
||||
|
||||
struct Comparison : public Expression
|
||||
{
|
||||
Expression* lvalue;
|
||||
string op;
|
||||
Expression* rvalue;
|
||||
|
||||
Comparison(Expression* lvalue, const string& op, Expression* rvalue);
|
||||
virtual ~Comparison();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct NewExpression : public Expression
|
||||
{
|
||||
Type* type;
|
||||
vector<Expression*> arguments;
|
||||
|
||||
NewExpression(Type* type);
|
||||
NewExpression(Type* type, int argc, ...);
|
||||
virtual ~NewExpression();
|
||||
virtual void Write(FILE* to);
|
||||
|
||||
private:
|
||||
void init(int n, va_list args);
|
||||
};
|
||||
|
||||
struct NewArrayExpression : public Expression
|
||||
{
|
||||
Type* type;
|
||||
Expression* size;
|
||||
|
||||
NewArrayExpression(Type* type, Expression* size);
|
||||
virtual ~NewArrayExpression();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct Ternary : public Expression
|
||||
{
|
||||
Expression* condition;
|
||||
Expression* ifpart;
|
||||
Expression* elsepart;
|
||||
|
||||
Ternary();
|
||||
Ternary(Expression* condition, Expression* ifpart, Expression* elsepart);
|
||||
virtual ~Ternary();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct Cast : public Expression
|
||||
{
|
||||
Type* type;
|
||||
Expression* expression;
|
||||
|
||||
Cast();
|
||||
Cast(Type* type, Expression* expression);
|
||||
virtual ~Cast();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct VariableDeclaration : public Statement
|
||||
{
|
||||
Variable* lvalue;
|
||||
Type* cast;
|
||||
Expression* rvalue;
|
||||
|
||||
VariableDeclaration(Variable* lvalue);
|
||||
VariableDeclaration(Variable* lvalue, Expression* rvalue, Type* cast = NULL);
|
||||
virtual ~VariableDeclaration();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct IfStatement : public Statement
|
||||
{
|
||||
Expression* expression;
|
||||
StatementBlock* statements;
|
||||
IfStatement* elseif;
|
||||
|
||||
IfStatement();
|
||||
virtual ~IfStatement();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct ReturnStatement : public Statement
|
||||
{
|
||||
Expression* expression;
|
||||
|
||||
ReturnStatement(Expression* expression);
|
||||
virtual ~ReturnStatement();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct TryStatement : public Statement
|
||||
{
|
||||
StatementBlock* statements;
|
||||
|
||||
TryStatement();
|
||||
virtual ~TryStatement();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct CatchStatement : public Statement
|
||||
{
|
||||
StatementBlock* statements;
|
||||
Variable* exception;
|
||||
|
||||
CatchStatement(Variable* exception);
|
||||
virtual ~CatchStatement();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct FinallyStatement : public Statement
|
||||
{
|
||||
StatementBlock* statements;
|
||||
|
||||
FinallyStatement();
|
||||
virtual ~FinallyStatement();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct Case
|
||||
{
|
||||
vector<string> cases;
|
||||
StatementBlock* statements;
|
||||
|
||||
Case();
|
||||
Case(const string& c);
|
||||
virtual ~Case();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct SwitchStatement : public Statement
|
||||
{
|
||||
Expression* expression;
|
||||
vector<Case*> cases;
|
||||
|
||||
SwitchStatement(Expression* expression);
|
||||
virtual ~SwitchStatement();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct Break : public Statement
|
||||
{
|
||||
Break();
|
||||
virtual ~Break();
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct Method : public ClassElement
|
||||
{
|
||||
string comment;
|
||||
int modifiers;
|
||||
Type* returnType;
|
||||
size_t returnTypeDimension;
|
||||
string name;
|
||||
vector<Variable*> parameters;
|
||||
vector<Type*> exceptions;
|
||||
StatementBlock* statements;
|
||||
|
||||
Method();
|
||||
virtual ~Method();
|
||||
|
||||
virtual void GatherTypes(set<Type*>* types) const;
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct Class : public ClassElement
|
||||
{
|
||||
enum {
|
||||
CLASS,
|
||||
INTERFACE
|
||||
};
|
||||
|
||||
string comment;
|
||||
int modifiers;
|
||||
int what; // CLASS or INTERFACE
|
||||
Type* type;
|
||||
Type* extends;
|
||||
vector<Type*> interfaces;
|
||||
vector<ClassElement*> elements;
|
||||
|
||||
Class();
|
||||
virtual ~Class();
|
||||
|
||||
virtual void GatherTypes(set<Type*>* types) const;
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
struct Document
|
||||
{
|
||||
string comment;
|
||||
string package;
|
||||
string originalSrc;
|
||||
set<Type*> imports;
|
||||
vector<Class*> classes;
|
||||
|
||||
Document();
|
||||
virtual ~Document();
|
||||
|
||||
virtual void Write(FILE* to);
|
||||
};
|
||||
|
||||
#endif // AIDL_AST_H_
|
||||
@@ -1,80 +0,0 @@
|
||||
# Copyright 2007 The Android Open Source Project
|
||||
#
|
||||
# Copies files into the directory structure described by a manifest
|
||||
|
||||
# This tool is prebuilt if we're doing an app-only build.
|
||||
ifeq ($(TARGET_BUILD_APPS)$(filter true,$(TARGET_BUILD_PDK)),)
|
||||
|
||||
LOCAL_PATH:= $(call my-dir)
|
||||
|
||||
# Logic shared between aidl and its unittests
|
||||
include $(CLEAR_VARS)
|
||||
LOCAL_MODULE := libaidl-common
|
||||
LOCAL_MODULE_HOST_OS := darwin linux windows
|
||||
|
||||
LOCAL_CLANG_CFLAGS := -Wall -Werror
|
||||
# Tragically, the code is riddled with unused parameters.
|
||||
LOCAL_CLANG_CFLAGS += -Wno-unused-parameter
|
||||
# yacc dumps a lot of code *just in case*.
|
||||
LOCAL_CLANG_CFLAGS += -Wno-unused-function
|
||||
LOCAL_CLANG_CFLAGS += -Wno-unneeded-internal-declaration
|
||||
# yacc is a tool from a more civilized age.
|
||||
LOCAL_CLANG_CFLAGS += -Wno-deprecated-register
|
||||
# yacc also has a habit of using char* over const char*.
|
||||
LOCAL_CLANG_CFLAGS += -Wno-writable-strings
|
||||
|
||||
LOCAL_SRC_FILES := \
|
||||
AST.cpp \
|
||||
Type.cpp \
|
||||
aidl.cpp \
|
||||
aidl_language.cpp \
|
||||
aidl_language_l.l \
|
||||
aidl_language_y.y \
|
||||
generate_java.cpp \
|
||||
generate_java_binder.cpp \
|
||||
options.cpp \
|
||||
search_path.cpp \
|
||||
|
||||
include $(BUILD_HOST_STATIC_LIBRARY)
|
||||
|
||||
|
||||
# aidl executable
|
||||
include $(CLEAR_VARS)
|
||||
LOCAL_MODULE := aidl
|
||||
|
||||
LOCAL_MODULE_HOST_OS := darwin linux windows
|
||||
LOCAL_CFLAGS := -Wall -Werror
|
||||
LOCAL_SRC_FILES := main.cpp
|
||||
LOCAL_STATIC_LIBRARIES := libaidl-common
|
||||
include $(BUILD_HOST_EXECUTABLE)
|
||||
|
||||
|
||||
# TODO(wiley) Compile these for mac as well after b/22771504
|
||||
ifeq ($(HOST_OS),linux)
|
||||
# Unit tests
|
||||
include $(CLEAR_VARS)
|
||||
LOCAL_MODULE := aidl_unittests
|
||||
|
||||
LOCAL_CFLAGS := -g -DUNIT_TEST -Wall -Werror
|
||||
# Tragically, the code is riddled with unused parameters.
|
||||
LOCAL_CLANG_CFLAGS := -Wno-unused-parameter
|
||||
LOCAL_SRC_FILES := \
|
||||
options_unittest.cpp \
|
||||
test_main.cpp \
|
||||
tests/end_to_end_tests.cpp \
|
||||
tests/example_interface_test_data.cpp \
|
||||
|
||||
LOCAL_SHARED_LIBRARIES := \
|
||||
libchrome-host \
|
||||
|
||||
LOCAL_STATIC_LIBRARIES := \
|
||||
libaidl-common \
|
||||
libgmock_host \
|
||||
libgtest_host \
|
||||
|
||||
LOCAL_LDLIBS_linux := -lrt
|
||||
|
||||
include $(BUILD_HOST_NATIVE_TEST)
|
||||
endif # HOST_OS == linux
|
||||
|
||||
endif # No TARGET_BUILD_APPS or TARGET_BUILD_PDK
|
||||
@@ -1,190 +0,0 @@
|
||||
|
||||
Copyright (c) 2005-2008, The Android Open Source Project
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
|
||||
|
||||
Apache License
|
||||
Version 2.0, January 2004
|
||||
http://www.apache.org/licenses/
|
||||
|
||||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||
|
||||
1. Definitions.
|
||||
|
||||
"License" shall mean the terms and conditions for use, reproduction,
|
||||
and distribution as defined by Sections 1 through 9 of this document.
|
||||
|
||||
"Licensor" shall mean the copyright owner or entity authorized by
|
||||
the copyright owner that is granting the License.
|
||||
|
||||
"Legal Entity" shall mean the union of the acting entity and all
|
||||
other entities that control, are controlled by, or are under common
|
||||
control with that entity. For the purposes of this definition,
|
||||
"control" means (i) the power, direct or indirect, to cause the
|
||||
direction or management of such entity, whether by contract or
|
||||
otherwise, or (ii) ownership of fifty percent (50%) or more of the
|
||||
outstanding shares, or (iii) beneficial ownership of such entity.
|
||||
|
||||
"You" (or "Your") shall mean an individual or Legal Entity
|
||||
exercising permissions granted by this License.
|
||||
|
||||
"Source" form shall mean the preferred form for making modifications,
|
||||
including but not limited to software source code, documentation
|
||||
source, and configuration files.
|
||||
|
||||
"Object" form shall mean any form resulting from mechanical
|
||||
transformation or translation of a Source form, including but
|
||||
not limited to compiled object code, generated documentation,
|
||||
and conversions to other media types.
|
||||
|
||||
"Work" shall mean the work of authorship, whether in Source or
|
||||
Object form, made available under the License, as indicated by a
|
||||
copyright notice that is included in or attached to the work
|
||||
(an example is provided in the Appendix below).
|
||||
|
||||
"Derivative Works" shall mean any work, whether in Source or Object
|
||||
form, that is based on (or derived from) the Work and for which the
|
||||
editorial revisions, annotations, elaborations, or other modifications
|
||||
represent, as a whole, an original work of authorship. For the purposes
|
||||
of this License, Derivative Works shall not include works that remain
|
||||
separable from, or merely link (or bind by name) to the interfaces of,
|
||||
the Work and Derivative Works thereof.
|
||||
|
||||
"Contribution" shall mean any work of authorship, including
|
||||
the original version of the Work and any modifications or additions
|
||||
to that Work or Derivative Works thereof, that is intentionally
|
||||
submitted to Licensor for inclusion in the Work by the copyright owner
|
||||
or by an individual or Legal Entity authorized to submit on behalf of
|
||||
the copyright owner. For the purposes of this definition, "submitted"
|
||||
means any form of electronic, verbal, or written communication sent
|
||||
to the Licensor or its representatives, including but not limited to
|
||||
communication on electronic mailing lists, source code control systems,
|
||||
and issue tracking systems that are managed by, or on behalf of, the
|
||||
Licensor for the purpose of discussing and improving the Work, but
|
||||
excluding communication that is conspicuously marked or otherwise
|
||||
designated in writing by the copyright owner as "Not a Contribution."
|
||||
|
||||
"Contributor" shall mean Licensor and any individual or Legal Entity
|
||||
on behalf of whom a Contribution has been received by Licensor and
|
||||
subsequently incorporated within the Work.
|
||||
|
||||
2. Grant of Copyright License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
copyright license to reproduce, prepare Derivative Works of,
|
||||
publicly display, publicly perform, sublicense, and distribute the
|
||||
Work and such Derivative Works in Source or Object form.
|
||||
|
||||
3. Grant of Patent License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
(except as stated in this section) patent license to make, have made,
|
||||
use, offer to sell, sell, import, and otherwise transfer the Work,
|
||||
where such license applies only to those patent claims licensable
|
||||
by such Contributor that are necessarily infringed by their
|
||||
Contribution(s) alone or by combination of their Contribution(s)
|
||||
with the Work to which such Contribution(s) was submitted. If You
|
||||
institute patent litigation against any entity (including a
|
||||
cross-claim or counterclaim in a lawsuit) alleging that the Work
|
||||
or a Contribution incorporated within the Work constitutes direct
|
||||
or contributory patent infringement, then any patent licenses
|
||||
granted to You under this License for that Work shall terminate
|
||||
as of the date such litigation is filed.
|
||||
|
||||
4. Redistribution. You may reproduce and distribute copies of the
|
||||
Work or Derivative Works thereof in any medium, with or without
|
||||
modifications, and in Source or Object form, provided that You
|
||||
meet the following conditions:
|
||||
|
||||
(a) You must give any other recipients of the Work or
|
||||
Derivative Works a copy of this License; and
|
||||
|
||||
(b) You must cause any modified files to carry prominent notices
|
||||
stating that You changed the files; and
|
||||
|
||||
(c) You must retain, in the Source form of any Derivative Works
|
||||
that You distribute, all copyright, patent, trademark, and
|
||||
attribution notices from the Source form of the Work,
|
||||
excluding those notices that do not pertain to any part of
|
||||
the Derivative Works; and
|
||||
|
||||
(d) If the Work includes a "NOTICE" text file as part of its
|
||||
distribution, then any Derivative Works that You distribute must
|
||||
include a readable copy of the attribution notices contained
|
||||
within such NOTICE file, excluding those notices that do not
|
||||
pertain to any part of the Derivative Works, in at least one
|
||||
of the following places: within a NOTICE text file distributed
|
||||
as part of the Derivative Works; within the Source form or
|
||||
documentation, if provided along with the Derivative Works; or,
|
||||
within a display generated by the Derivative Works, if and
|
||||
wherever such third-party notices normally appear. The contents
|
||||
of the NOTICE file are for informational purposes only and
|
||||
do not modify the License. You may add Your own attribution
|
||||
notices within Derivative Works that You distribute, alongside
|
||||
or as an addendum to the NOTICE text from the Work, provided
|
||||
that such additional attribution notices cannot be construed
|
||||
as modifying the License.
|
||||
|
||||
You may add Your own copyright statement to Your modifications and
|
||||
may provide additional or different license terms and conditions
|
||||
for use, reproduction, or distribution of Your modifications, or
|
||||
for any such Derivative Works as a whole, provided Your use,
|
||||
reproduction, and distribution of the Work otherwise complies with
|
||||
the conditions stated in this License.
|
||||
|
||||
5. Submission of Contributions. Unless You explicitly state otherwise,
|
||||
any Contribution intentionally submitted for inclusion in the Work
|
||||
by You to the Licensor shall be under the terms and conditions of
|
||||
this License, without any additional terms or conditions.
|
||||
Notwithstanding the above, nothing herein shall supersede or modify
|
||||
the terms of any separate license agreement you may have executed
|
||||
with Licensor regarding such Contributions.
|
||||
|
||||
6. Trademarks. This License does not grant permission to use the trade
|
||||
names, trademarks, service marks, or product names of the Licensor,
|
||||
except as required for reasonable and customary use in describing the
|
||||
origin of the Work and reproducing the content of the NOTICE file.
|
||||
|
||||
7. Disclaimer of Warranty. Unless required by applicable law or
|
||||
agreed to in writing, Licensor provides the Work (and each
|
||||
Contributor provides its Contributions) on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
implied, including, without limitation, any warranties or conditions
|
||||
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
|
||||
PARTICULAR PURPOSE. You are solely responsible for determining the
|
||||
appropriateness of using or redistributing the Work and assume any
|
||||
risks associated with Your exercise of permissions under this License.
|
||||
|
||||
8. Limitation of Liability. In no event and under no legal theory,
|
||||
whether in tort (including negligence), contract, or otherwise,
|
||||
unless required by applicable law (such as deliberate and grossly
|
||||
negligent acts) or agreed to in writing, shall any Contributor be
|
||||
liable to You for damages, including any direct, indirect, special,
|
||||
incidental, or consequential damages of any character arising as a
|
||||
result of this License or out of the use or inability to use the
|
||||
Work (including but not limited to damages for loss of goodwill,
|
||||
work stoppage, computer failure or malfunction, or any and all
|
||||
other commercial damages or losses), even if such Contributor
|
||||
has been advised of the possibility of such damages.
|
||||
|
||||
9. Accepting Warranty or Additional Liability. While redistributing
|
||||
the Work or Derivative Works thereof, You may choose to offer,
|
||||
and charge a fee for, acceptance of support, warranty, indemnity,
|
||||
or other liability obligations and/or rights consistent with this
|
||||
License. However, in accepting such obligations, You may act only
|
||||
on Your own behalf and on Your sole responsibility, not on behalf
|
||||
of any other Contributor, and only if You agree to indemnify,
|
||||
defend, and hold each Contributor harmless for any liability
|
||||
incurred by, or claims asserted against, such Contributor by reason
|
||||
of your accepting any such warranty or additional liability.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
|
||||
1245
tools/aidl/Type.cpp
1245
tools/aidl/Type.cpp
File diff suppressed because it is too large
Load Diff
@@ -1,473 +0,0 @@
|
||||
#ifndef AIDL_TYPE_H_
|
||||
#define AIDL_TYPE_H_
|
||||
|
||||
#include "AST.h"
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
using std::string;
|
||||
using std::vector;
|
||||
|
||||
class Type
|
||||
{
|
||||
public:
|
||||
// kinds
|
||||
enum {
|
||||
BUILT_IN,
|
||||
USERDATA,
|
||||
INTERFACE,
|
||||
GENERATED
|
||||
};
|
||||
|
||||
// WriteToParcel flags
|
||||
enum {
|
||||
PARCELABLE_WRITE_RETURN_VALUE = 0x0001
|
||||
};
|
||||
|
||||
Type(const string& name, int kind, bool canWriteToParcel,
|
||||
bool canBeOut);
|
||||
Type(const string& package, const string& name,
|
||||
int kind, bool canWriteToParcel, bool canBeOut,
|
||||
const string& declFile = "", int declLine = -1);
|
||||
virtual ~Type();
|
||||
|
||||
inline string Package() const { return m_package; }
|
||||
inline string Name() const { return m_name; }
|
||||
inline string QualifiedName() const { return m_qualifiedName; }
|
||||
inline int Kind() const { return m_kind; }
|
||||
inline string DeclFile() const { return m_declFile; }
|
||||
inline int DeclLine() const { return m_declLine; }
|
||||
inline bool CanWriteToParcel() const { return m_canWriteToParcel; }
|
||||
inline bool CanBeOutParameter() const { return m_canBeOut; }
|
||||
|
||||
virtual string ImportType() const;
|
||||
virtual string CreatorName() const;
|
||||
virtual string InstantiableName() const;
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
|
||||
virtual bool CanBeArray() const;
|
||||
|
||||
virtual void WriteArrayToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
|
||||
protected:
|
||||
void SetQualifiedName(const string& qualified);
|
||||
Expression* BuildWriteToParcelFlags(int flags);
|
||||
|
||||
private:
|
||||
Type();
|
||||
Type(const Type&);
|
||||
|
||||
string m_package;
|
||||
string m_name;
|
||||
string m_qualifiedName;
|
||||
string m_declFile;
|
||||
int m_declLine;
|
||||
int m_kind;
|
||||
bool m_canWriteToParcel;
|
||||
bool m_canBeOut;
|
||||
};
|
||||
|
||||
class BasicType : public Type
|
||||
{
|
||||
public:
|
||||
BasicType(const string& name,
|
||||
const string& marshallParcel,
|
||||
const string& unmarshallParcel,
|
||||
const string& writeArrayParcel,
|
||||
const string& createArrayParcel,
|
||||
const string& readArrayParcel);
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
|
||||
virtual bool CanBeArray() const;
|
||||
|
||||
virtual void WriteArrayToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
|
||||
private:
|
||||
string m_marshallParcel;
|
||||
string m_unmarshallParcel;
|
||||
string m_writeArrayParcel;
|
||||
string m_createArrayParcel;
|
||||
string m_readArrayParcel;
|
||||
};
|
||||
|
||||
class BooleanType : public Type
|
||||
{
|
||||
public:
|
||||
BooleanType();
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
|
||||
virtual bool CanBeArray() const;
|
||||
|
||||
virtual void WriteArrayToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class CharType : public Type
|
||||
{
|
||||
public:
|
||||
CharType();
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
|
||||
virtual bool CanBeArray() const;
|
||||
|
||||
virtual void WriteArrayToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
|
||||
class StringType : public Type
|
||||
{
|
||||
public:
|
||||
StringType();
|
||||
|
||||
virtual string CreatorName() const;
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
|
||||
virtual bool CanBeArray() const;
|
||||
|
||||
virtual void WriteArrayToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class CharSequenceType : public Type
|
||||
{
|
||||
public:
|
||||
CharSequenceType();
|
||||
|
||||
virtual string CreatorName() const;
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class RemoteExceptionType : public Type
|
||||
{
|
||||
public:
|
||||
RemoteExceptionType();
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class RuntimeExceptionType : public Type
|
||||
{
|
||||
public:
|
||||
RuntimeExceptionType();
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class IBinderType : public Type
|
||||
{
|
||||
public:
|
||||
IBinderType();
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
|
||||
virtual void WriteArrayToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class IInterfaceType : public Type
|
||||
{
|
||||
public:
|
||||
IInterfaceType();
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class BinderType : public Type
|
||||
{
|
||||
public:
|
||||
BinderType();
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class BinderProxyType : public Type
|
||||
{
|
||||
public:
|
||||
BinderProxyType();
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class ParcelType : public Type
|
||||
{
|
||||
public:
|
||||
ParcelType();
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class ParcelableInterfaceType : public Type
|
||||
{
|
||||
public:
|
||||
ParcelableInterfaceType();
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class MapType : public Type
|
||||
{
|
||||
public:
|
||||
MapType();
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class ListType : public Type
|
||||
{
|
||||
public:
|
||||
ListType();
|
||||
|
||||
virtual string InstantiableName() const;
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class UserDataType : public Type
|
||||
{
|
||||
public:
|
||||
UserDataType(const string& package, const string& name,
|
||||
bool builtIn, bool canWriteToParcel,
|
||||
const string& declFile = "", int declLine = -1);
|
||||
|
||||
virtual string CreatorName() const;
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
|
||||
virtual bool CanBeArray() const;
|
||||
|
||||
virtual void WriteArrayToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadArrayFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
};
|
||||
|
||||
class InterfaceType : public Type
|
||||
{
|
||||
public:
|
||||
InterfaceType(const string& package, const string& name,
|
||||
bool builtIn, bool oneway,
|
||||
const string& declFile, int declLine);
|
||||
|
||||
bool OneWay() const;
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
|
||||
private:
|
||||
bool m_oneway;
|
||||
};
|
||||
|
||||
|
||||
class GenericType : public Type
|
||||
{
|
||||
public:
|
||||
GenericType(const string& package, const string& name,
|
||||
const vector<Type*>& args);
|
||||
|
||||
const vector<Type*>& GenericArgumentTypes() const;
|
||||
string GenericArguments() const;
|
||||
|
||||
virtual string ImportType() const;
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
|
||||
private:
|
||||
string m_genericArguments;
|
||||
string m_importName;
|
||||
vector<Type*> m_args;
|
||||
};
|
||||
|
||||
class ClassLoaderType : public Type
|
||||
{
|
||||
public:
|
||||
ClassLoaderType();
|
||||
};
|
||||
|
||||
class GenericListType : public GenericType
|
||||
{
|
||||
public:
|
||||
GenericListType(const string& package, const string& name,
|
||||
const vector<Type*>& args);
|
||||
|
||||
virtual string CreatorName() const;
|
||||
virtual string InstantiableName() const;
|
||||
|
||||
virtual void WriteToParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags);
|
||||
virtual void CreateFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
virtual void ReadFromParcel(StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl);
|
||||
|
||||
private:
|
||||
string m_creator;
|
||||
};
|
||||
|
||||
class Namespace
|
||||
{
|
||||
public:
|
||||
Namespace();
|
||||
~Namespace();
|
||||
void Add(Type* type);
|
||||
|
||||
// args is the number of template types (what is this called?)
|
||||
void AddGenericType(const string& package, const string& name, int args);
|
||||
|
||||
// lookup a specific class name
|
||||
Type* Find(const string& name) const;
|
||||
Type* Find(const char* package, const char* name) const;
|
||||
|
||||
// try to search by either a full name or a partial name
|
||||
Type* Search(const string& name);
|
||||
|
||||
void Dump() const;
|
||||
|
||||
private:
|
||||
struct Generic {
|
||||
string package;
|
||||
string name;
|
||||
string qualified;
|
||||
int args;
|
||||
};
|
||||
|
||||
const Generic* search_generic(const string& name) const;
|
||||
|
||||
vector<Type*> m_types;
|
||||
vector<Generic> m_generics;
|
||||
};
|
||||
|
||||
extern Namespace NAMES;
|
||||
|
||||
extern Type* VOID_TYPE;
|
||||
extern Type* BOOLEAN_TYPE;
|
||||
extern Type* BYTE_TYPE;
|
||||
extern Type* CHAR_TYPE;
|
||||
extern Type* INT_TYPE;
|
||||
extern Type* LONG_TYPE;
|
||||
extern Type* FLOAT_TYPE;
|
||||
extern Type* DOUBLE_TYPE;
|
||||
extern Type* OBJECT_TYPE;
|
||||
extern Type* STRING_TYPE;
|
||||
extern Type* CHAR_SEQUENCE_TYPE;
|
||||
extern Type* TEXT_UTILS_TYPE;
|
||||
extern Type* REMOTE_EXCEPTION_TYPE;
|
||||
extern Type* RUNTIME_EXCEPTION_TYPE;
|
||||
extern Type* IBINDER_TYPE;
|
||||
extern Type* IINTERFACE_TYPE;
|
||||
extern Type* BINDER_NATIVE_TYPE;
|
||||
extern Type* BINDER_PROXY_TYPE;
|
||||
extern Type* PARCEL_TYPE;
|
||||
extern Type* PARCELABLE_INTERFACE_TYPE;
|
||||
|
||||
extern Type* CONTEXT_TYPE;
|
||||
|
||||
extern Expression* NULL_VALUE;
|
||||
extern Expression* THIS_VALUE;
|
||||
extern Expression* SUPER_VALUE;
|
||||
extern Expression* TRUE_VALUE;
|
||||
extern Expression* FALSE_VALUE;
|
||||
|
||||
void register_base_types();
|
||||
|
||||
#endif // AIDL_TYPE_H_
|
||||
1075
tools/aidl/aidl.cpp
1075
tools/aidl/aidl.cpp
File diff suppressed because it is too large
Load Diff
@@ -1,9 +0,0 @@
|
||||
#ifndef AIDL_AIDL_H_
|
||||
#define AIDL_AIDL_H_
|
||||
|
||||
#include "options.h"
|
||||
|
||||
int compile_aidl(Options& options);
|
||||
int preprocess_aidl(const Options& options);
|
||||
|
||||
#endif // AIDL_AIDL_H_
|
||||
@@ -1,94 +0,0 @@
|
||||
#include "aidl_language.h"
|
||||
#include "aidl_language_y.hpp"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string>
|
||||
#include <iostream>
|
||||
|
||||
#ifdef _WIN32
|
||||
int isatty(int fd)
|
||||
{
|
||||
return (fd == 0);
|
||||
}
|
||||
#endif
|
||||
|
||||
using std::string;
|
||||
using std::cerr;
|
||||
using std::endl;
|
||||
|
||||
ParserCallbacks* g_callbacks = NULL; // &k_parserCallbacks;
|
||||
|
||||
void yylex_init(void **);
|
||||
void yylex_destroy(void *);
|
||||
void yyset_in(FILE *f, void *);
|
||||
int yyparse(ParseState*);
|
||||
|
||||
ParseState::ParseState() : ParseState("") {}
|
||||
|
||||
ParseState::ParseState(const string& filename)
|
||||
: filename_(filename) {
|
||||
yylex_init(&scanner_);
|
||||
}
|
||||
|
||||
ParseState::~ParseState() {
|
||||
yylex_destroy(scanner_);
|
||||
}
|
||||
|
||||
string ParseState::FileName() {
|
||||
return filename_;
|
||||
}
|
||||
|
||||
string ParseState::Package() {
|
||||
return g_currentPackage;
|
||||
}
|
||||
|
||||
void ParseState::ProcessDocument(const document_item_type& items) {
|
||||
/* The cast is not my fault. I didn't write the code on the other side. */
|
||||
/* TODO(sadmac): b/23977313 */
|
||||
g_callbacks->document((document_item_type *)&items);
|
||||
}
|
||||
|
||||
void ParseState::ProcessImport(const buffer_type& statement) {
|
||||
/* The cast is not my fault. I didn't write the code on the other side. */
|
||||
/* TODO(sadmac): b/23977313 */
|
||||
g_callbacks->import((buffer_type *)&statement);
|
||||
}
|
||||
|
||||
void ParseState::ReportError(const string& err) {
|
||||
/* FIXME: We're printing out the line number as -1. We used to use yylineno
|
||||
* (which was NEVER correct even before reentrant parsing). Now we'll need
|
||||
* another way.
|
||||
*/
|
||||
cerr << filename_ << ":" << -1 << ": " << err << endl;
|
||||
error_ = 1;
|
||||
}
|
||||
|
||||
bool ParseState::FoundNoErrors() {
|
||||
return error_ == 0;
|
||||
}
|
||||
|
||||
void *ParseState::Scanner() {
|
||||
return scanner_;
|
||||
}
|
||||
|
||||
bool ParseState::OpenFileFromDisk() {
|
||||
FILE *in = fopen(FileName().c_str(), "r");
|
||||
|
||||
if (! in)
|
||||
return false;
|
||||
|
||||
yyset_in(in, Scanner());
|
||||
return true;
|
||||
}
|
||||
|
||||
int ParseState::RunParser() {
|
||||
int ret = yy::parser(this).parse();
|
||||
|
||||
free((void *)g_currentPackage);
|
||||
g_currentPackage = NULL;
|
||||
|
||||
if (error_)
|
||||
return 1;
|
||||
|
||||
return ret;
|
||||
}
|
||||
@@ -1,189 +0,0 @@
|
||||
#ifndef AIDL_AIDL_LANGUAGE_H_
|
||||
#define AIDL_AIDL_LANGUAGE_H_
|
||||
|
||||
#include <string>
|
||||
|
||||
#include "macros.h"
|
||||
|
||||
typedef enum {
|
||||
NO_EXTRA_TEXT = 0,
|
||||
SHORT_COMMENT,
|
||||
LONG_COMMENT,
|
||||
COPY_TEXT,
|
||||
WHITESPACE
|
||||
} which_extra_text;
|
||||
|
||||
typedef struct extra_text_type {
|
||||
unsigned lineno;
|
||||
which_extra_text which;
|
||||
char* data;
|
||||
unsigned len;
|
||||
struct extra_text_type* next;
|
||||
} extra_text_type;
|
||||
|
||||
typedef struct buffer_type {
|
||||
unsigned lineno;
|
||||
unsigned token;
|
||||
char *data;
|
||||
extra_text_type* extra;
|
||||
} buffer_type;
|
||||
|
||||
typedef struct type_type {
|
||||
buffer_type type;
|
||||
buffer_type array_token;
|
||||
int dimension;
|
||||
} type_type;
|
||||
|
||||
typedef struct arg_type {
|
||||
buffer_type comma_token; // empty in the first one in the list
|
||||
buffer_type direction;
|
||||
type_type type;
|
||||
buffer_type name;
|
||||
struct arg_type *next;
|
||||
} arg_type;
|
||||
|
||||
enum {
|
||||
METHOD_TYPE
|
||||
};
|
||||
|
||||
typedef struct interface_item_type {
|
||||
unsigned item_type;
|
||||
struct interface_item_type* next;
|
||||
} interface_item_type;
|
||||
|
||||
typedef struct method_type {
|
||||
interface_item_type interface_item;
|
||||
type_type type;
|
||||
bool oneway;
|
||||
buffer_type oneway_token;
|
||||
buffer_type name;
|
||||
buffer_type open_paren_token;
|
||||
arg_type* args;
|
||||
buffer_type close_paren_token;
|
||||
bool hasId;
|
||||
buffer_type equals_token;
|
||||
buffer_type id;
|
||||
// XXX missing comments/copy text here
|
||||
buffer_type semicolon_token;
|
||||
buffer_type* comments_token; // points into this structure, DO NOT DELETE
|
||||
int assigned_id;
|
||||
} method_type;
|
||||
|
||||
enum {
|
||||
USER_DATA_TYPE = 12,
|
||||
INTERFACE_TYPE_BINDER
|
||||
};
|
||||
|
||||
typedef struct document_item_type {
|
||||
unsigned item_type;
|
||||
struct document_item_type* next;
|
||||
} document_item_type;
|
||||
|
||||
|
||||
typedef struct user_data_type {
|
||||
document_item_type document_item;
|
||||
buffer_type keyword_token; // only the first one
|
||||
char* package;
|
||||
buffer_type name;
|
||||
buffer_type semicolon_token;
|
||||
bool parcelable;
|
||||
} user_data_type;
|
||||
|
||||
typedef struct interface_type {
|
||||
document_item_type document_item;
|
||||
buffer_type interface_token;
|
||||
bool oneway;
|
||||
buffer_type oneway_token;
|
||||
char* package;
|
||||
buffer_type name;
|
||||
buffer_type open_brace_token;
|
||||
interface_item_type* interface_items;
|
||||
buffer_type close_brace_token;
|
||||
buffer_type* comments_token; // points into this structure, DO NOT DELETE
|
||||
} interface_type;
|
||||
|
||||
typedef union lexer_type {
|
||||
buffer_type buffer;
|
||||
type_type type;
|
||||
arg_type *arg;
|
||||
method_type* method;
|
||||
interface_item_type* interface_item;
|
||||
interface_type* interface_obj;
|
||||
user_data_type* user_data;
|
||||
document_item_type* document_item;
|
||||
} lexer_type;
|
||||
|
||||
|
||||
#define YYSTYPE lexer_type
|
||||
|
||||
#if __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
int parse_aidl(char const *);
|
||||
|
||||
// strips off the leading whitespace, the "import" text
|
||||
// also returns whether it's a local or system import
|
||||
// we rely on the input matching the import regex from below
|
||||
char* parse_import_statement(const char* text);
|
||||
|
||||
// in, out or inout
|
||||
enum {
|
||||
IN_PARAMETER = 1,
|
||||
OUT_PARAMETER = 2,
|
||||
INOUT_PARAMETER = 3
|
||||
};
|
||||
int convert_direction(const char* direction);
|
||||
|
||||
// callbacks from within the parser
|
||||
// these functions all take ownership of the strings
|
||||
typedef struct ParserCallbacks {
|
||||
void (*document)(document_item_type* items);
|
||||
void (*import)(buffer_type* statement);
|
||||
} ParserCallbacks;
|
||||
|
||||
extern ParserCallbacks* g_callbacks;
|
||||
|
||||
// the package name for our current file
|
||||
extern char const* g_currentPackage;
|
||||
|
||||
typedef enum {
|
||||
STATEMENT_INSIDE_INTERFACE
|
||||
} error_type;
|
||||
|
||||
void init_buffer_type(buffer_type* buf, int lineno);
|
||||
|
||||
|
||||
class ParseState {
|
||||
public:
|
||||
ParseState();
|
||||
ParseState(const std::string& filename);
|
||||
~ParseState();
|
||||
|
||||
bool OpenFileFromDisk();
|
||||
int RunParser();
|
||||
void ReportError(const std::string& err);
|
||||
|
||||
bool FoundNoErrors();
|
||||
std::string FileName();
|
||||
std::string Package();
|
||||
void *Scanner();
|
||||
|
||||
void ProcessDocument(const document_item_type& items);
|
||||
void ProcessImport(const buffer_type& statement);
|
||||
|
||||
private:
|
||||
int error_ = 0;
|
||||
std::string filename_;
|
||||
std::string package_;
|
||||
void *scanner_ = nullptr;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(ParseState);
|
||||
};
|
||||
|
||||
#if __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
#endif // AIDL_AIDL_LANGUAGE_H_
|
||||
@@ -1,196 +0,0 @@
|
||||
%{
|
||||
#include "aidl_language.h"
|
||||
#include "aidl_language_y.hpp"
|
||||
#include "search_path.h"
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
extern YYSTYPE yylval;
|
||||
|
||||
// comment and whitespace handling
|
||||
// these functions save a copy of the buffer
|
||||
static void begin_extra_text(unsigned lineno, which_extra_text which);
|
||||
static void append_extra_text(char* text);
|
||||
static extra_text_type* get_extra_text(void); // you now own the object
|
||||
// this returns
|
||||
static void drop_extra_text(void);
|
||||
|
||||
// package handling
|
||||
static void do_package_statement(const char* importText);
|
||||
|
||||
#define SET_BUFFER(t) \
|
||||
do { \
|
||||
yylval->buffer.lineno = yyget_lineno(yyscanner); \
|
||||
yylval->buffer.token = (t); \
|
||||
yylval->buffer.data = strdup(yytext); \
|
||||
yylval->buffer.extra = get_extra_text(); \
|
||||
} while(0)
|
||||
|
||||
%}
|
||||
|
||||
%option yylineno
|
||||
%option noyywrap
|
||||
%option reentrant
|
||||
%option bison-bridge
|
||||
%option bison-locations
|
||||
|
||||
%x COPYING LONG_COMMENT
|
||||
|
||||
identifier [_a-zA-Z][_a-zA-Z0-9\.]*
|
||||
whitespace ([ \t\n\r]+)
|
||||
brackets \[{whitespace}?\]
|
||||
idvalue (0|[1-9][0-9]*)
|
||||
|
||||
%%
|
||||
|
||||
|
||||
\%\%\{ { begin_extra_text(yylineno, COPY_TEXT); BEGIN(COPYING); }
|
||||
<COPYING>\}\%\% { BEGIN(INITIAL); }
|
||||
<COPYING>.*\n { append_extra_text(yytext); }
|
||||
<COPYING>.* { append_extra_text(yytext); }
|
||||
<COPYING>\n+ { append_extra_text(yytext); }
|
||||
|
||||
|
||||
\/\* { begin_extra_text(yylineno, (which_extra_text)LONG_COMMENT);
|
||||
BEGIN(LONG_COMMENT); }
|
||||
<LONG_COMMENT>[^*]* { append_extra_text(yytext); }
|
||||
<LONG_COMMENT>\*+[^/] { append_extra_text(yytext); }
|
||||
<LONG_COMMENT>\n { append_extra_text(yytext); }
|
||||
<LONG_COMMENT>\**\/ { BEGIN(INITIAL); }
|
||||
|
||||
^{whitespace}?import{whitespace}[^ \t\r\n]+{whitespace}?; {
|
||||
SET_BUFFER(yy::parser::token::IMPORT);
|
||||
return yy::parser::token::IMPORT;
|
||||
}
|
||||
^{whitespace}?package{whitespace}[^ \t\r\n]+{whitespace}?; {
|
||||
do_package_statement(yytext);
|
||||
SET_BUFFER(yy::parser::token::PACKAGE);
|
||||
return yy::parser::token::PACKAGE;
|
||||
}
|
||||
<<EOF>> { yyterminate(); }
|
||||
|
||||
\/\/.*\n { begin_extra_text(yylineno, SHORT_COMMENT);
|
||||
append_extra_text(yytext); }
|
||||
|
||||
{whitespace} { /* begin_extra_text(yylineno, WHITESPACE);
|
||||
append_extra_text(yytext); */ }
|
||||
|
||||
; { SET_BUFFER(';'); return ';'; }
|
||||
\{ { SET_BUFFER('{'); return '{'; }
|
||||
\} { SET_BUFFER('}'); return '}'; }
|
||||
\( { SET_BUFFER('('); return '('; }
|
||||
\) { SET_BUFFER(')'); return ')'; }
|
||||
, { SET_BUFFER(','); return ','; }
|
||||
= { SET_BUFFER('='); return '='; }
|
||||
|
||||
/* keywords */
|
||||
parcelable { SET_BUFFER(yy::parser::token::PARCELABLE); return yy::parser::token::PARCELABLE; }
|
||||
interface { SET_BUFFER(yy::parser::token::INTERFACE); return yy::parser::token::INTERFACE; }
|
||||
in { SET_BUFFER(yy::parser::token::IN); return yy::parser::token::IN; }
|
||||
out { SET_BUFFER(yy::parser::token::OUT); return yy::parser::token::OUT; }
|
||||
inout { SET_BUFFER(yy::parser::token::INOUT); return yy::parser::token::INOUT; }
|
||||
oneway { SET_BUFFER(yy::parser::token::ONEWAY); return yy::parser::token::ONEWAY; }
|
||||
|
||||
{brackets}+ { SET_BUFFER(yy::parser::token::ARRAY); return yy::parser::token::ARRAY; }
|
||||
{idvalue} { SET_BUFFER(yy::parser::token::IDVALUE); return yy::parser::token::IDVALUE; }
|
||||
{identifier} { SET_BUFFER(yy::parser::token::IDENTIFIER); return yy::parser::token::IDENTIFIER; }
|
||||
{identifier}\<{whitespace}*{identifier}({whitespace}*,{whitespace}*{identifier})*{whitespace}*\> {
|
||||
SET_BUFFER(yy::parser::token::GENERIC); return yy::parser::token::GENERIC; }
|
||||
|
||||
/* syntax error! */
|
||||
. { printf("UNKNOWN(%s)", yytext);
|
||||
yylval->buffer.lineno = yylineno;
|
||||
yylval->buffer.token = yy::parser::token::IDENTIFIER;
|
||||
yylval->buffer.data = strdup(yytext);
|
||||
return yy::parser::token::IDENTIFIER;
|
||||
}
|
||||
|
||||
%%
|
||||
|
||||
// comment and whitespace handling
|
||||
// ================================================
|
||||
extra_text_type* g_extraText = NULL;
|
||||
extra_text_type* g_nextExtraText = NULL;
|
||||
|
||||
void begin_extra_text(unsigned lineno, which_extra_text which)
|
||||
{
|
||||
extra_text_type* text = (extra_text_type*)malloc(sizeof(extra_text_type));
|
||||
text->lineno = lineno;
|
||||
text->which = which;
|
||||
text->data = NULL;
|
||||
text->len = 0;
|
||||
text->next = NULL;
|
||||
if (g_nextExtraText == NULL) {
|
||||
g_extraText = text;
|
||||
} else {
|
||||
g_nextExtraText->next = text;
|
||||
}
|
||||
g_nextExtraText = text;
|
||||
}
|
||||
|
||||
void append_extra_text(char* text)
|
||||
{
|
||||
if (g_nextExtraText->data == NULL) {
|
||||
g_nextExtraText->data = strdup(text);
|
||||
g_nextExtraText->len = strlen(text);
|
||||
} else {
|
||||
char* orig = g_nextExtraText->data;
|
||||
unsigned oldLen = g_nextExtraText->len;
|
||||
unsigned len = strlen(text);
|
||||
g_nextExtraText->len += len;
|
||||
g_nextExtraText->data = (char*)malloc(g_nextExtraText->len+1);
|
||||
memcpy(g_nextExtraText->data, orig, oldLen);
|
||||
memcpy(g_nextExtraText->data+oldLen, text, len);
|
||||
g_nextExtraText->data[g_nextExtraText->len] = '\0';
|
||||
free(orig);
|
||||
}
|
||||
}
|
||||
|
||||
extra_text_type*
|
||||
get_extra_text(void)
|
||||
{
|
||||
extra_text_type* result = g_extraText;
|
||||
g_extraText = NULL;
|
||||
g_nextExtraText = NULL;
|
||||
return result;
|
||||
}
|
||||
|
||||
void drop_extra_text(void)
|
||||
{
|
||||
extra_text_type* p = g_extraText;
|
||||
while (p) {
|
||||
extra_text_type* next = p->next;
|
||||
free(p->data);
|
||||
free(p);
|
||||
free(next);
|
||||
}
|
||||
g_extraText = NULL;
|
||||
g_nextExtraText = NULL;
|
||||
}
|
||||
|
||||
|
||||
// package handling
|
||||
// ================================================
|
||||
void do_package_statement(const char* importText)
|
||||
{
|
||||
if (g_currentPackage) free((void*)g_currentPackage);
|
||||
g_currentPackage = parse_import_statement(importText);
|
||||
}
|
||||
|
||||
|
||||
// main parse function
|
||||
// ================================================
|
||||
extern ParseState *psGlobal;
|
||||
char const* g_currentPackage = NULL;
|
||||
|
||||
int parse_aidl(char const *filename) {
|
||||
ParseState ps(filename);
|
||||
psGlobal = &ps;
|
||||
|
||||
if (!ps.OpenFileFromDisk()) {
|
||||
fprintf(stderr, "aidl: unable to open file for read: %s\n", filename);
|
||||
return 1;
|
||||
}
|
||||
|
||||
return ps.RunParser();
|
||||
}
|
||||
@@ -1,343 +0,0 @@
|
||||
%{
|
||||
#include "aidl_language.h"
|
||||
#include "aidl_language_y.hpp"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
int yylex(lexer_type *, yy::parser::location_type *l, void *);
|
||||
|
||||
static int count_brackets(const char*);
|
||||
|
||||
#define lex_scanner ps->Scanner()
|
||||
|
||||
%}
|
||||
|
||||
%parse-param { ParseState* ps }
|
||||
%lex-param { void *lex_scanner }
|
||||
|
||||
%pure-parser
|
||||
%skeleton "glr.cc"
|
||||
|
||||
%token IMPORT
|
||||
%token PACKAGE
|
||||
%token IDENTIFIER
|
||||
%token IDVALUE
|
||||
%token GENERIC
|
||||
%token ARRAY
|
||||
%token PARCELABLE
|
||||
%token INTERFACE
|
||||
%token IN
|
||||
%token OUT
|
||||
%token INOUT
|
||||
%token ONEWAY
|
||||
|
||||
%%
|
||||
document:
|
||||
document_items { ps->ProcessDocument(*$1.document_item); }
|
||||
| headers document_items { ps->ProcessDocument(*$2.document_item); }
|
||||
;
|
||||
|
||||
headers:
|
||||
package { }
|
||||
| imports { }
|
||||
| package imports { }
|
||||
;
|
||||
|
||||
package:
|
||||
PACKAGE { }
|
||||
;
|
||||
|
||||
imports:
|
||||
IMPORT { ps->ProcessImport($1.buffer); }
|
||||
| IMPORT imports { ps->ProcessImport($1.buffer); }
|
||||
;
|
||||
|
||||
document_items:
|
||||
{ $$.document_item = NULL; }
|
||||
| document_items declaration {
|
||||
if ($2.document_item == NULL) {
|
||||
// error cases only
|
||||
$$ = $1;
|
||||
} else {
|
||||
document_item_type* p = $1.document_item;
|
||||
while (p && p->next) {
|
||||
p=p->next;
|
||||
}
|
||||
if (p) {
|
||||
p->next = (document_item_type*)$2.document_item;
|
||||
$$ = $1;
|
||||
} else {
|
||||
$$.document_item = (document_item_type*)$2.document_item;
|
||||
}
|
||||
}
|
||||
}
|
||||
| document_items error {
|
||||
fprintf(stderr, "%s:%d: syntax error don't know what to do with \"%s\"\n",
|
||||
ps->FileName().c_str(),
|
||||
$2.buffer.lineno, $2.buffer.data);
|
||||
$$ = $1;
|
||||
}
|
||||
;
|
||||
|
||||
declaration:
|
||||
parcelable_decl { $$.document_item = (document_item_type*)$1.user_data; }
|
||||
| interface_decl { $$.document_item = (document_item_type*)$1.interface_item; }
|
||||
;
|
||||
|
||||
parcelable_decl:
|
||||
PARCELABLE IDENTIFIER ';' {
|
||||
user_data_type* b = (user_data_type*)malloc(sizeof(user_data_type));
|
||||
b->document_item.item_type = USER_DATA_TYPE;
|
||||
b->document_item.next = NULL;
|
||||
b->keyword_token = $1.buffer;
|
||||
b->name = $2.buffer;
|
||||
b->package =
|
||||
strdup(ps->Package().c_str());
|
||||
b->semicolon_token = $3.buffer;
|
||||
b->parcelable = true;
|
||||
$$.user_data = b;
|
||||
}
|
||||
| PARCELABLE ';' {
|
||||
fprintf(stderr, "%s:%d syntax error in parcelable declaration. Expected type name.\n",
|
||||
ps->FileName().c_str(), $1.buffer.lineno);
|
||||
$$.user_data = NULL;
|
||||
}
|
||||
| PARCELABLE error ';' {
|
||||
fprintf(stderr, "%s:%d syntax error in parcelable declaration. Expected type name, saw \"%s\".\n",
|
||||
ps->FileName().c_str(), $2.buffer.lineno, $2.buffer.data);
|
||||
$$.user_data = NULL;
|
||||
}
|
||||
;
|
||||
|
||||
interface_header:
|
||||
INTERFACE {
|
||||
interface_type* c = (interface_type*)malloc(sizeof(interface_type));
|
||||
c->document_item.item_type = INTERFACE_TYPE_BINDER;
|
||||
c->document_item.next = NULL;
|
||||
c->interface_token = $1.buffer;
|
||||
c->oneway = false;
|
||||
memset(&c->oneway_token, 0, sizeof(buffer_type));
|
||||
c->comments_token = &c->interface_token;
|
||||
$$.interface_obj = c;
|
||||
}
|
||||
| ONEWAY INTERFACE {
|
||||
interface_type* c = (interface_type*)malloc(sizeof(interface_type));
|
||||
c->document_item.item_type = INTERFACE_TYPE_BINDER;
|
||||
c->document_item.next = NULL;
|
||||
c->interface_token = $2.buffer;
|
||||
c->oneway = true;
|
||||
c->oneway_token = $1.buffer;
|
||||
c->comments_token = &c->oneway_token;
|
||||
$$.interface_obj = c;
|
||||
}
|
||||
;
|
||||
|
||||
interface_decl:
|
||||
interface_header IDENTIFIER '{' interface_items '}' {
|
||||
interface_type* c = $1.interface_obj;
|
||||
c->name = $2.buffer;
|
||||
c->package =
|
||||
strdup(ps->Package().c_str());
|
||||
c->open_brace_token = $3.buffer;
|
||||
c->interface_items = $4.interface_item;
|
||||
c->close_brace_token = $5.buffer;
|
||||
$$.interface_obj = c;
|
||||
}
|
||||
| INTERFACE error '{' interface_items '}' {
|
||||
fprintf(stderr, "%s:%d: syntax error in interface declaration. Expected type name, saw \"%s\"\n",
|
||||
ps->FileName().c_str(), $2.buffer.lineno, $2.buffer.data);
|
||||
$$.document_item = NULL;
|
||||
}
|
||||
| INTERFACE error '}' {
|
||||
fprintf(stderr, "%s:%d: syntax error in interface declaration. Expected type name, saw \"%s\"\n",
|
||||
ps->FileName().c_str(), $2.buffer.lineno, $2.buffer.data);
|
||||
$$.document_item = NULL;
|
||||
}
|
||||
|
||||
;
|
||||
|
||||
interface_items:
|
||||
{ $$.interface_item = NULL; }
|
||||
| interface_items method_decl {
|
||||
interface_item_type* p=$1.interface_item;
|
||||
while (p && p->next) {
|
||||
p=p->next;
|
||||
}
|
||||
if (p) {
|
||||
p->next = (interface_item_type*)$2.method;
|
||||
$$ = $1;
|
||||
} else {
|
||||
$$.interface_item = (interface_item_type*)$2.method;
|
||||
}
|
||||
}
|
||||
| interface_items error ';' {
|
||||
fprintf(stderr, "%s:%d: syntax error before ';' (expected method declaration)\n",
|
||||
ps->FileName().c_str(), $3.buffer.lineno);
|
||||
$$ = $1;
|
||||
}
|
||||
;
|
||||
|
||||
method_decl:
|
||||
type IDENTIFIER '(' arg_list ')' ';' {
|
||||
method_type *method = (method_type*)malloc(sizeof(method_type));
|
||||
method->interface_item.item_type = METHOD_TYPE;
|
||||
method->interface_item.next = NULL;
|
||||
method->oneway = false;
|
||||
method->type = $1.type;
|
||||
memset(&method->oneway_token, 0, sizeof(buffer_type));
|
||||
method->name = $2.buffer;
|
||||
method->open_paren_token = $3.buffer;
|
||||
method->args = $4.arg;
|
||||
method->close_paren_token = $5.buffer;
|
||||
method->hasId = false;
|
||||
memset(&method->equals_token, 0, sizeof(buffer_type));
|
||||
memset(&method->id, 0, sizeof(buffer_type));
|
||||
method->semicolon_token = $6.buffer;
|
||||
method->comments_token = &method->type.type;
|
||||
$$.method = method;
|
||||
}
|
||||
| ONEWAY type IDENTIFIER '(' arg_list ')' ';' {
|
||||
method_type *method = (method_type*)malloc(sizeof(method_type));
|
||||
method->interface_item.item_type = METHOD_TYPE;
|
||||
method->interface_item.next = NULL;
|
||||
method->oneway = true;
|
||||
method->oneway_token = $1.buffer;
|
||||
method->type = $2.type;
|
||||
method->name = $3.buffer;
|
||||
method->open_paren_token = $4.buffer;
|
||||
method->args = $5.arg;
|
||||
method->close_paren_token = $6.buffer;
|
||||
method->hasId = false;
|
||||
memset(&method->equals_token, 0, sizeof(buffer_type));
|
||||
memset(&method->id, 0, sizeof(buffer_type));
|
||||
method->semicolon_token = $7.buffer;
|
||||
method->comments_token = &method->oneway_token;
|
||||
$$.method = method;
|
||||
}
|
||||
| type IDENTIFIER '(' arg_list ')' '=' IDVALUE ';' {
|
||||
method_type *method = (method_type*)malloc(sizeof(method_type));
|
||||
method->interface_item.item_type = METHOD_TYPE;
|
||||
method->interface_item.next = NULL;
|
||||
method->oneway = false;
|
||||
memset(&method->oneway_token, 0, sizeof(buffer_type));
|
||||
method->type = $1.type;
|
||||
method->name = $2.buffer;
|
||||
method->open_paren_token = $3.buffer;
|
||||
method->args = $4.arg;
|
||||
method->close_paren_token = $5.buffer;
|
||||
method->hasId = true;
|
||||
method->equals_token = $6.buffer;
|
||||
method->id = $7.buffer;
|
||||
method->semicolon_token = $8.buffer;
|
||||
method->comments_token = &method->type.type;
|
||||
$$.method = method;
|
||||
}
|
||||
| ONEWAY type IDENTIFIER '(' arg_list ')' '=' IDVALUE ';' {
|
||||
method_type *method = (method_type*)malloc(sizeof(method_type));
|
||||
method->interface_item.item_type = METHOD_TYPE;
|
||||
method->interface_item.next = NULL;
|
||||
method->oneway = true;
|
||||
method->oneway_token = $1.buffer;
|
||||
method->type = $2.type;
|
||||
method->name = $3.buffer;
|
||||
method->open_paren_token = $4.buffer;
|
||||
method->args = $5.arg;
|
||||
method->close_paren_token = $6.buffer;
|
||||
method->hasId = true;
|
||||
method->equals_token = $7.buffer;
|
||||
method->id = $8.buffer;
|
||||
method->semicolon_token = $9.buffer;
|
||||
method->comments_token = &method->oneway_token;
|
||||
$$.method = method;
|
||||
}
|
||||
;
|
||||
|
||||
arg_list:
|
||||
{ $$.arg = NULL; }
|
||||
| arg { $$ = $1; }
|
||||
| arg_list ',' arg {
|
||||
if ($$.arg != NULL) {
|
||||
// only NULL on error
|
||||
$$ = $1;
|
||||
arg_type *p = $1.arg;
|
||||
while (p && p->next) {
|
||||
p=p->next;
|
||||
}
|
||||
$3.arg->comma_token = $2.buffer;
|
||||
p->next = $3.arg;
|
||||
}
|
||||
}
|
||||
| error {
|
||||
fprintf(stderr, "%s:%d: syntax error in parameter list\n",
|
||||
ps->FileName().c_str(), $1.buffer.lineno);
|
||||
$$.arg = NULL;
|
||||
}
|
||||
;
|
||||
|
||||
arg:
|
||||
direction type IDENTIFIER {
|
||||
arg_type* arg = (arg_type*)malloc(sizeof(arg_type));
|
||||
memset(&arg->comma_token, 0, sizeof(buffer_type));
|
||||
arg->direction = $1.buffer;
|
||||
arg->type = $2.type;
|
||||
arg->name = $3.buffer;
|
||||
arg->next = NULL;
|
||||
$$.arg = arg;
|
||||
}
|
||||
;
|
||||
|
||||
type:
|
||||
IDENTIFIER {
|
||||
$$.type.type = $1.buffer;
|
||||
init_buffer_type(&$$.type.array_token,
|
||||
$1.buffer.lineno);
|
||||
$$.type.dimension = 0;
|
||||
}
|
||||
| IDENTIFIER ARRAY {
|
||||
$$.type.type = $1.buffer;
|
||||
$$.type.array_token = $2.buffer;
|
||||
$$.type.dimension = count_brackets($2.buffer.data);
|
||||
}
|
||||
| GENERIC {
|
||||
$$.type.type = $1.buffer;
|
||||
init_buffer_type(&$$.type.array_token,
|
||||
$1.buffer.lineno);
|
||||
$$.type.dimension = 0;
|
||||
}
|
||||
;
|
||||
|
||||
direction:
|
||||
{ init_buffer_type(&$$.buffer, $$.buffer.lineno); }
|
||||
| IN { $$.buffer = $1.buffer; }
|
||||
| OUT { $$.buffer = $1.buffer; }
|
||||
| INOUT { $$.buffer = $1.buffer; }
|
||||
;
|
||||
|
||||
%%
|
||||
|
||||
#include <ctype.h>
|
||||
#include <stdio.h>
|
||||
|
||||
void init_buffer_type(buffer_type* buf, int lineno)
|
||||
{
|
||||
buf->lineno = lineno;
|
||||
buf->token = 0;
|
||||
buf->data = NULL;
|
||||
buf->extra = NULL;
|
||||
}
|
||||
|
||||
static int count_brackets(const char* s)
|
||||
{
|
||||
int n=0;
|
||||
while (*s) {
|
||||
if (*s == '[') n++;
|
||||
s++;
|
||||
}
|
||||
return n;
|
||||
}
|
||||
|
||||
void yy::parser::error(const yy::parser::location_type& l, const std::string& errstr)
|
||||
{
|
||||
ps->ReportError(errstr);
|
||||
}
|
||||
@@ -1,96 +0,0 @@
|
||||
#include "generate_java.h"
|
||||
#include "Type.h"
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
// =================================================
|
||||
VariableFactory::VariableFactory(const string& base)
|
||||
:m_base(base),
|
||||
m_index(0)
|
||||
{
|
||||
}
|
||||
|
||||
Variable*
|
||||
VariableFactory::Get(Type* type)
|
||||
{
|
||||
char name[100];
|
||||
sprintf(name, "%s%d", m_base.c_str(), m_index);
|
||||
m_index++;
|
||||
Variable* v = new Variable(type, name);
|
||||
m_vars.push_back(v);
|
||||
return v;
|
||||
}
|
||||
|
||||
Variable*
|
||||
VariableFactory::Get(int index)
|
||||
{
|
||||
return m_vars[index];
|
||||
}
|
||||
|
||||
// =================================================
|
||||
string
|
||||
gather_comments(extra_text_type* extra)
|
||||
{
|
||||
string s;
|
||||
while (extra) {
|
||||
if (extra->which == SHORT_COMMENT) {
|
||||
s += extra->data;
|
||||
}
|
||||
else if (extra->which == LONG_COMMENT) {
|
||||
s += "/*";
|
||||
s += extra->data;
|
||||
s += "*/";
|
||||
}
|
||||
extra = extra->next;
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
string
|
||||
append(const char* a, const char* b)
|
||||
{
|
||||
string s = a;
|
||||
s += b;
|
||||
return s;
|
||||
}
|
||||
|
||||
// =================================================
|
||||
int
|
||||
generate_java(const string& filename, const string& originalSrc,
|
||||
interface_type* iface)
|
||||
{
|
||||
Class* cl;
|
||||
|
||||
if (iface->document_item.item_type == INTERFACE_TYPE_BINDER) {
|
||||
cl = generate_binder_interface_class(iface);
|
||||
}
|
||||
|
||||
Document* document = new Document;
|
||||
document->comment = "";
|
||||
if (iface->package) document->package = iface->package;
|
||||
document->originalSrc = originalSrc;
|
||||
document->classes.push_back(cl);
|
||||
|
||||
// printf("outputting... filename=%s\n", filename.c_str());
|
||||
FILE* to;
|
||||
if (filename == "-") {
|
||||
to = stdout;
|
||||
} else {
|
||||
/* open file in binary mode to ensure that the tool produces the
|
||||
* same output on all platforms !!
|
||||
*/
|
||||
to = fopen(filename.c_str(), "wb");
|
||||
if (to == NULL) {
|
||||
fprintf(stderr, "unable to open %s for write\n", filename.c_str());
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
document->Write(to);
|
||||
|
||||
fclose(to);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1,33 +0,0 @@
|
||||
#ifndef AIDL_GENERATE_JAVA_H_
|
||||
#define AIDL_GENERATE_JAVA_H_
|
||||
|
||||
#include "aidl_language.h"
|
||||
#include "AST.h"
|
||||
|
||||
#include <string>
|
||||
|
||||
using std::string;
|
||||
using std::vector;
|
||||
|
||||
int generate_java(const string& filename, const string& originalSrc,
|
||||
interface_type* iface);
|
||||
|
||||
Class* generate_binder_interface_class(const interface_type* iface);
|
||||
|
||||
string gather_comments(extra_text_type* extra);
|
||||
string append(const char* a, const char* b);
|
||||
|
||||
class VariableFactory
|
||||
{
|
||||
public:
|
||||
VariableFactory(const string& base); // base must be short
|
||||
Variable* Get(Type* type);
|
||||
Variable* Get(int index);
|
||||
private:
|
||||
vector<Variable*> m_vars;
|
||||
string m_base;
|
||||
int m_index;
|
||||
};
|
||||
|
||||
#endif // AIDL_GENERATE_JAVA_H_
|
||||
|
||||
@@ -1,560 +0,0 @@
|
||||
#include "generate_java.h"
|
||||
#include "Type.h"
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
// =================================================
|
||||
class StubClass : public Class
|
||||
{
|
||||
public:
|
||||
StubClass(Type* type, Type* interfaceType);
|
||||
virtual ~StubClass();
|
||||
|
||||
Variable* transact_code;
|
||||
Variable* transact_data;
|
||||
Variable* transact_reply;
|
||||
Variable* transact_flags;
|
||||
SwitchStatement* transact_switch;
|
||||
private:
|
||||
void make_as_interface(Type* interfaceType);
|
||||
};
|
||||
|
||||
StubClass::StubClass(Type* type, Type* interfaceType)
|
||||
:Class()
|
||||
{
|
||||
this->comment = "/** Local-side IPC implementation stub class. */";
|
||||
this->modifiers = PUBLIC | ABSTRACT | STATIC;
|
||||
this->what = Class::CLASS;
|
||||
this->type = type;
|
||||
this->extends = BINDER_NATIVE_TYPE;
|
||||
this->interfaces.push_back(interfaceType);
|
||||
|
||||
// descriptor
|
||||
Field* descriptor = new Field(STATIC | FINAL | PRIVATE,
|
||||
new Variable(STRING_TYPE, "DESCRIPTOR"));
|
||||
descriptor->value = "\"" + interfaceType->QualifiedName() + "\"";
|
||||
this->elements.push_back(descriptor);
|
||||
|
||||
// ctor
|
||||
Method* ctor = new Method;
|
||||
ctor->modifiers = PUBLIC;
|
||||
ctor->comment = "/** Construct the stub at attach it to the "
|
||||
"interface. */";
|
||||
ctor->name = "Stub";
|
||||
ctor->statements = new StatementBlock;
|
||||
MethodCall* attach = new MethodCall(THIS_VALUE, "attachInterface",
|
||||
2, THIS_VALUE, new LiteralExpression("DESCRIPTOR"));
|
||||
ctor->statements->Add(attach);
|
||||
this->elements.push_back(ctor);
|
||||
|
||||
// asInterface
|
||||
make_as_interface(interfaceType);
|
||||
|
||||
// asBinder
|
||||
Method* asBinder = new Method;
|
||||
asBinder->modifiers = PUBLIC | OVERRIDE;
|
||||
asBinder->returnType = IBINDER_TYPE;
|
||||
asBinder->name = "asBinder";
|
||||
asBinder->statements = new StatementBlock;
|
||||
asBinder->statements->Add(new ReturnStatement(THIS_VALUE));
|
||||
this->elements.push_back(asBinder);
|
||||
|
||||
// onTransact
|
||||
this->transact_code = new Variable(INT_TYPE, "code");
|
||||
this->transact_data = new Variable(PARCEL_TYPE, "data");
|
||||
this->transact_reply = new Variable(PARCEL_TYPE, "reply");
|
||||
this->transact_flags = new Variable(INT_TYPE, "flags");
|
||||
Method* onTransact = new Method;
|
||||
onTransact->modifiers = PUBLIC | OVERRIDE;
|
||||
onTransact->returnType = BOOLEAN_TYPE;
|
||||
onTransact->name = "onTransact";
|
||||
onTransact->parameters.push_back(this->transact_code);
|
||||
onTransact->parameters.push_back(this->transact_data);
|
||||
onTransact->parameters.push_back(this->transact_reply);
|
||||
onTransact->parameters.push_back(this->transact_flags);
|
||||
onTransact->statements = new StatementBlock;
|
||||
onTransact->exceptions.push_back(REMOTE_EXCEPTION_TYPE);
|
||||
this->elements.push_back(onTransact);
|
||||
this->transact_switch = new SwitchStatement(this->transact_code);
|
||||
|
||||
onTransact->statements->Add(this->transact_switch);
|
||||
MethodCall* superCall = new MethodCall(SUPER_VALUE, "onTransact", 4,
|
||||
this->transact_code, this->transact_data,
|
||||
this->transact_reply, this->transact_flags);
|
||||
onTransact->statements->Add(new ReturnStatement(superCall));
|
||||
}
|
||||
|
||||
StubClass::~StubClass()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
StubClass::make_as_interface(Type *interfaceType)
|
||||
{
|
||||
Variable* obj = new Variable(IBINDER_TYPE, "obj");
|
||||
|
||||
Method* m = new Method;
|
||||
m->comment = "/**\n * Cast an IBinder object into an ";
|
||||
m->comment += interfaceType->QualifiedName();
|
||||
m->comment += " interface,\n";
|
||||
m->comment += " * generating a proxy if needed.\n */";
|
||||
m->modifiers = PUBLIC | STATIC;
|
||||
m->returnType = interfaceType;
|
||||
m->name = "asInterface";
|
||||
m->parameters.push_back(obj);
|
||||
m->statements = new StatementBlock;
|
||||
|
||||
IfStatement* ifstatement = new IfStatement();
|
||||
ifstatement->expression = new Comparison(obj, "==", NULL_VALUE);
|
||||
ifstatement->statements = new StatementBlock;
|
||||
ifstatement->statements->Add(new ReturnStatement(NULL_VALUE));
|
||||
m->statements->Add(ifstatement);
|
||||
|
||||
// IInterface iin = obj.queryLocalInterface(DESCRIPTOR)
|
||||
MethodCall* queryLocalInterface = new MethodCall(obj, "queryLocalInterface");
|
||||
queryLocalInterface->arguments.push_back(new LiteralExpression("DESCRIPTOR"));
|
||||
IInterfaceType* iinType = new IInterfaceType();
|
||||
Variable *iin = new Variable(iinType, "iin");
|
||||
VariableDeclaration* iinVd = new VariableDeclaration(iin, queryLocalInterface, NULL);
|
||||
m->statements->Add(iinVd);
|
||||
|
||||
// Ensure the instance type of the local object is as expected.
|
||||
// One scenario where this is needed is if another package (with a
|
||||
// different class loader) runs in the same process as the service.
|
||||
|
||||
// if (iin != null && iin instanceof <interfaceType>) return (<interfaceType>) iin;
|
||||
Comparison* iinNotNull = new Comparison(iin, "!=", NULL_VALUE);
|
||||
Comparison* instOfCheck = new Comparison(iin, " instanceof ",
|
||||
new LiteralExpression(interfaceType->QualifiedName()));
|
||||
IfStatement* instOfStatement = new IfStatement();
|
||||
instOfStatement->expression = new Comparison(iinNotNull, "&&", instOfCheck);
|
||||
instOfStatement->statements = new StatementBlock;
|
||||
instOfStatement->statements->Add(new ReturnStatement(new Cast(interfaceType, iin)));
|
||||
m->statements->Add(instOfStatement);
|
||||
|
||||
string proxyType = interfaceType->QualifiedName();
|
||||
proxyType += ".Stub.Proxy";
|
||||
NewExpression* ne = new NewExpression(NAMES.Find(proxyType));
|
||||
ne->arguments.push_back(obj);
|
||||
m->statements->Add(new ReturnStatement(ne));
|
||||
|
||||
this->elements.push_back(m);
|
||||
}
|
||||
|
||||
|
||||
|
||||
// =================================================
|
||||
class ProxyClass : public Class
|
||||
{
|
||||
public:
|
||||
ProxyClass(Type* type, InterfaceType* interfaceType);
|
||||
virtual ~ProxyClass();
|
||||
|
||||
Variable* mRemote;
|
||||
bool mOneWay;
|
||||
};
|
||||
|
||||
ProxyClass::ProxyClass(Type* type, InterfaceType* interfaceType)
|
||||
:Class()
|
||||
{
|
||||
this->modifiers = PRIVATE | STATIC;
|
||||
this->what = Class::CLASS;
|
||||
this->type = type;
|
||||
this->interfaces.push_back(interfaceType);
|
||||
|
||||
mOneWay = interfaceType->OneWay();
|
||||
|
||||
// IBinder mRemote
|
||||
mRemote = new Variable(IBINDER_TYPE, "mRemote");
|
||||
this->elements.push_back(new Field(PRIVATE, mRemote));
|
||||
|
||||
// Proxy()
|
||||
Variable* remote = new Variable(IBINDER_TYPE, "remote");
|
||||
Method* ctor = new Method;
|
||||
ctor->name = "Proxy";
|
||||
ctor->statements = new StatementBlock;
|
||||
ctor->parameters.push_back(remote);
|
||||
ctor->statements->Add(new Assignment(mRemote, remote));
|
||||
this->elements.push_back(ctor);
|
||||
|
||||
// IBinder asBinder()
|
||||
Method* asBinder = new Method;
|
||||
asBinder->modifiers = PUBLIC | OVERRIDE;
|
||||
asBinder->returnType = IBINDER_TYPE;
|
||||
asBinder->name = "asBinder";
|
||||
asBinder->statements = new StatementBlock;
|
||||
asBinder->statements->Add(new ReturnStatement(mRemote));
|
||||
this->elements.push_back(asBinder);
|
||||
}
|
||||
|
||||
ProxyClass::~ProxyClass()
|
||||
{
|
||||
}
|
||||
|
||||
// =================================================
|
||||
static void
|
||||
generate_new_array(Type* t, StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel)
|
||||
{
|
||||
Variable* len = new Variable(INT_TYPE, v->name + "_length");
|
||||
addTo->Add(new VariableDeclaration(len, new MethodCall(parcel, "readInt")));
|
||||
IfStatement* lencheck = new IfStatement();
|
||||
lencheck->expression = new Comparison(len, "<", new LiteralExpression("0"));
|
||||
lencheck->statements->Add(new Assignment(v, NULL_VALUE));
|
||||
lencheck->elseif = new IfStatement();
|
||||
lencheck->elseif->statements->Add(new Assignment(v,
|
||||
new NewArrayExpression(t, len)));
|
||||
addTo->Add(lencheck);
|
||||
}
|
||||
|
||||
static void
|
||||
generate_write_to_parcel(Type* t, StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, int flags)
|
||||
{
|
||||
if (v->dimension == 0) {
|
||||
t->WriteToParcel(addTo, v, parcel, flags);
|
||||
}
|
||||
if (v->dimension == 1) {
|
||||
t->WriteArrayToParcel(addTo, v, parcel, flags);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
generate_create_from_parcel(Type* t, StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl)
|
||||
{
|
||||
if (v->dimension == 0) {
|
||||
t->CreateFromParcel(addTo, v, parcel, cl);
|
||||
}
|
||||
if (v->dimension == 1) {
|
||||
t->CreateArrayFromParcel(addTo, v, parcel, cl);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
generate_read_from_parcel(Type* t, StatementBlock* addTo, Variable* v,
|
||||
Variable* parcel, Variable** cl)
|
||||
{
|
||||
if (v->dimension == 0) {
|
||||
t->ReadFromParcel(addTo, v, parcel, cl);
|
||||
}
|
||||
if (v->dimension == 1) {
|
||||
t->ReadArrayFromParcel(addTo, v, parcel, cl);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
generate_method(const method_type* method, Class* interface,
|
||||
StubClass* stubClass, ProxyClass* proxyClass, int index)
|
||||
{
|
||||
arg_type* arg;
|
||||
int i;
|
||||
bool hasOutParams = false;
|
||||
|
||||
const bool oneway = proxyClass->mOneWay || method->oneway;
|
||||
|
||||
// == the TRANSACT_ constant =============================================
|
||||
string transactCodeName = "TRANSACTION_";
|
||||
transactCodeName += method->name.data;
|
||||
|
||||
char transactCodeValue[60];
|
||||
sprintf(transactCodeValue, "(android.os.IBinder.FIRST_CALL_TRANSACTION + %d)", index);
|
||||
|
||||
Field* transactCode = new Field(STATIC | FINAL,
|
||||
new Variable(INT_TYPE, transactCodeName));
|
||||
transactCode->value = transactCodeValue;
|
||||
stubClass->elements.push_back(transactCode);
|
||||
|
||||
// == the declaration in the interface ===================================
|
||||
Method* decl = new Method;
|
||||
decl->comment = gather_comments(method->comments_token->extra);
|
||||
decl->modifiers = PUBLIC;
|
||||
decl->returnType = NAMES.Search(method->type.type.data);
|
||||
decl->returnTypeDimension = method->type.dimension;
|
||||
decl->name = method->name.data;
|
||||
|
||||
arg = method->args;
|
||||
while (arg != NULL) {
|
||||
decl->parameters.push_back(new Variable(
|
||||
NAMES.Search(arg->type.type.data), arg->name.data,
|
||||
arg->type.dimension));
|
||||
arg = arg->next;
|
||||
}
|
||||
|
||||
decl->exceptions.push_back(REMOTE_EXCEPTION_TYPE);
|
||||
|
||||
interface->elements.push_back(decl);
|
||||
|
||||
// == the stub method ====================================================
|
||||
|
||||
Case* c = new Case(transactCodeName);
|
||||
|
||||
MethodCall* realCall = new MethodCall(THIS_VALUE, method->name.data);
|
||||
|
||||
// interface token validation is the very first thing we do
|
||||
c->statements->Add(new MethodCall(stubClass->transact_data,
|
||||
"enforceInterface", 1, new LiteralExpression("DESCRIPTOR")));
|
||||
|
||||
// args
|
||||
Variable* cl = NULL;
|
||||
VariableFactory stubArgs("_arg");
|
||||
arg = method->args;
|
||||
while (arg != NULL) {
|
||||
Type* t = NAMES.Search(arg->type.type.data);
|
||||
Variable* v = stubArgs.Get(t);
|
||||
v->dimension = arg->type.dimension;
|
||||
|
||||
c->statements->Add(new VariableDeclaration(v));
|
||||
|
||||
if (convert_direction(arg->direction.data) & IN_PARAMETER) {
|
||||
generate_create_from_parcel(t, c->statements, v,
|
||||
stubClass->transact_data, &cl);
|
||||
} else {
|
||||
if (arg->type.dimension == 0) {
|
||||
c->statements->Add(new Assignment(v, new NewExpression(v->type)));
|
||||
}
|
||||
else if (arg->type.dimension == 1) {
|
||||
generate_new_array(v->type, c->statements, v,
|
||||
stubClass->transact_data);
|
||||
}
|
||||
else {
|
||||
fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__,
|
||||
__LINE__);
|
||||
}
|
||||
}
|
||||
|
||||
realCall->arguments.push_back(v);
|
||||
|
||||
arg = arg->next;
|
||||
}
|
||||
|
||||
// the real call
|
||||
Variable* _result = NULL;
|
||||
if (0 == strcmp(method->type.type.data, "void")) {
|
||||
c->statements->Add(realCall);
|
||||
|
||||
if (!oneway) {
|
||||
// report that there were no exceptions
|
||||
MethodCall* ex = new MethodCall(stubClass->transact_reply,
|
||||
"writeNoException", 0);
|
||||
c->statements->Add(ex);
|
||||
}
|
||||
} else {
|
||||
_result = new Variable(decl->returnType, "_result",
|
||||
decl->returnTypeDimension);
|
||||
c->statements->Add(new VariableDeclaration(_result, realCall));
|
||||
|
||||
if (!oneway) {
|
||||
// report that there were no exceptions
|
||||
MethodCall* ex = new MethodCall(stubClass->transact_reply,
|
||||
"writeNoException", 0);
|
||||
c->statements->Add(ex);
|
||||
}
|
||||
|
||||
// marshall the return value
|
||||
generate_write_to_parcel(decl->returnType, c->statements, _result,
|
||||
stubClass->transact_reply,
|
||||
Type::PARCELABLE_WRITE_RETURN_VALUE);
|
||||
}
|
||||
|
||||
// out parameters
|
||||
i = 0;
|
||||
arg = method->args;
|
||||
while (arg != NULL) {
|
||||
Type* t = NAMES.Search(arg->type.type.data);
|
||||
Variable* v = stubArgs.Get(i++);
|
||||
|
||||
if (convert_direction(arg->direction.data) & OUT_PARAMETER) {
|
||||
generate_write_to_parcel(t, c->statements, v,
|
||||
stubClass->transact_reply,
|
||||
Type::PARCELABLE_WRITE_RETURN_VALUE);
|
||||
hasOutParams = true;
|
||||
}
|
||||
|
||||
arg = arg->next;
|
||||
}
|
||||
|
||||
// return true
|
||||
c->statements->Add(new ReturnStatement(TRUE_VALUE));
|
||||
stubClass->transact_switch->cases.push_back(c);
|
||||
|
||||
// == the proxy method ===================================================
|
||||
Method* proxy = new Method;
|
||||
proxy->comment = gather_comments(method->comments_token->extra);
|
||||
proxy->modifiers = PUBLIC | OVERRIDE;
|
||||
proxy->returnType = NAMES.Search(method->type.type.data);
|
||||
proxy->returnTypeDimension = method->type.dimension;
|
||||
proxy->name = method->name.data;
|
||||
proxy->statements = new StatementBlock;
|
||||
arg = method->args;
|
||||
while (arg != NULL) {
|
||||
proxy->parameters.push_back(new Variable(
|
||||
NAMES.Search(arg->type.type.data), arg->name.data,
|
||||
arg->type.dimension));
|
||||
arg = arg->next;
|
||||
}
|
||||
proxy->exceptions.push_back(REMOTE_EXCEPTION_TYPE);
|
||||
proxyClass->elements.push_back(proxy);
|
||||
|
||||
// the parcels
|
||||
Variable* _data = new Variable(PARCEL_TYPE, "_data");
|
||||
proxy->statements->Add(new VariableDeclaration(_data,
|
||||
new MethodCall(PARCEL_TYPE, "obtain")));
|
||||
Variable* _reply = NULL;
|
||||
if (!oneway) {
|
||||
_reply = new Variable(PARCEL_TYPE, "_reply");
|
||||
proxy->statements->Add(new VariableDeclaration(_reply,
|
||||
new MethodCall(PARCEL_TYPE, "obtain")));
|
||||
}
|
||||
|
||||
// the return value
|
||||
_result = NULL;
|
||||
if (0 != strcmp(method->type.type.data, "void")) {
|
||||
_result = new Variable(proxy->returnType, "_result",
|
||||
method->type.dimension);
|
||||
proxy->statements->Add(new VariableDeclaration(_result));
|
||||
}
|
||||
|
||||
// try and finally
|
||||
TryStatement* tryStatement = new TryStatement();
|
||||
proxy->statements->Add(tryStatement);
|
||||
FinallyStatement* finallyStatement = new FinallyStatement();
|
||||
proxy->statements->Add(finallyStatement);
|
||||
|
||||
// the interface identifier token: the DESCRIPTOR constant, marshalled as a string
|
||||
tryStatement->statements->Add(new MethodCall(_data, "writeInterfaceToken",
|
||||
1, new LiteralExpression("DESCRIPTOR")));
|
||||
|
||||
// the parameters
|
||||
arg = method->args;
|
||||
while (arg != NULL) {
|
||||
Type* t = NAMES.Search(arg->type.type.data);
|
||||
Variable* v = new Variable(t, arg->name.data, arg->type.dimension);
|
||||
int dir = convert_direction(arg->direction.data);
|
||||
if (dir == OUT_PARAMETER && arg->type.dimension != 0) {
|
||||
IfStatement* checklen = new IfStatement();
|
||||
checklen->expression = new Comparison(v, "==", NULL_VALUE);
|
||||
checklen->statements->Add(new MethodCall(_data, "writeInt", 1,
|
||||
new LiteralExpression("-1")));
|
||||
checklen->elseif = new IfStatement();
|
||||
checklen->elseif->statements->Add(new MethodCall(_data, "writeInt",
|
||||
1, new FieldVariable(v, "length")));
|
||||
tryStatement->statements->Add(checklen);
|
||||
}
|
||||
else if (dir & IN_PARAMETER) {
|
||||
generate_write_to_parcel(t, tryStatement->statements, v, _data, 0);
|
||||
}
|
||||
arg = arg->next;
|
||||
}
|
||||
|
||||
// the transact call
|
||||
MethodCall* call = new MethodCall(proxyClass->mRemote, "transact", 4,
|
||||
new LiteralExpression("Stub." + transactCodeName),
|
||||
_data, _reply ? _reply : NULL_VALUE,
|
||||
new LiteralExpression(
|
||||
oneway ? "android.os.IBinder.FLAG_ONEWAY" : "0"));
|
||||
tryStatement->statements->Add(call);
|
||||
|
||||
// throw back exceptions.
|
||||
if (_reply) {
|
||||
MethodCall* ex = new MethodCall(_reply, "readException", 0);
|
||||
tryStatement->statements->Add(ex);
|
||||
}
|
||||
|
||||
// returning and cleanup
|
||||
if (_reply != NULL) {
|
||||
if (_result != NULL) {
|
||||
generate_create_from_parcel(proxy->returnType,
|
||||
tryStatement->statements, _result, _reply, &cl);
|
||||
}
|
||||
|
||||
// the out/inout parameters
|
||||
arg = method->args;
|
||||
while (arg != NULL) {
|
||||
Type* t = NAMES.Search(arg->type.type.data);
|
||||
Variable* v = new Variable(t, arg->name.data, arg->type.dimension);
|
||||
if (convert_direction(arg->direction.data) & OUT_PARAMETER) {
|
||||
generate_read_from_parcel(t, tryStatement->statements,
|
||||
v, _reply, &cl);
|
||||
}
|
||||
arg = arg->next;
|
||||
}
|
||||
|
||||
finallyStatement->statements->Add(new MethodCall(_reply, "recycle"));
|
||||
}
|
||||
finallyStatement->statements->Add(new MethodCall(_data, "recycle"));
|
||||
|
||||
if (_result != NULL) {
|
||||
proxy->statements->Add(new ReturnStatement(_result));
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
generate_interface_descriptors(StubClass* stub, ProxyClass* proxy)
|
||||
{
|
||||
// the interface descriptor transaction handler
|
||||
Case* c = new Case("INTERFACE_TRANSACTION");
|
||||
c->statements->Add(new MethodCall(stub->transact_reply, "writeString",
|
||||
1, new LiteralExpression("DESCRIPTOR")));
|
||||
c->statements->Add(new ReturnStatement(TRUE_VALUE));
|
||||
stub->transact_switch->cases.push_back(c);
|
||||
|
||||
// and the proxy-side method returning the descriptor directly
|
||||
Method* getDesc = new Method;
|
||||
getDesc->modifiers = PUBLIC;
|
||||
getDesc->returnType = STRING_TYPE;
|
||||
getDesc->returnTypeDimension = 0;
|
||||
getDesc->name = "getInterfaceDescriptor";
|
||||
getDesc->statements = new StatementBlock;
|
||||
getDesc->statements->Add(new ReturnStatement(new LiteralExpression("DESCRIPTOR")));
|
||||
proxy->elements.push_back(getDesc);
|
||||
}
|
||||
|
||||
Class*
|
||||
generate_binder_interface_class(const interface_type* iface)
|
||||
{
|
||||
InterfaceType* interfaceType = static_cast<InterfaceType*>(
|
||||
NAMES.Find(iface->package, iface->name.data));
|
||||
|
||||
// the interface class
|
||||
Class* interface = new Class;
|
||||
interface->comment = gather_comments(iface->comments_token->extra);
|
||||
interface->modifiers = PUBLIC;
|
||||
interface->what = Class::INTERFACE;
|
||||
interface->type = interfaceType;
|
||||
interface->interfaces.push_back(IINTERFACE_TYPE);
|
||||
|
||||
// the stub inner class
|
||||
StubClass* stub = new StubClass(
|
||||
NAMES.Find(iface->package, append(iface->name.data, ".Stub").c_str()),
|
||||
interfaceType);
|
||||
interface->elements.push_back(stub);
|
||||
|
||||
// the proxy inner class
|
||||
ProxyClass* proxy = new ProxyClass(
|
||||
NAMES.Find(iface->package,
|
||||
append(iface->name.data, ".Stub.Proxy").c_str()),
|
||||
interfaceType);
|
||||
stub->elements.push_back(proxy);
|
||||
|
||||
// stub and proxy support for getInterfaceDescriptor()
|
||||
generate_interface_descriptors(stub, proxy);
|
||||
|
||||
// all the declared methods of the interface
|
||||
int index = 0;
|
||||
interface_item_type* item = iface->interface_items;
|
||||
while (item != NULL) {
|
||||
if (item->item_type == METHOD_TYPE) {
|
||||
method_type * method_item = (method_type*) item;
|
||||
generate_method(method_item, interface, stub, proxy, method_item->assigned_id);
|
||||
}
|
||||
item = item->next;
|
||||
index++;
|
||||
}
|
||||
|
||||
return interface;
|
||||
}
|
||||
|
||||
@@ -1,8 +0,0 @@
|
||||
#ifndef AIDL_MACROS_H_
|
||||
#define AIDL_MACROS_H_
|
||||
|
||||
#define DISALLOW_COPY_AND_ASSIGN(TypeName) \
|
||||
TypeName(const TypeName&); \
|
||||
void operator=(const TypeName&)
|
||||
|
||||
#endif // AIDL_MACROS_H_
|
||||
@@ -1,23 +0,0 @@
|
||||
#include "aidl.h"
|
||||
#include "options.h"
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
int
|
||||
main(int argc, const char **argv)
|
||||
{
|
||||
Options options;
|
||||
int result = parse_options(argc, argv, &options);
|
||||
if (result) {
|
||||
return result;
|
||||
}
|
||||
|
||||
switch (options.task) {
|
||||
case COMPILE_AIDL:
|
||||
return compile_aidl(options);
|
||||
case PREPROCESS_AIDL:
|
||||
return preprocess_aidl(options);
|
||||
}
|
||||
fprintf(stderr, "aidl: internal error\n");
|
||||
return 1;
|
||||
}
|
||||
@@ -1,150 +0,0 @@
|
||||
|
||||
#include "options.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
static int
|
||||
usage()
|
||||
{
|
||||
fprintf(stderr,
|
||||
"usage: aidl OPTIONS INPUT [OUTPUT]\n"
|
||||
" aidl --preprocess OUTPUT INPUT...\n"
|
||||
"\n"
|
||||
"OPTIONS:\n"
|
||||
" -I<DIR> search path for import statements.\n"
|
||||
" -d<FILE> generate dependency file.\n"
|
||||
" -a generate dependency file next to the output file with the name based on the input file.\n"
|
||||
" -p<FILE> file created by --preprocess to import.\n"
|
||||
" -o<FOLDER> base output folder for generated files.\n"
|
||||
" -b fail when trying to compile a parcelable.\n"
|
||||
"\n"
|
||||
"INPUT:\n"
|
||||
" An aidl interface file.\n"
|
||||
"\n"
|
||||
"OUTPUT:\n"
|
||||
" The generated interface files.\n"
|
||||
" If omitted and the -o option is not used, the input filename is used, with the .aidl extension changed to a .java extension.\n"
|
||||
" If the -o option is used, the generated files will be placed in the base output folder, under their package folder\n"
|
||||
);
|
||||
return 1;
|
||||
}
|
||||
|
||||
int
|
||||
parse_options(int argc, const char* const* argv, Options *options)
|
||||
{
|
||||
int i = 1;
|
||||
|
||||
if (argc >= 2 && 0 == strcmp(argv[1], "--preprocess")) {
|
||||
if (argc < 4) {
|
||||
return usage();
|
||||
}
|
||||
options->outputFileName = argv[2];
|
||||
for (int i=3; i<argc; i++) {
|
||||
options->filesToPreprocess.push_back(argv[i]);
|
||||
}
|
||||
options->task = PREPROCESS_AIDL;
|
||||
return 0;
|
||||
}
|
||||
|
||||
// OPTIONS
|
||||
while (i < argc) {
|
||||
const char* s = argv[i];
|
||||
int len = strlen(s);
|
||||
if (s[0] == '-') {
|
||||
if (len > 1) {
|
||||
// -I<system-import-path>
|
||||
if (s[1] == 'I') {
|
||||
if (len > 2) {
|
||||
options->importPaths.push_back(s+2);
|
||||
} else {
|
||||
fprintf(stderr, "-I option (%d) requires a path.\n", i);
|
||||
return usage();
|
||||
}
|
||||
}
|
||||
else if (s[1] == 'd') {
|
||||
if (len > 2) {
|
||||
options->depFileName = s+2;
|
||||
} else {
|
||||
fprintf(stderr, "-d option (%d) requires a file.\n", i);
|
||||
return usage();
|
||||
}
|
||||
}
|
||||
else if (s[1] == 'a') {
|
||||
options->autoDepFile = true;
|
||||
}
|
||||
else if (s[1] == 'p') {
|
||||
if (len > 2) {
|
||||
options->preprocessedFiles.push_back(s+2);
|
||||
} else {
|
||||
fprintf(stderr, "-p option (%d) requires a file.\n", i);
|
||||
return usage();
|
||||
}
|
||||
}
|
||||
else if (s[1] == 'o') {
|
||||
if (len > 2) {
|
||||
options->outputBaseFolder = s+2;
|
||||
} else {
|
||||
fprintf(stderr, "-o option (%d) requires a path.\n", i);
|
||||
return usage();
|
||||
}
|
||||
}
|
||||
else if (len == 2 && s[1] == 'b') {
|
||||
options->failOnParcelable = true;
|
||||
}
|
||||
else {
|
||||
// s[1] is not known
|
||||
fprintf(stderr, "unknown option (%d): %s\n", i, s);
|
||||
return usage();
|
||||
}
|
||||
} else {
|
||||
// len <= 1
|
||||
fprintf(stderr, "unknown option (%d): %s\n", i, s);
|
||||
return usage();
|
||||
}
|
||||
} else {
|
||||
// s[0] != '-'
|
||||
break;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
|
||||
// INPUT
|
||||
if (i < argc) {
|
||||
options->inputFileName = argv[i];
|
||||
i++;
|
||||
} else {
|
||||
fprintf(stderr, "INPUT required\n");
|
||||
return usage();
|
||||
}
|
||||
|
||||
// OUTPUT
|
||||
if (i < argc) {
|
||||
options->outputFileName = argv[i];
|
||||
i++;
|
||||
} else if (options->outputBaseFolder.length() == 0) {
|
||||
// copy input into output and change the extension from .aidl to .java
|
||||
options->outputFileName = options->inputFileName;
|
||||
string::size_type pos = options->outputFileName.size()-5;
|
||||
if (options->outputFileName.compare(pos, 5, ".aidl") == 0) { // 5 = strlen(".aidl")
|
||||
options->outputFileName.replace(pos, 5, ".java"); // 5 = strlen(".aidl")
|
||||
} else {
|
||||
fprintf(stderr, "INPUT is not an .aidl file.\n");
|
||||
return usage();
|
||||
}
|
||||
}
|
||||
|
||||
// anything remaining?
|
||||
if (i != argc) {
|
||||
fprintf(stderr, "unknown option%s:", (i==argc-1?(const char*)"":(const char*)"s"));
|
||||
for (; i<argc-1; i++) {
|
||||
fprintf(stderr, " %s", argv[i]);
|
||||
}
|
||||
fprintf(stderr, "\n");
|
||||
return usage();
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1,37 +0,0 @@
|
||||
#ifndef AIDL_OPTIONS_H_
|
||||
#define AIDL_OPTIONS_H_
|
||||
|
||||
#include <string.h>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
using std::string;
|
||||
using std::vector;
|
||||
|
||||
enum {
|
||||
COMPILE_AIDL,
|
||||
PREPROCESS_AIDL
|
||||
};
|
||||
|
||||
// This struct is the parsed version of the command line options
|
||||
struct Options
|
||||
{
|
||||
int task{COMPILE_AIDL};
|
||||
bool failOnParcelable{false};
|
||||
vector<string> importPaths;
|
||||
vector<string> preprocessedFiles;
|
||||
string inputFileName;
|
||||
string outputFileName;
|
||||
string outputBaseFolder;
|
||||
string depFileName;
|
||||
bool autoDepFile{false};
|
||||
|
||||
vector<string> filesToPreprocess;
|
||||
};
|
||||
|
||||
// takes the inputs from the command line and fills in the Options struct
|
||||
// Returns 0 on success, and nonzero on failure.
|
||||
// It also prints the usage statement on failure.
|
||||
int parse_options(int argc, const char* const* argv, Options *options);
|
||||
|
||||
#endif // AIDL_OPTIONS_H_
|
||||
@@ -1,54 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) 2015, The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include "options.h"
|
||||
|
||||
using std::vector;
|
||||
using std::string;
|
||||
|
||||
const char kPreprocessCommandOutputFile[] = "output_file_name";
|
||||
const char kPreprocessCommandInput1[] = "input1";
|
||||
const char kPreprocessCommandInput2[] = "input2";
|
||||
const char kPreprocessCommandInput3[] = "input3";
|
||||
const char* kPreprocessCommand[] = {
|
||||
"aidl", "--preprocess",
|
||||
kPreprocessCommandOutputFile,
|
||||
kPreprocessCommandInput1,
|
||||
kPreprocessCommandInput2,
|
||||
kPreprocessCommandInput3,
|
||||
};
|
||||
|
||||
TEST(OptionsTests, ParsesPreprocess) {
|
||||
Options options;
|
||||
const int argc = sizeof(kPreprocessCommand) / sizeof(*kPreprocessCommand);
|
||||
EXPECT_EQ(parse_options(argc, kPreprocessCommand, &options), 0);
|
||||
EXPECT_EQ(options.task, PREPROCESS_AIDL);
|
||||
EXPECT_EQ(options.failOnParcelable, false);
|
||||
EXPECT_EQ(options.importPaths.size(), 0u);
|
||||
EXPECT_EQ(options.preprocessedFiles.size(), 0u);
|
||||
EXPECT_EQ(options.inputFileName, string{""});
|
||||
EXPECT_EQ(options.outputFileName, string{kPreprocessCommandOutputFile});
|
||||
EXPECT_EQ(options.autoDepFile, false);
|
||||
const vector<string> expected_input{kPreprocessCommandInput1,
|
||||
kPreprocessCommandInput2,
|
||||
kPreprocessCommandInput3};
|
||||
EXPECT_EQ(options.filesToPreprocess, expected_input);
|
||||
}
|
||||
@@ -1,26 +0,0 @@
|
||||
/*
|
||||
* Copyright 2015, The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef AIDL_OS_H_
|
||||
#define AIDL_OS_H_
|
||||
|
||||
#if defined(_WIN32)
|
||||
#define OS_PATH_SEPARATOR '\\'
|
||||
#else
|
||||
#define OS_PATH_SEPARATOR '/'
|
||||
#endif
|
||||
|
||||
#endif // AIDL_OS_H_
|
||||
@@ -1,58 +0,0 @@
|
||||
#include <unistd.h>
|
||||
#include "search_path.h"
|
||||
#include "options.h"
|
||||
#include "os.h"
|
||||
#include <string.h>
|
||||
|
||||
#ifdef _WIN32
|
||||
#include <io.h>
|
||||
#endif
|
||||
|
||||
static vector<string> g_importPaths;
|
||||
|
||||
void
|
||||
set_import_paths(const vector<string>& importPaths)
|
||||
{
|
||||
g_importPaths = importPaths;
|
||||
}
|
||||
|
||||
char*
|
||||
find_import_file(const char* given)
|
||||
{
|
||||
string expected = given;
|
||||
|
||||
int N = expected.length();
|
||||
for (int i=0; i<N; i++) {
|
||||
char c = expected[i];
|
||||
if (c == '.') {
|
||||
expected[i] = OS_PATH_SEPARATOR;
|
||||
}
|
||||
}
|
||||
expected += ".aidl";
|
||||
|
||||
vector<string>& paths = g_importPaths;
|
||||
for (vector<string>::iterator it=paths.begin(); it!=paths.end(); it++) {
|
||||
string f = *it;
|
||||
if (f.size() == 0) {
|
||||
f = ".";
|
||||
f += OS_PATH_SEPARATOR;
|
||||
}
|
||||
else if (f[f.size()-1] != OS_PATH_SEPARATOR) {
|
||||
f += OS_PATH_SEPARATOR;
|
||||
}
|
||||
f.append(expected);
|
||||
|
||||
#ifdef _WIN32
|
||||
/* check that the file exists and is not write-only */
|
||||
if (0 == _access(f.c_str(), 0) && /* mode 0=exist */
|
||||
0 == _access(f.c_str(), 4) ) { /* mode 4=readable */
|
||||
#else
|
||||
if (0 == access(f.c_str(), R_OK)) {
|
||||
#endif
|
||||
return strdup(f.c_str());
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -1,25 +0,0 @@
|
||||
#ifndef AIDL_SEARCH_PATH_H_
|
||||
#define AIDL_SEARCH_PATH_H_
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#if __cplusplus
|
||||
#include <vector>
|
||||
#include <string>
|
||||
|
||||
using std::string;
|
||||
using std::vector;
|
||||
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
// returns a FILE* and the char* for the file that it found
|
||||
// given is the class name we're looking for
|
||||
char* find_import_file(const char* given);
|
||||
|
||||
#if __cplusplus
|
||||
}; // extern "C"
|
||||
void set_import_paths(const vector<string>& importPaths);
|
||||
#endif
|
||||
|
||||
#endif // AIDL_SEARCH_PATH_H_
|
||||
@@ -1,6 +0,0 @@
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
::testing::InitGoogleTest(&argc, argv);
|
||||
return RUN_ALL_TESTS();
|
||||
}
|
||||
@@ -1,165 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) 2015, The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include <memory>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
#include <base/logging.h>
|
||||
#include <base/files/file_path.h>
|
||||
#include <base/files/file_util.h>
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include "aidl.h"
|
||||
#include "options.h"
|
||||
#include "tests/test_data.h"
|
||||
|
||||
using base::FilePath;
|
||||
using std::string;
|
||||
using std::unique_ptr;
|
||||
using std::vector;
|
||||
|
||||
using namespace aidl::test_data;
|
||||
|
||||
namespace {
|
||||
|
||||
const char kDiffTemplate[] = "diff %s %s";
|
||||
const char kStubInterfaceTemplate[] = "package %s;\ninterface %s { }";
|
||||
const char kStubParcelableTemplate[] = "package %s;\nparcelable %s;";
|
||||
|
||||
FilePath GetPathForPackageClass(const char* package_class,
|
||||
const char* extension) {
|
||||
string rel_path{package_class};
|
||||
for (char& c : rel_path) {
|
||||
if (c == '.') {
|
||||
c = FilePath::kSeparators[0];
|
||||
}
|
||||
}
|
||||
rel_path += extension;
|
||||
return FilePath(rel_path);
|
||||
}
|
||||
|
||||
void SplitPackageClass(const string& package_class,
|
||||
FilePath* rel_path,
|
||||
string* package,
|
||||
string* class_name) {
|
||||
*package = string{package_class, 0, package_class.rfind('.')};
|
||||
*class_name = string{package_class, package_class.rfind('.') + 1};
|
||||
*rel_path = GetPathForPackageClass(package_class.c_str(), ".aidl");
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
class EndToEndTest : public ::testing::Test {
|
||||
protected:
|
||||
virtual void SetUp() {
|
||||
ASSERT_TRUE(base::CreateNewTempDirectory(
|
||||
string{"end_to_end_testsyyyy"}, &tmpDir_));
|
||||
inputDir_ = tmpDir_.Append("input");
|
||||
outputDir_ = tmpDir_.Append("output");
|
||||
ASSERT_TRUE(base::CreateDirectory(inputDir_));
|
||||
ASSERT_TRUE(base::CreateDirectory(outputDir_));
|
||||
}
|
||||
|
||||
virtual void TearDown() {
|
||||
ASSERT_TRUE(DeleteFile(tmpDir_, true))
|
||||
<< "Failed to remove temp directory: " << tmpDir_.value();
|
||||
}
|
||||
|
||||
FilePath CreateInputFile(const FilePath& relative_path,
|
||||
const char contents[],
|
||||
int size) {
|
||||
const FilePath created_file = inputDir_.Append(relative_path);
|
||||
EXPECT_TRUE(base::CreateDirectory(created_file.DirName()));
|
||||
EXPECT_TRUE(base::WriteFile(created_file, contents, size));
|
||||
return created_file;
|
||||
}
|
||||
|
||||
void CreateStubAidlFile(const string& package_class,
|
||||
const char* file_template) {
|
||||
string package, class_name;
|
||||
FilePath rel_path;
|
||||
SplitPackageClass(package_class, &rel_path, &package, &class_name);
|
||||
const size_t buf_len =
|
||||
strlen(file_template) + package.length() + class_name.length() + 1;
|
||||
unique_ptr<char[]> contents(new char[buf_len]);
|
||||
const int written = snprintf(contents.get(), buf_len, file_template,
|
||||
package.c_str(), class_name.c_str());
|
||||
EXPECT_GT(written, 0);
|
||||
CreateInputFile(rel_path, contents.get(), written);
|
||||
}
|
||||
|
||||
void WriteStubAidls(const char** parcelables, const char** interfaces) {
|
||||
while (*parcelables) {
|
||||
CreateStubAidlFile(string{*parcelables}, kStubParcelableTemplate);
|
||||
++parcelables;
|
||||
}
|
||||
while (*interfaces) {
|
||||
CreateStubAidlFile(string{*interfaces}, kStubInterfaceTemplate);
|
||||
++interfaces;
|
||||
}
|
||||
}
|
||||
|
||||
void CheckFileContents(const FilePath& rel_path,
|
||||
const string& expected_content) {
|
||||
string actual_contents;
|
||||
FilePath actual_path = outputDir_.Append(rel_path);
|
||||
if (!ReadFileToString(actual_path, &actual_contents)) {
|
||||
FAIL() << "Failed to read expected output file: " << rel_path.value();
|
||||
}
|
||||
// Generated .java files mention the "original" file as part of their
|
||||
// comment header. Thus we look for expected_content being a substring.
|
||||
if (actual_contents.find(expected_content) == string::npos) {
|
||||
// When the match fails, display a diff of what's wrong. This greatly
|
||||
// aids in debugging.
|
||||
FilePath expected_path;
|
||||
EXPECT_TRUE(CreateTemporaryFileInDir(tmpDir_, &expected_path));
|
||||
base::WriteFile(expected_path, expected_content.c_str(),
|
||||
expected_content.length());
|
||||
const size_t buf_len =
|
||||
strlen(kDiffTemplate) + actual_path.value().length() +
|
||||
expected_path.value().length() + 1;
|
||||
unique_ptr<char[]> diff_cmd(new char[buf_len]);
|
||||
EXPECT_GT(snprintf(diff_cmd.get(), buf_len, kDiffTemplate,
|
||||
expected_path.value().c_str(),
|
||||
actual_path.value().c_str()), 0);
|
||||
system(diff_cmd.get());
|
||||
FAIL() << "Actual contents of " << rel_path.value()
|
||||
<< " did not match expected content";
|
||||
}
|
||||
}
|
||||
|
||||
FilePath tmpDir_;
|
||||
FilePath inputDir_;
|
||||
FilePath outputDir_;
|
||||
};
|
||||
|
||||
TEST_F(EndToEndTest, IExampleInterface) {
|
||||
Options options;
|
||||
options.failOnParcelable = true;
|
||||
options.importPaths.push_back(inputDir_.value());
|
||||
options.inputFileName =
|
||||
CreateInputFile(GetPathForPackageClass(kIExampleInterfaceClass, ".aidl"),
|
||||
kIExampleInterfaceContents,
|
||||
strlen(kIExampleInterfaceContents)).value();
|
||||
options.autoDepFile = true;
|
||||
options.outputBaseFolder = outputDir_.value();
|
||||
WriteStubAidls(kIExampleInterfaceParcelables, kIExampleInterfaceInterfaces);
|
||||
EXPECT_EQ(compile_aidl(options), 0);
|
||||
CheckFileContents(GetPathForPackageClass(kIExampleInterfaceClass, ".java"),
|
||||
kIExampleInterfaceJava);
|
||||
// We'd like to check the depends file, but it mentions unique file paths.
|
||||
}
|
||||
@@ -1,404 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) 2015, The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "tests/test_data.h"
|
||||
|
||||
namespace aidl {
|
||||
namespace test_data {
|
||||
|
||||
const char kIExampleInterfaceClass[] = "android.test.IExampleInterface";
|
||||
|
||||
const char* kIExampleInterfaceParcelables[] = {
|
||||
"android.foo.ExampleParcelable",
|
||||
"android.test.ExampleParcelable2",
|
||||
nullptr,
|
||||
};
|
||||
|
||||
const char* kIExampleInterfaceInterfaces[] = {
|
||||
"android.bar.IAuxInterface",
|
||||
"android.test.IAuxInterface2",
|
||||
nullptr,
|
||||
};
|
||||
|
||||
const char kIExampleInterfaceContents[] = R"(
|
||||
package android.test;
|
||||
|
||||
import android.foo.ExampleParcelable;
|
||||
import android.test.ExampleParcelable2;
|
||||
import android.bar.IAuxInterface;
|
||||
import android.test.IAuxInterface2;
|
||||
|
||||
interface IExampleInterface {
|
||||
boolean isEnabled();
|
||||
int getState();
|
||||
String getAddress();
|
||||
|
||||
ExampleParcelable[] getParcelables();
|
||||
|
||||
boolean setScanMode(int mode, int duration);
|
||||
|
||||
void registerBinder(IAuxInterface foo);
|
||||
IExampleInterface getRecursiveBinder();
|
||||
|
||||
int takesAnInterface(in IAuxInterface2 arg);
|
||||
int takesAParcelable(in ExampleParcelable2 arg);
|
||||
}
|
||||
)";
|
||||
|
||||
const char kIExampleInterfaceDeps[] =
|
||||
R"(/tmp/.org.chromium.Chromium.Cdq7YZ/output/android/test/IExampleInterface.java: \
|
||||
/tmp/.org.chromium.Chromium.Cdq7YZ/input/android/test/IExampleInterface.aidl \
|
||||
/tmp/.org.chromium.Chromium.Cdq7YZ/input/android/foo/ExampleParcelable.aidl \
|
||||
/tmp/.org.chromium.Chromium.Cdq7YZ/input/android/test/ExampleParcelable2.aidl \
|
||||
/tmp/.org.chromium.Chromium.Cdq7YZ/input/android/bar/IAuxInterface.aidl \
|
||||
/tmp/.org.chromium.Chromium.Cdq7YZ/input/android/test/IAuxInterface2.aidl
|
||||
|
||||
/tmp/.org.chromium.Chromium.Cdq7YZ/input/android/test/IExampleInterface.aidl :
|
||||
/tmp/.org.chromium.Chromium.Cdq7YZ/input/android/foo/ExampleParcelable.aidl :
|
||||
/tmp/.org.chromium.Chromium.Cdq7YZ/input/android/test/ExampleParcelable2.aidl :
|
||||
/tmp/.org.chromium.Chromium.Cdq7YZ/input/android/bar/IAuxInterface.aidl :
|
||||
/tmp/.org.chromium.Chromium.Cdq7YZ/input/android/test/IAuxInterface2.aidl :)";
|
||||
|
||||
const char kIExampleInterfaceJava[] =
|
||||
R"(package android.test;
|
||||
public interface IExampleInterface extends android.os.IInterface
|
||||
{
|
||||
/** Local-side IPC implementation stub class. */
|
||||
public static abstract class Stub extends android.os.Binder implements android.test.IExampleInterface
|
||||
{
|
||||
private static final java.lang.String DESCRIPTOR = "android.test.IExampleInterface";
|
||||
/** Construct the stub at attach it to the interface. */
|
||||
public Stub()
|
||||
{
|
||||
this.attachInterface(this, DESCRIPTOR);
|
||||
}
|
||||
/**
|
||||
* Cast an IBinder object into an android.test.IExampleInterface interface,
|
||||
* generating a proxy if needed.
|
||||
*/
|
||||
public static android.test.IExampleInterface asInterface(android.os.IBinder obj)
|
||||
{
|
||||
if ((obj==null)) {
|
||||
return null;
|
||||
}
|
||||
android.os.IInterface iin = obj.queryLocalInterface(DESCRIPTOR);
|
||||
if (((iin!=null)&&(iin instanceof android.test.IExampleInterface))) {
|
||||
return ((android.test.IExampleInterface)iin);
|
||||
}
|
||||
return new android.test.IExampleInterface.Stub.Proxy(obj);
|
||||
}
|
||||
@Override public android.os.IBinder asBinder()
|
||||
{
|
||||
return this;
|
||||
}
|
||||
@Override public boolean onTransact(int code, android.os.Parcel data, android.os.Parcel reply, int flags) throws android.os.RemoteException
|
||||
{
|
||||
switch (code)
|
||||
{
|
||||
case INTERFACE_TRANSACTION:
|
||||
{
|
||||
reply.writeString(DESCRIPTOR);
|
||||
return true;
|
||||
}
|
||||
case TRANSACTION_isEnabled:
|
||||
{
|
||||
data.enforceInterface(DESCRIPTOR);
|
||||
boolean _result = this.isEnabled();
|
||||
reply.writeNoException();
|
||||
reply.writeInt(((_result)?(1):(0)));
|
||||
return true;
|
||||
}
|
||||
case TRANSACTION_getState:
|
||||
{
|
||||
data.enforceInterface(DESCRIPTOR);
|
||||
int _result = this.getState();
|
||||
reply.writeNoException();
|
||||
reply.writeInt(_result);
|
||||
return true;
|
||||
}
|
||||
case TRANSACTION_getAddress:
|
||||
{
|
||||
data.enforceInterface(DESCRIPTOR);
|
||||
java.lang.String _result = this.getAddress();
|
||||
reply.writeNoException();
|
||||
reply.writeString(_result);
|
||||
return true;
|
||||
}
|
||||
case TRANSACTION_getParcelables:
|
||||
{
|
||||
data.enforceInterface(DESCRIPTOR);
|
||||
android.foo.ExampleParcelable[] _result = this.getParcelables();
|
||||
reply.writeNoException();
|
||||
reply.writeTypedArray(_result, android.os.Parcelable.PARCELABLE_WRITE_RETURN_VALUE);
|
||||
return true;
|
||||
}
|
||||
case TRANSACTION_setScanMode:
|
||||
{
|
||||
data.enforceInterface(DESCRIPTOR);
|
||||
int _arg0;
|
||||
_arg0 = data.readInt();
|
||||
int _arg1;
|
||||
_arg1 = data.readInt();
|
||||
boolean _result = this.setScanMode(_arg0, _arg1);
|
||||
reply.writeNoException();
|
||||
reply.writeInt(((_result)?(1):(0)));
|
||||
return true;
|
||||
}
|
||||
case TRANSACTION_registerBinder:
|
||||
{
|
||||
data.enforceInterface(DESCRIPTOR);
|
||||
android.bar.IAuxInterface _arg0;
|
||||
_arg0 = android.bar.IAuxInterface.Stub.asInterface(data.readStrongBinder());
|
||||
this.registerBinder(_arg0);
|
||||
reply.writeNoException();
|
||||
return true;
|
||||
}
|
||||
case TRANSACTION_getRecursiveBinder:
|
||||
{
|
||||
data.enforceInterface(DESCRIPTOR);
|
||||
android.test.IExampleInterface _result = this.getRecursiveBinder();
|
||||
reply.writeNoException();
|
||||
reply.writeStrongBinder((((_result!=null))?(_result.asBinder()):(null)));
|
||||
return true;
|
||||
}
|
||||
case TRANSACTION_takesAnInterface:
|
||||
{
|
||||
data.enforceInterface(DESCRIPTOR);
|
||||
android.test.IAuxInterface2 _arg0;
|
||||
_arg0 = android.test.IAuxInterface2.Stub.asInterface(data.readStrongBinder());
|
||||
int _result = this.takesAnInterface(_arg0);
|
||||
reply.writeNoException();
|
||||
reply.writeInt(_result);
|
||||
return true;
|
||||
}
|
||||
case TRANSACTION_takesAParcelable:
|
||||
{
|
||||
data.enforceInterface(DESCRIPTOR);
|
||||
android.test.ExampleParcelable2 _arg0;
|
||||
if ((0!=data.readInt())) {
|
||||
_arg0 = android.test.ExampleParcelable2.CREATOR.createFromParcel(data);
|
||||
}
|
||||
else {
|
||||
_arg0 = null;
|
||||
}
|
||||
int _result = this.takesAParcelable(_arg0);
|
||||
reply.writeNoException();
|
||||
reply.writeInt(_result);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return super.onTransact(code, data, reply, flags);
|
||||
}
|
||||
private static class Proxy implements android.test.IExampleInterface
|
||||
{
|
||||
private android.os.IBinder mRemote;
|
||||
Proxy(android.os.IBinder remote)
|
||||
{
|
||||
mRemote = remote;
|
||||
}
|
||||
@Override public android.os.IBinder asBinder()
|
||||
{
|
||||
return mRemote;
|
||||
}
|
||||
public java.lang.String getInterfaceDescriptor()
|
||||
{
|
||||
return DESCRIPTOR;
|
||||
}
|
||||
@Override public boolean isEnabled() throws android.os.RemoteException
|
||||
{
|
||||
android.os.Parcel _data = android.os.Parcel.obtain();
|
||||
android.os.Parcel _reply = android.os.Parcel.obtain();
|
||||
boolean _result;
|
||||
try {
|
||||
_data.writeInterfaceToken(DESCRIPTOR);
|
||||
mRemote.transact(Stub.TRANSACTION_isEnabled, _data, _reply, 0);
|
||||
_reply.readException();
|
||||
_result = (0!=_reply.readInt());
|
||||
}
|
||||
finally {
|
||||
_reply.recycle();
|
||||
_data.recycle();
|
||||
}
|
||||
return _result;
|
||||
}
|
||||
@Override public int getState() throws android.os.RemoteException
|
||||
{
|
||||
android.os.Parcel _data = android.os.Parcel.obtain();
|
||||
android.os.Parcel _reply = android.os.Parcel.obtain();
|
||||
int _result;
|
||||
try {
|
||||
_data.writeInterfaceToken(DESCRIPTOR);
|
||||
mRemote.transact(Stub.TRANSACTION_getState, _data, _reply, 0);
|
||||
_reply.readException();
|
||||
_result = _reply.readInt();
|
||||
}
|
||||
finally {
|
||||
_reply.recycle();
|
||||
_data.recycle();
|
||||
}
|
||||
return _result;
|
||||
}
|
||||
@Override public java.lang.String getAddress() throws android.os.RemoteException
|
||||
{
|
||||
android.os.Parcel _data = android.os.Parcel.obtain();
|
||||
android.os.Parcel _reply = android.os.Parcel.obtain();
|
||||
java.lang.String _result;
|
||||
try {
|
||||
_data.writeInterfaceToken(DESCRIPTOR);
|
||||
mRemote.transact(Stub.TRANSACTION_getAddress, _data, _reply, 0);
|
||||
_reply.readException();
|
||||
_result = _reply.readString();
|
||||
}
|
||||
finally {
|
||||
_reply.recycle();
|
||||
_data.recycle();
|
||||
}
|
||||
return _result;
|
||||
}
|
||||
@Override public android.foo.ExampleParcelable[] getParcelables() throws android.os.RemoteException
|
||||
{
|
||||
android.os.Parcel _data = android.os.Parcel.obtain();
|
||||
android.os.Parcel _reply = android.os.Parcel.obtain();
|
||||
android.foo.ExampleParcelable[] _result;
|
||||
try {
|
||||
_data.writeInterfaceToken(DESCRIPTOR);
|
||||
mRemote.transact(Stub.TRANSACTION_getParcelables, _data, _reply, 0);
|
||||
_reply.readException();
|
||||
_result = _reply.createTypedArray(android.foo.ExampleParcelable.CREATOR);
|
||||
}
|
||||
finally {
|
||||
_reply.recycle();
|
||||
_data.recycle();
|
||||
}
|
||||
return _result;
|
||||
}
|
||||
@Override public boolean setScanMode(int mode, int duration) throws android.os.RemoteException
|
||||
{
|
||||
android.os.Parcel _data = android.os.Parcel.obtain();
|
||||
android.os.Parcel _reply = android.os.Parcel.obtain();
|
||||
boolean _result;
|
||||
try {
|
||||
_data.writeInterfaceToken(DESCRIPTOR);
|
||||
_data.writeInt(mode);
|
||||
_data.writeInt(duration);
|
||||
mRemote.transact(Stub.TRANSACTION_setScanMode, _data, _reply, 0);
|
||||
_reply.readException();
|
||||
_result = (0!=_reply.readInt());
|
||||
}
|
||||
finally {
|
||||
_reply.recycle();
|
||||
_data.recycle();
|
||||
}
|
||||
return _result;
|
||||
}
|
||||
@Override public void registerBinder(android.bar.IAuxInterface foo) throws android.os.RemoteException
|
||||
{
|
||||
android.os.Parcel _data = android.os.Parcel.obtain();
|
||||
android.os.Parcel _reply = android.os.Parcel.obtain();
|
||||
try {
|
||||
_data.writeInterfaceToken(DESCRIPTOR);
|
||||
_data.writeStrongBinder((((foo!=null))?(foo.asBinder()):(null)));
|
||||
mRemote.transact(Stub.TRANSACTION_registerBinder, _data, _reply, 0);
|
||||
_reply.readException();
|
||||
}
|
||||
finally {
|
||||
_reply.recycle();
|
||||
_data.recycle();
|
||||
}
|
||||
}
|
||||
@Override public android.test.IExampleInterface getRecursiveBinder() throws android.os.RemoteException
|
||||
{
|
||||
android.os.Parcel _data = android.os.Parcel.obtain();
|
||||
android.os.Parcel _reply = android.os.Parcel.obtain();
|
||||
android.test.IExampleInterface _result;
|
||||
try {
|
||||
_data.writeInterfaceToken(DESCRIPTOR);
|
||||
mRemote.transact(Stub.TRANSACTION_getRecursiveBinder, _data, _reply, 0);
|
||||
_reply.readException();
|
||||
_result = android.test.IExampleInterface.Stub.asInterface(_reply.readStrongBinder());
|
||||
}
|
||||
finally {
|
||||
_reply.recycle();
|
||||
_data.recycle();
|
||||
}
|
||||
return _result;
|
||||
}
|
||||
@Override public int takesAnInterface(android.test.IAuxInterface2 arg) throws android.os.RemoteException
|
||||
{
|
||||
android.os.Parcel _data = android.os.Parcel.obtain();
|
||||
android.os.Parcel _reply = android.os.Parcel.obtain();
|
||||
int _result;
|
||||
try {
|
||||
_data.writeInterfaceToken(DESCRIPTOR);
|
||||
_data.writeStrongBinder((((arg!=null))?(arg.asBinder()):(null)));
|
||||
mRemote.transact(Stub.TRANSACTION_takesAnInterface, _data, _reply, 0);
|
||||
_reply.readException();
|
||||
_result = _reply.readInt();
|
||||
}
|
||||
finally {
|
||||
_reply.recycle();
|
||||
_data.recycle();
|
||||
}
|
||||
return _result;
|
||||
}
|
||||
@Override public int takesAParcelable(android.test.ExampleParcelable2 arg) throws android.os.RemoteException
|
||||
{
|
||||
android.os.Parcel _data = android.os.Parcel.obtain();
|
||||
android.os.Parcel _reply = android.os.Parcel.obtain();
|
||||
int _result;
|
||||
try {
|
||||
_data.writeInterfaceToken(DESCRIPTOR);
|
||||
if ((arg!=null)) {
|
||||
_data.writeInt(1);
|
||||
arg.writeToParcel(_data, 0);
|
||||
}
|
||||
else {
|
||||
_data.writeInt(0);
|
||||
}
|
||||
mRemote.transact(Stub.TRANSACTION_takesAParcelable, _data, _reply, 0);
|
||||
_reply.readException();
|
||||
_result = _reply.readInt();
|
||||
}
|
||||
finally {
|
||||
_reply.recycle();
|
||||
_data.recycle();
|
||||
}
|
||||
return _result;
|
||||
}
|
||||
}
|
||||
static final int TRANSACTION_isEnabled = (android.os.IBinder.FIRST_CALL_TRANSACTION + 0);
|
||||
static final int TRANSACTION_getState = (android.os.IBinder.FIRST_CALL_TRANSACTION + 1);
|
||||
static final int TRANSACTION_getAddress = (android.os.IBinder.FIRST_CALL_TRANSACTION + 2);
|
||||
static final int TRANSACTION_getParcelables = (android.os.IBinder.FIRST_CALL_TRANSACTION + 3);
|
||||
static final int TRANSACTION_setScanMode = (android.os.IBinder.FIRST_CALL_TRANSACTION + 4);
|
||||
static final int TRANSACTION_registerBinder = (android.os.IBinder.FIRST_CALL_TRANSACTION + 5);
|
||||
static final int TRANSACTION_getRecursiveBinder = (android.os.IBinder.FIRST_CALL_TRANSACTION + 6);
|
||||
static final int TRANSACTION_takesAnInterface = (android.os.IBinder.FIRST_CALL_TRANSACTION + 7);
|
||||
static final int TRANSACTION_takesAParcelable = (android.os.IBinder.FIRST_CALL_TRANSACTION + 8);
|
||||
}
|
||||
public boolean isEnabled() throws android.os.RemoteException;
|
||||
public int getState() throws android.os.RemoteException;
|
||||
public java.lang.String getAddress() throws android.os.RemoteException;
|
||||
public android.foo.ExampleParcelable[] getParcelables() throws android.os.RemoteException;
|
||||
public boolean setScanMode(int mode, int duration) throws android.os.RemoteException;
|
||||
public void registerBinder(android.bar.IAuxInterface foo) throws android.os.RemoteException;
|
||||
public android.test.IExampleInterface getRecursiveBinder() throws android.os.RemoteException;
|
||||
public int takesAnInterface(android.test.IAuxInterface2 arg) throws android.os.RemoteException;
|
||||
public int takesAParcelable(android.test.ExampleParcelable2 arg) throws android.os.RemoteException;
|
||||
})";
|
||||
|
||||
} // namespace test_data
|
||||
} // namespace aidl
|
||||
@@ -1,33 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) 2015, The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef AIDL_TESTS_TEST_DATA_H_
|
||||
#define AIDL_TESTS_TEST_DATA_H_
|
||||
|
||||
namespace aidl {
|
||||
namespace test_data {
|
||||
|
||||
extern const char kIExampleInterfaceClass[];
|
||||
extern const char kIExampleInterfaceContents[];
|
||||
extern const char* kIExampleInterfaceParcelables[];
|
||||
extern const char* kIExampleInterfaceInterfaces[];
|
||||
|
||||
extern const char kIExampleInterfaceDeps[];
|
||||
extern const char kIExampleInterfaceJava[];
|
||||
|
||||
} // namespace test_data
|
||||
} // namespace aidl
|
||||
#endif // AIDL_TESTS_TEST_DATA_H_
|
||||
Reference in New Issue
Block a user