summaryrefslogtreecommitdiffstats
path: root/tools/aidl
diff options
context:
space:
mode:
authorLuis Vidal <lvidal@cyngn.com>2016-06-22 17:17:52 -0700
committerLuis Vidal <lvidal@cyngn.com>2016-07-15 11:03:01 -0700
commitedd2da9b5bf098db9505e84033ca45fda688fe7f (patch)
tree9501d504941cbd7c1f33a0395afe117e34f0a66a /tools/aidl
parentdf41276baeda099bdfe95c59af43c65dee2763eb (diff)
downloadframeworks_base-edd2da9b5bf098db9505e84033ca45fda688fe7f.zip
frameworks_base-edd2da9b5bf098db9505e84033ca45fda688fe7f.tar.gz
frameworks_base-edd2da9b5bf098db9505e84033ca45fda688fe7f.tar.bz2
AIDL: Add option to generate No-Op methods
Add the option to generate a default (no-op) implementation of an interface Change-Id: I2631e93c8b85e056cf928e9592342dc4466f293e
Diffstat (limited to 'tools/aidl')
-rw-r--r--tools/aidl/aidl.cpp14
-rw-r--r--tools/aidl/generate_java.cpp4
-rw-r--r--tools/aidl/generate_java.h7
-rw-r--r--tools/aidl/generate_java_binder.cpp93
-rw-r--r--tools/aidl/options.cpp4
-rw-r--r--tools/aidl/options.h1
6 files changed, 115 insertions, 8 deletions
diff --git a/tools/aidl/aidl.cpp b/tools/aidl/aidl.cpp
index cd4fbe5..d37a946 100644
--- a/tools/aidl/aidl.cpp
+++ b/tools/aidl/aidl.cpp
@@ -345,6 +345,13 @@ gather_types(const char* filename, document_item_type* items)
name, Type::GENERATED, false, false, false,
filename, c->name.lineno);
NAMES.Add(proxy);
+
+ name = c->name.data;
+ name += ".NoOp";
+ Type* noOp = new Type(c->package ? c->package : "",
+ name, Type::GENERATED, false, false, false,
+ filename, c->name.lineno);
+ NAMES.Add(noOp);
}
else if (items->item_type == INTERFACE_TYPE_RPC) {
// for interfaces, also add the service base type, we don't
@@ -1064,8 +1071,13 @@ compile_aidl(Options& options)
// make sure the folders of the output file all exists
check_outputFilePath(options.outputFileName);
+ int flags = 0;
+ if (options.generateNoOpMethods) {
+ flags |= GENERATE_NO_OP_CLASS;
+ }
+
err = generate_java(options.outputFileName, options.inputFileName.c_str(),
- (interface_type*)mainDoc);
+ (interface_type*)mainDoc, flags);
return err;
}
diff --git a/tools/aidl/generate_java.cpp b/tools/aidl/generate_java.cpp
index 9e57407..8817461 100644
--- a/tools/aidl/generate_java.cpp
+++ b/tools/aidl/generate_java.cpp
@@ -59,12 +59,12 @@ append(const char* a, const char* b)
// =================================================
int
generate_java(const string& filename, const string& originalSrc,
- interface_type* iface)
+ interface_type* iface, int flags)
{
Class* cl;
if (iface->document_item.item_type == INTERFACE_TYPE_BINDER) {
- cl = generate_binder_interface_class(iface);
+ cl = generate_binder_interface_class(iface, flags);
}
else if (iface->document_item.item_type == INTERFACE_TYPE_RPC) {
cl = generate_rpc_interface_class(iface);
diff --git a/tools/aidl/generate_java.h b/tools/aidl/generate_java.h
index 4bfcfeb..45b2703 100644
--- a/tools/aidl/generate_java.h
+++ b/tools/aidl/generate_java.h
@@ -9,9 +9,9 @@
using namespace std;
int generate_java(const string& filename, const string& originalSrc,
- interface_type* iface);
+ interface_type* iface, int flags);
-Class* generate_binder_interface_class(const interface_type* iface);
+Class* generate_binder_interface_class(const interface_type* iface, int flags);
Class* generate_rpc_interface_class(const interface_type* iface);
string gather_comments(extra_text_type* extra);
@@ -29,5 +29,8 @@ private:
int m_index;
};
+//Set of flags that can be passed to generate_java
+#define GENERATE_NO_OP_CLASS 1 << 0
+
#endif // GENERATE_JAVA_H
diff --git a/tools/aidl/generate_java_binder.cpp b/tools/aidl/generate_java_binder.cpp
index 1b538ca..48ac027 100644
--- a/tools/aidl/generate_java_binder.cpp
+++ b/tools/aidl/generate_java_binder.cpp
@@ -194,6 +194,36 @@ ProxyClass::~ProxyClass()
}
// =================================================
+class DefaultNoOpClass : public Class {
+public:
+ DefaultNoOpClass(Type* type, InterfaceType* interfaceType);
+ virtual ~DefaultNoOpClass();
+};
+
+DefaultNoOpClass::DefaultNoOpClass(Type* type, InterfaceType* interfaceType)
+ :Class()
+{
+ this->comment = "/** No-Op implementation */";
+ this->comment += "\n/** @hide */";
+ this->modifiers = PUBLIC | STATIC;
+ this->what = Class::CLASS;
+ this->type = type;
+ this->interfaces.push_back(interfaceType);
+
+ // 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(NULL_VALUE));
+ this->elements.push_back(asBinder);
+}
+
+DefaultNoOpClass::~DefaultNoOpClass() {
+}
+
+// =================================================
static void
generate_new_array(Type* t, StatementBlock* addTo, Variable* v,
Variable* parcel)
@@ -245,10 +275,24 @@ generate_read_from_parcel(Type* t, StatementBlock* addTo, Variable* v,
}
}
+static bool
+is_numeric_java_type(const char* str) {
+ static const char* KEYWORDS[] = { "int", "byte", "char", "float", "double",
+ "short", "long", NULL };
+ const char** k = KEYWORDS;
+ while (*k) {
+ if (0 == strcmp(str, *k)) {
+ return true;
+ }
+ k++;
+ }
+ return false;
+}
static void
generate_method(const method_type* method, Class* interface,
- StubClass* stubClass, ProxyClass* proxyClass, int index)
+ StubClass* stubClass, ProxyClass* proxyClass, DefaultNoOpClass* noOpClass,
+ int index)
{
arg_type* arg;
int i;
@@ -294,6 +338,39 @@ generate_method(const method_type* method, Class* interface,
interface->elements.push_back(decl);
+ // == the no-op method ===================================================
+ if (noOpClass != NULL) {
+ Method* noOpMethod = new Method;
+ noOpMethod->comment = gather_comments(method->comments_token->extra);
+ noOpMethod->modifiers = OVERRIDE | PUBLIC;
+ noOpMethod->returnType = NAMES.Search(method->type.type.data);
+ noOpMethod->returnTypeDimension = method->type.dimension;
+ noOpMethod->name = method->name.data;
+ noOpMethod->statements = new StatementBlock;
+
+ arg = method->args;
+ while (arg != NULL) {
+ noOpMethod->parameters.push_back(new Variable(
+ NAMES.Search(arg->type.type.data), arg->name.data,
+ arg->type.dimension));
+ arg = arg->next;
+ }
+
+ if (0 != strcmp(method->type.type.data, "void")) {
+ bool isNumeric = is_numeric_java_type(method->type.type.data);
+ bool isBoolean = 0 == strcmp(method->type.type.data, "boolean");
+
+ if (isNumeric && method->type.dimension == 0) {
+ noOpMethod->statements->Add(new ReturnStatement(new LiteralExpression("0")));
+ } else if (isBoolean && method->type.dimension == 0) {
+ noOpMethod->statements->Add(new ReturnStatement(FALSE_VALUE));
+ } else {
+ noOpMethod->statements->Add(new ReturnStatement(NULL_VALUE));
+ }
+ }
+ noOpMethod->exceptions.push_back(REMOTE_EXCEPTION_TYPE);
+ noOpClass->elements.push_back(noOpMethod);
+ }
// == the stub method ====================================================
Case* c = new Case(transactCodeName);
@@ -520,7 +597,7 @@ generate_interface_descriptors(StubClass* stub, ProxyClass* proxy)
}
Class*
-generate_binder_interface_class(const interface_type* iface)
+generate_binder_interface_class(const interface_type* iface, int flags)
{
InterfaceType* interfaceType = static_cast<InterfaceType*>(
NAMES.Find(iface->package, iface->name.data));
@@ -533,6 +610,15 @@ generate_binder_interface_class(const interface_type* iface)
interface->type = interfaceType;
interface->interfaces.push_back(IINTERFACE_TYPE);
+ // the No-Op inner class
+ DefaultNoOpClass* noOpClass = NULL;
+ if ((flags & GENERATE_NO_OP_CLASS) != 0) {
+ noOpClass = new DefaultNoOpClass(
+ NAMES.Find(iface->package, append(iface->name.data, ".NoOp").c_str()),
+ interfaceType);
+ interface->elements.push_back(noOpClass);
+ }
+
// the stub inner class
StubClass* stub = new StubClass(
NAMES.Find(iface->package, append(iface->name.data, ".Stub").c_str()),
@@ -555,7 +641,8 @@ generate_binder_interface_class(const interface_type* iface)
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);
+ generate_method(method_item, interface, stub, proxy, noOpClass,
+ method_item->assigned_id);
}
item = item->next;
index++;
diff --git a/tools/aidl/options.cpp b/tools/aidl/options.cpp
index 7b2daeb..9de1957 100644
--- a/tools/aidl/options.cpp
+++ b/tools/aidl/options.cpp
@@ -51,6 +51,7 @@ parse_options(int argc, const char* const* argv, Options *options)
options->task = COMPILE_AIDL;
options->failOnParcelable = false;
options->autoDepFile = false;
+ options->generateNoOpMethods = false;
// OPTIONS
while (i < argc) {
@@ -97,6 +98,9 @@ parse_options(int argc, const char* const* argv, Options *options)
else if (len == 2 && s[1] == 'b') {
options->failOnParcelable = true;
}
+ else if (s[1] == 'n') {
+ options->generateNoOpMethods = true;
+ }
else {
// s[1] is not known
fprintf(stderr, "unknown option (%d): %s\n", i, s);
diff --git a/tools/aidl/options.h b/tools/aidl/options.h
index 387e37d..969cc1c 100644
--- a/tools/aidl/options.h
+++ b/tools/aidl/options.h
@@ -24,6 +24,7 @@ struct Options
string outputBaseFolder;
string depFileName;
bool autoDepFile;
+ bool generateNoOpMethods;
vector<string> filesToPreprocess;
};