[-]
[+]
|
Changed |
_service:tar_git:libgbinder.changes
|
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder.spec
^
|
|
[-]
[+]
|
Changed |
_service
^
|
@@ -2,6 +2,6 @@
<service name="tar_git">
<param name="url">https://github.com/mer-hybris/libgbinder.git</param>
<param name="branch">master</param>
- <param name="revision">1.0.46</param>
+ <param name="revision">1.1.10</param>
</service>
</services>
\ No newline at end of file
|
[-]
[+]
|
Deleted |
_service:tar_git:libgbinder-1.0.46.tar.bz2/src/gbinder_defaultservicemanager.c
^
|
@@ -1,321 +0,0 @@
-/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
- *
- * You may use this file under the terms of BSD license as follows:
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
- * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
- * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
- * THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "gbinder_servicemanager_p.h"
-#include "gbinder_rpc_protocol.h"
-#include "gbinder_servicepoll.h"
-#include "gbinder_eventloop_p.h"
-#include "gbinder_log.h"
-
-#include <gbinder_client.h>
-#include <gbinder_local_request.h>
-#include <gbinder_remote_reply.h>
-
-#include <gutil_macros.h>
-
-#include <errno.h>
-#include <pthread.h>
-
-typedef struct gbinder_defaultservicemanager_watch {
- GBinderServicePoll* poll;
- char* name;
- gulong handler_id;
- GBinderEventLoopTimeout* notify;
-} GBinderDefaultServiceManagerWatch;
-
-typedef GBinderServiceManagerClass GBinderDefaultServiceManagerClass;
-typedef struct gbinder_defaultservicemanager {
- GBinderServiceManager manager;
- GBinderServicePoll* poll;
- GHashTable* watch_table;
-} GBinderDefaultServiceManager;
-
-G_DEFINE_TYPE(GBinderDefaultServiceManager,
- gbinder_defaultservicemanager,
- GBINDER_TYPE_SERVICEMANAGER)
-
-#define PARENT_CLASS gbinder_defaultservicemanager_parent_class
-#define GBINDER_TYPE_DEFAULTSERVICEMANAGER \
- gbinder_defaultservicemanager_get_type()
-#define GBINDER_DEFAULTSERVICEMANAGER(obj) \
- G_TYPE_CHECK_INSTANCE_CAST((obj), GBINDER_TYPE_DEFAULTSERVICEMANAGER, \
- GBinderDefaultServiceManager)
-
-enum gbinder_defaultservicemanager_calls {
- GET_SERVICE_TRANSACTION = GBINDER_FIRST_CALL_TRANSACTION,
- CHECK_SERVICE_TRANSACTION,
- ADD_SERVICE_TRANSACTION,
- LIST_SERVICES_TRANSACTION
-};
-
-#define DEFAULTSERVICEMANAGER_IFACE "android.os.IServiceManager"
-
-GBinderServiceManager*
-gbinder_defaultservicemanager_new(
- const char* dev)
-{
- return gbinder_servicemanager_new_with_type
- (GBINDER_TYPE_DEFAULTSERVICEMANAGER, dev);
-}
-
-static
-void
-gbinder_defaultservicemanager_watch_proc(
- GBinderServicePoll* poll,
- const char* name_added,
- void* user_data)
-{
- GBinderDefaultServiceManagerWatch* watch = user_data;
-
- if (!g_strcmp0(name_added, watch->name)) {
- GBinderServiceManager* manager =
- gbinder_servicepoll_manager(watch->poll);
-
- if (watch->notify) {
- gbinder_timeout_remove(watch->notify);
- watch->notify = NULL;
- }
- gbinder_servicemanager_service_registered(manager, name_added);
- }
-}
-
-static
-gboolean
-gbinder_defaultservicemanager_watch_notify(
- gpointer user_data)
-{
- GBinderDefaultServiceManagerWatch* watch = user_data;
- GBinderServiceManager* manager = gbinder_servicepoll_manager(watch->poll);
- char* name = g_strdup(watch->name);
-
- GASSERT(watch->notify);
- watch->notify = NULL;
- gbinder_servicemanager_service_registered(manager, name);
- g_free(name);
- return G_SOURCE_REMOVE;
-}
-
-static
-void
-gbinder_defaultservicemanager_watch_free(
- gpointer user_data)
-{
- GBinderDefaultServiceManagerWatch* watch = user_data;
-
- gbinder_timeout_remove(watch->notify);
- gbinder_servicepoll_remove_handler(watch->poll, watch->handler_id);
- gbinder_servicepoll_unref(watch->poll);
- g_free(watch->name);
- g_slice_free(GBinderDefaultServiceManagerWatch, watch);
-}
-
-static
-GBinderDefaultServiceManagerWatch*
-gbinder_defaultservicemanager_watch_new(
- GBinderDefaultServiceManager* manager,
- const char* name)
-{
- GBinderDefaultServiceManagerWatch* watch =
- g_slice_new0(GBinderDefaultServiceManagerWatch);
-
- watch->name = g_strdup(name);
- watch->poll = gbinder_servicepoll_new(&manager->manager, &manager->poll);
- watch->handler_id = gbinder_servicepoll_add_handler(watch->poll,
- gbinder_defaultservicemanager_watch_proc, watch);
- return watch;
-}
-
-static
-GBinderLocalRequest*
-gbinder_servicemanager_list_services_req(
- GBinderServiceManager* self,
- gint32 index)
-{
- return gbinder_local_request_append_int32
- (gbinder_client_new_request(self->client), index);
-}
-
-static
-char**
-gbinder_defaultservicemanager_list(
- GBinderServiceManager* self)
-{
- GPtrArray* list = g_ptr_array_new();
- GBinderLocalRequest* req = gbinder_servicemanager_list_services_req(self,0);
- GBinderRemoteReply* reply;
-
- while ((reply = gbinder_client_transact_sync_reply(self->client,
- LIST_SERVICES_TRANSACTION, req, NULL)) != NULL) {
- char* service = gbinder_remote_reply_read_string16(reply);
-
- gbinder_remote_reply_unref(reply);
- if (service) {
- g_ptr_array_add(list, service);
- gbinder_local_request_unref(req);
- req = gbinder_servicemanager_list_services_req(self, list->len);
- } else {
- break;
- }
- }
-
- gbinder_local_request_unref(req);
- g_ptr_array_add(list, NULL);
- return (char**)g_ptr_array_free(list, FALSE);
-}
-
-static
-GBinderRemoteObject*
-gbinder_defaultservicemanager_get_service(
- GBinderServiceManager* self,
- const char* name,
|
[-]
[+]
|
Deleted |
_service:tar_git:libgbinder-1.0.46.tar.bz2/src/gbinder_hwservicemanager.c
^
|
@@ -1,399 +0,0 @@
-/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
- *
- * You may use this file under the terms of BSD license as follows:
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
- * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
- * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
- * THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "gbinder_servicemanager_p.h"
-#include "gbinder_rpc_protocol.h"
-#include "gbinder_log.h"
-
-#include <gbinder_client.h>
-#include <gbinder_local_object.h>
-#include <gbinder_local_request.h>
-#include <gbinder_remote_reply.h>
-#include <gbinder_remote_request.h>
-#include <gbinder_reader.h>
-
-#include <errno.h>
-#include <pthread.h>
-
-typedef struct gbinder_hwservicemanager_watch {
- char* name;
- GBinderLocalObject* callback;
-} GBinderHwServiceManagerWatch;
-
-typedef GBinderServiceManagerClass GBinderHwServiceManagerClass;
-typedef struct gbinder_hwservicemanager {
- GBinderServiceManager manager;
- GHashTable* watch_table;
-} GBinderHwServiceManager;
-
-G_DEFINE_TYPE(GBinderHwServiceManager,
- gbinder_hwservicemanager,
- GBINDER_TYPE_SERVICEMANAGER)
-
-#define PARENT_CLASS gbinder_hwservicemanager_parent_class
-#define GBINDER_TYPE_HWSERVICEMANAGER (gbinder_hwservicemanager_get_type())
-#define GBINDER_HWSERVICEMANAGER(obj) \
- G_TYPE_CHECK_INSTANCE_CAST((obj), GBINDER_TYPE_HWSERVICEMANAGER, \
- GBinderHwServiceManager)
-
-enum gbinder_hwservicemanager_calls {
- GET_TRANSACTION = GBINDER_FIRST_CALL_TRANSACTION,
- ADD_TRANSACTION,
- GET_TRANSPORT_TRANSACTION,
- LIST_TRANSACTION,
- LIST_BY_INTERFACE_TRANSACTION,
- REGISTER_FOR_NOTIFICATIONS_TRANSACTION,
- DEBUG_DUMP_TRANSACTION,
- REGISTER_PASSTHROUGH_CLIENT_TRANSACTION
-};
-
-enum gbinder_hwservicemanager_notifications {
- ON_REGISTRATION_TRANSACTION = GBINDER_FIRST_CALL_TRANSACTION
-};
-
-#define HWSERVICEMANAGER_IFACE "android.hidl.manager@1.0::IServiceManager"
-#define HWSERVICEMANAGER_NOTIFICATION_IFACE \
- "android.hidl.manager@1.0::IServiceNotification"
-
-static
-void
-gbinder_hwservicemanager_handle_registration(
- GBinderHwServiceManager* self,
- GBinderReader* reader)
-{
- char* fqname = gbinder_reader_read_hidl_string(reader);
- char* name = gbinder_reader_read_hidl_string(reader);
- gboolean preexisting;
-
- /* (string fqName, string name, bool preexisting) */
- if (fqname && name && gbinder_reader_read_bool(reader, &preexisting) &&
- gbinder_reader_at_end(reader)) {
- char* full_name = g_strconcat(fqname, "/", name, NULL);
-
- GDEBUG("%s %s", full_name, preexisting ? "true" : "false");
- gbinder_servicemanager_service_registered(&self->manager, full_name);
- g_free(full_name);
- } else {
- GWARN("Failed to parse IServiceNotification::onRegistration payload");
- }
- g_free(fqname);
- g_free(name);
-}
-
-static
-GBinderLocalReply*
-gbinder_hwservicemanager_notification(
- GBinderLocalObject* obj,
- GBinderRemoteRequest* req,
- guint code,
- guint flags,
- int* status,
- void* user_data)
-{
- GBinderHwServiceManager* self = GBINDER_HWSERVICEMANAGER(user_data);
- const char* iface = gbinder_remote_request_interface(req);
-
- if (!g_strcmp0(iface, HWSERVICEMANAGER_NOTIFICATION_IFACE)) {
- GBinderReader reader;
-
- gbinder_remote_request_init_reader(req, &reader);
- switch (code) {
- case ON_REGISTRATION_TRANSACTION:
- GDEBUG(HWSERVICEMANAGER_NOTIFICATION_IFACE " %u onRegistration",
- code);
- gbinder_hwservicemanager_handle_registration(self, &reader);
- *status = GBINDER_STATUS_OK;
- break;
- default:
- GDEBUG(HWSERVICEMANAGER_NOTIFICATION_IFACE " %u", code);
- *status = GBINDER_STATUS_FAILED;
- break;
- }
- } else {
- GDEBUG("%s %u", iface, code);
- *status = GBINDER_STATUS_FAILED;
- }
- return NULL;
-}
-
-GBinderServiceManager*
-gbinder_hwservicemanager_new(
- const char* dev)
-{
- return gbinder_servicemanager_new_with_type
- (gbinder_hwservicemanager_get_type(), dev);
-}
-
-static
-char**
-gbinder_hwservicemanager_list(
- GBinderServiceManager* self)
-{
- GBinderLocalRequest* req = gbinder_client_new_request(self->client);
- GBinderRemoteReply* reply = gbinder_client_transact_sync_reply
- (self->client, LIST_TRANSACTION, req, NULL);
-
- gbinder_local_request_unref(req);
- if (reply) {
- GBinderReader reader;
- char** result = NULL;
- int status = -1;
-
- gbinder_remote_reply_init_reader(reply, &reader);
-
- /* Read status */
- GVERIFY(gbinder_reader_read_int32(&reader, &status));
- GASSERT(status == GBINDER_STATUS_OK);
-
- /* Followed by hidl_vec<string> */
- result = gbinder_reader_read_hidl_string_vec(&reader);
- gbinder_remote_reply_unref(reply);
- return result;
- }
- return NULL;
-}
-
-static
-GBinderRemoteObject*
-gbinder_hwservicemanager_get_service(
- GBinderServiceManager* self,
- const char* fqinstance,
- int* status)
-{
- /* e.g. "android.hardware.radio@1.1::IRadio/slot1" */
- const char* sep = strchr(fqinstance, '/');
- GBinderRemoteObject* obj = NULL;
-
- if (sep) {
- GBinderRemoteReply* reply;
- GBinderLocalRequest* req = gbinder_client_new_request(self->client);
- char* fqname = g_strndup(fqinstance, sep - fqinstance);
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/AUTHORS
^
|
@@ -3,3 +3,5 @@
Franz-Josef Haider <franz.haider@jolla.com>
Juho Hämäläinen <juho.hamalainen@jolla.com>
Andrew Branson <andrew.branson@jolla.com>
+Rinigus <rinigus.git@gmail.com>
+George Hopkins <george-hopkins@null.net>
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/LICENSE
^
|
@@ -1,5 +1,5 @@
-Copyright (C) 2018-2020 Jolla Ltd.
-Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+Copyright (C) 2018-2021 Jolla Ltd.
+Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
You may use this file under the terms of BSD license as follows:
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/Makefile
^
|
@@ -15,8 +15,8 @@
#
VERSION_MAJOR = 1
-VERSION_MINOR = 0
-VERSION_RELEASE = 46
+VERSION_MINOR = 1
+VERSION_RELEASE = 10
# Version for pkg-config
PCVERSION = $(VERSION_MAJOR).$(VERSION_MINOR).$(VERSION_RELEASE)
@@ -75,9 +75,11 @@
#
SRC = \
+ gbinder_bridge.c \
gbinder_buffer.c \
gbinder_cleanup.c \
gbinder_client.c \
+ gbinder_config.c \
gbinder_driver.c \
gbinder_eventloop.c \
gbinder_io_32.c \
@@ -87,6 +89,7 @@
gbinder_local_reply.c \
gbinder_local_request.c \
gbinder_log.c \
+ gbinder_proxy_object.c \
gbinder_reader.c \
gbinder_remote_object.c \
gbinder_remote_reply.c \
@@ -97,9 +100,10 @@
gbinder_writer.c
SRC += \
- gbinder_defaultservicemanager.c \
- gbinder_hwservicemanager.c \
- gbinder_servicemanager.c
+ gbinder_servicemanager.c \
+ gbinder_servicemanager_aidl.c \
+ gbinder_servicemanager_aidl2.c \
+ gbinder_servicemanager_hidl.c
SRC += \
gbinder_system.c
@@ -153,6 +157,16 @@
RELEASE_OBJS = $(SRC:%.c=$(RELEASE_BUILD_DIR)/%.o)
COVERAGE_OBJS = $(SRC:%.c=$(COVERAGE_BUILD_DIR)/%.o)
+DEBUG_SO = $(DEBUG_BUILD_DIR)/$(LIB_SO)
+RELEASE_SO = $(RELEASE_BUILD_DIR)/$(LIB_SO)
+DEBUG_LINK = $(DEBUG_BUILD_DIR)/$(LIB_SYMLINK1)
+RELEASE_LINK = $(RELEASE_BUILD_DIR)/$(LIB_SYMLINK1)
+DEBUG_DEV_LINK = $(DEBUG_BUILD_DIR)/$(LIB_DEV_SYMLINK)
+RELEASE_DEV_LINK = $(RELEASE_BUILD_DIR)/$(LIB_DEV_SYMLINK)
+DEBUG_LIB = $(DEBUG_BUILD_DIR)/$(LIB)
+RELEASE_LIB = $(RELEASE_BUILD_DIR)/$(LIB)
+COVERAGE_LIB = $(COVERAGE_BUILD_DIR)/$(LIB)
+
#
# Dependencies
#
@@ -169,20 +183,15 @@
$(RELEASE_OBJS) $(RELEASE_SO): | $(RELEASE_BUILD_DIR) $(RELEASE_DEPS)
$(COVERAGE_OBJS) $(COVERAGE_LIB): | $(COVERAGE_BUILD_DIR)
+$(DEBUG_LINK): | $(DEBUG_LIB)
+$(RELEASE_LINK): | $(RELEASE_LIB)
+$(DEBUG_DEV_LINK): | $(DEBUG_LINK)
+$(RELEASE_DEV_LINK): | $(RELEASE_LINK)
+
#
# Rules
#
-DEBUG_SO = $(DEBUG_BUILD_DIR)/$(LIB_SO)
-RELEASE_SO = $(RELEASE_BUILD_DIR)/$(LIB_SO)
-DEBUG_LINK = $(DEBUG_BUILD_DIR)/$(LIB_SYMLINK1)
-RELEASE_LINK = $(RELEASE_BUILD_DIR)/$(LIB_SYMLINK1)
-DEBUG_DEV_LINK = $(DEBUG_BUILD_DIR)/$(LIB_DEV_SYMLINK)
-RELEASE_DEV_LINK = $(RELEASE_BUILD_DIR)/$(LIB_DEV_SYMLINK)
-DEBUG_LIB = $(DEBUG_BUILD_DIR)/$(LIB)
-RELEASE_LIB = $(RELEASE_BUILD_DIR)/$(LIB)
-COVERAGE_LIB = $(COVERAGE_BUILD_DIR)/$(LIB)
-
debug: $(DEBUG_SO) $(DEBUG_LINK) $(DEBUG_DEV_LINK)
release: $(RELEASE_SO) $(RELEASE_LINK) $(RELEASE_DEV_LINK)
@@ -319,7 +328,7 @@
INSTALL_PKGCONFIG_DIR = $(DESTDIR)$(ABS_LIBDIR)/pkgconfig
install: $(INSTALL_LIB_DIR)
- $(INSTALL_FILES) $(RELEASE_SO) $(INSTALL_LIB_DIR)
+ $(INSTALL) -m 755 $(RELEASE_SO) $(INSTALL_LIB_DIR)
ln -sf $(LIB_SO) $(INSTALL_LIB_DIR)/$(LIB_SYMLINK2)
ln -sf $(LIB_SYMLINK2) $(INSTALL_LIB_DIR)/$(LIB_SYMLINK1)
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/README
^
|
@@ -1,7 +1,44 @@
GLib-style interface to binder (Android IPC mechanism)
-Provides:
+Key features:
1. Integration with GLib event loop
2. Detection of 32 vs 64 bit kernel at runtime
3. Asynchronous transactions that don't block the event thread
+4. Stable service manager and low-level transation APIs
+
+Android keeps changing both low-level RPC and service manager
+protocols from version to version. To counter that, libgbinder
+implements configirable backends for different variants of those,
+and yet keeping its own API unchanged.
+
+Configuration is loaded from [Protocol] and [ServiceManager] sections
+of /etc/gbinder.conf file. The keys are binder device names or the
+special Default value, the value is the identifier of the protocol
+or service manager variant, respectively.
+
+In addition to reading /etc/gbinder.conf if it exists, /etc/gbinder.d
+directory is scanned for .conf files, the file list is sorted, files are
+loaded one by one, overwriting the entries loaded from /etc/gbinder.conf
+or from the previously processed file.
+
+Known protocol and service manager variants are aidl, aidl2 and hidl.
+This list is expected to expand further in the future. The default
+configuration is as follows:
+
+ [Protocol]
+ Default = aidl
+ /dev/binder = aidl
+ /dev/hwbinder = hidl
+
+ [ServiceManager]
+ Default = aidl
+ /dev/binder = aidl
+ /dev/hwbinder = hidl
+
+Alternatively, one can specify the desired Android API level:
+
+ [General]
+ ApiLevel = 29
+
+and let libgbinder pick the appropriate preset.
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/debian/changelog
^
|
@@ -1,3 +1,100 @@
+libgbinder (1.1.10) unstable; urgency=low
+
+ * Release dead binder nodes
+ * Use gutil_memdup() instead of g_memdup()
+
+ -- Slava Monich <slava.monich@jolla.com> Mon, 10 May 2021 02:36:43 +0300
+
+libgbinder (1.1.9) unstable; urgency=low
+
+ * Include definition of _IOC_SIZE
+
+ -- Slava Monich <slava.monich@jolla.com> Tue, 20 Apr 2021 12:52:41 +0300
+
+libgbinder (1.1.8) unstable; urgency=low
+
+ * Handle out-of-range transaction codes
+
+ -- Slava Monich <slava.monich@jolla.com> Fri, 16 Apr 2021 19:11:14 +0300
+
+libgbinder (1.1.7) unstable; urgency=low
+
+ * Dropped use of g_main_context_invoke_full()
+
+ -- Slava Monich <slava.monich@jolla.com> Wed, 31 Mar 2021 23:10:37 +0300
+
+libgbinder (1.1.6) unstable; urgency=low
+
+ * Implemented support for passing object over the bridge
+ * Retry service name registration
+ * Wait for completion of the reply
+ * Fixed death handling by GBinderBridge
+ * Added gbinder_bridge_new2()
+ * Added -s option to binder-bridge
+ * Fixed invalid slice deallocation
+ * Made unit tests more reliable
+ * Make sure that libgbinder doesn't block on exit
+
+ -- Slava Monich <slava.monich@jolla.com> Tue, 02 Mar 2021 18:18:03 +0200
+
+libgbinder (1.1.5) unstable; urgency=low
+
+ * Fixed gbinder_remote_reply_copy_to_local() for empty replies
+ * Improved binder simulation
+ * Added GBinderBridge object
+ * Added proxy_object and bridge unit tests
+ * Added binder-bridge to libgbinder-tools package
+
+ -- Slava Monich <slava.monich@jolla.com> Fri, 29 Jan 2021 04:00:09 +0200
+
+libgbinder (1.1.4) unstable; urgency=low
+
+ * Fixed a threading issue
+ * Decode NULL object reference
+ * Added new basic HIDL types
+ * Set TF_ACCEPT_FDS transaction flag
+ * Added servicemanager_hidl unit test
+
+ -- Slava Monich <slava.monich@jolla.com> Thu, 21 Jan 2021 03:34:45 +0200
+
+libgbinder (1.1.3) unstable; urgency=low
+
+ * Improved unit test coverage
+
+ -- Slava Monich <slava.monich@jolla.com> Wed, 23 Dec 2020 21:48:27 +0200
+
+libgbinder (1.1.2) unstable; urgency=low
+
+ * Fixed random unit text failures
+
+ -- Slava Monich <slava.monich@jolla.com> Wed, 23 Dec 2020 12:39:22 +0200
+
+libgbinder (1.1.1) unstable; urgency=low
+
+ * Handle corner cases for abandoned loopers
+ * Pass 0x0f priority to aidl2 service list request.
+ * Improved binder simulation for unit tests
+ * Added servicemanager_aidl unit test
+
+ -- Slava Monich <slava.monich@jolla.com> Tue, 22 Dec 2020 15:15:10 +0200
+
+libgbinder (1.1.0) unstable; urgency=low
+
+ * Made RPC protocol configurable per binder device
+ * Made service managers configurable per binder device
+ * Added support for multiple config files
+ * Added "aidl2" variant of service manager
+ * Added "aidl2" variant of RPC protocol
+ * Added support for API level presets
+
+ -- Slava Monich <slava.monich@jolla.com> Fri, 04 Dec 2020 13:47:26 +0200
+
+libgbinder (1.0.47) unstable; urgency=low
+
+ * Make library executable on RPM based systems
+
+ -- Slava Monich <slava.monich@jolla.com> Sat, 19 Sep 2020 20:14:20 +0300
+
libgbinder (1.0.46) unstable; urgency=low
* Make sure we drop fds that are going to be closed
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/debian/copyright
^
|
@@ -1,5 +1,5 @@
-Copyright (C) 2018-2020 Jolla Ltd.
-Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+Copyright (C) 2018-2021 Jolla Ltd.
+Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
You may use this file under the terms of BSD license as follows:
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/debian/rules
^
|
@@ -8,11 +8,13 @@
override_dh_auto_build:
dh_auto_build -- LIBDIR=$(LIBDIR) release pkgconfig debian/libgbinder.install debian/libgbinder-dev.install
+ dh_auto_build -- -C test/binder-bridge release
dh_auto_build -- -C test/binder-list release
dh_auto_build -- -C test/binder-ping release
override_dh_auto_install:
dh_auto_install -- LIBDIR=$(LIBDIR) install-dev
+ dh_auto_install -- -C test/binder-bridge
dh_auto_install -- -C test/binder-list
dh_auto_install -- -C test/binder-ping
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/include/gbinder.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -35,6 +35,7 @@
/* Convenience header to pull in everything at once */
+#include "gbinder_bridge.h"
#include "gbinder_buffer.h"
#include "gbinder_client.h"
#include "gbinder_local_object.h"
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/include/gbinder_bridge.h
^
|
@@ -0,0 +1,89 @@
+/*
+ * Copyright (C) 2021 Jolla Ltd.
+ * Copyright (C) 2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef GBINDER_BRIDGE_H
+#define GBINDER_BRIDGE_H
+
+#include "gbinder_types.h"
+
+/* Since 1.1.5 */
+
+G_BEGIN_DECLS
+
+/*
+ * A binder bridge object.
+ *
+ * For example, bridging "foobar" with interfaces ["example@1.0::IFoo",
+ * "example@1.0::IBar"] would:
+ *
+ * 1. Watch "example@1.0::IFoo/foobar" and "example@1.0::IBar/foobar" on dest
+ * 2. When those names appears, register objects with the same name on src
+ * 3. Pass calls coming from src to the dest objects and replies in the
+ * opposite direction
+ * 4. When dest objects disappear, remove the corresponding bridging objects
+ * from src
+ *
+ * and so on.
+ */
+
+GBinderBridge*
+gbinder_bridge_new(
+ const char* name,
+ const char* const* ifaces,
+ GBinderServiceManager* src,
+ GBinderServiceManager* dest) /* Since 1.1.5 */
+ G_GNUC_WARN_UNUSED_RESULT;
+
+GBinderBridge*
+gbinder_bridge_new2(
+ const char* src_name,
+ const char* dest_name,
+ const char* const* ifaces,
+ GBinderServiceManager* src,
+ GBinderServiceManager* dest) /* Since 1.1.6 */
+ G_GNUC_WARN_UNUSED_RESULT;
+
+void
+gbinder_bridge_free(
+ GBinderBridge* bridge); /* Since 1.1.5 */
+
+G_END_DECLS
+
+#endif /* GBINDER_BRIDGE_H */
+
+/*
+ * Local Variables:
+ * mode: C
+ * c-basic-offset: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/include/gbinder_servicemanager.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2020 Jolla Ltd.
+ * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -80,25 +80,29 @@
GBinderServiceManager*
gbinder_defaultservicemanager_new(
- const char* dev);
+ const char* dev)
+ G_DEPRECATED_FOR(gbinder_servicemanager_new);
GBinderServiceManager*
gbinder_hwservicemanager_new(
- const char* dev);
+ const char* dev)
+ G_DEPRECATED_FOR(gbinder_servicemanager_new);
GBinderLocalObject*
gbinder_servicemanager_new_local_object(
GBinderServiceManager* sm,
const char* iface,
GBinderLocalTransactFunc handler,
- void* user_data);
+ void* user_data)
+ G_GNUC_WARN_UNUSED_RESULT;
GBinderLocalObject*
gbinder_servicemanager_new_local_object2(
GBinderServiceManager* sm,
const char* const* ifaces,
GBinderLocalTransactFunc handler,
- void* user_data); /* Since 1.0.29 */
+ void* user_data) /* Since 1.0.29 */
+ G_GNUC_WARN_UNUSED_RESULT;
GBinderServiceManager*
gbinder_servicemanager_ref(
@@ -125,7 +129,9 @@
char**
gbinder_servicemanager_list_sync(
- GBinderServiceManager* sm);
+ GBinderServiceManager* sm)
+ G_GNUC_WARN_UNUSED_RESULT
+ G_GNUC_MALLOC;
gulong
gbinder_servicemanager_get_service(
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/include/gbinder_types.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -59,6 +59,7 @@
* 6. Reader parses the data coming with RemoteRequest and RemoteReply
*/
+typedef struct gbinder_bridge GBinderBridge; /* Since 1.1.5 */
typedef struct gbinder_buffer GBinderBuffer;
typedef struct gbinder_client GBinderClient;
typedef struct gbinder_ipc GBinderIpc;
@@ -76,16 +77,20 @@
/* Basic HIDL types */
+#define GBINDER_ALIGNED(x) __attribute__ ((aligned(x)))
+
typedef struct gbinder_hidl_vec {
union {
guint64 value;
const void* ptr;
} data;
guint32 count;
- guint32 owns_buffer;
+ guint8 owns_buffer;
+ guint8 pad[3];
} GBinderHidlVec;
#define GBINDER_HIDL_VEC_BUFFER_OFFSET (0)
+G_STATIC_ASSERT(sizeof(GBinderHidlVec) == 16);
typedef struct gbinder_hidl_string {
union {
@@ -93,10 +98,51 @@
const char* str;
} data;
guint32 len;
- guint32 owns_buffer;
+ guint8 owns_buffer;
+ guint8 pad[3];
} GBinderHidlString;
#define GBINDER_HIDL_STRING_BUFFER_OFFSET (0)
+G_STATIC_ASSERT(sizeof(GBinderHidlString) == 16);
+
+typedef struct gbinder_fds {
+ guint32 version GBINDER_ALIGNED(4);
+ guint32 num_fds GBINDER_ALIGNED(4);
+ guint32 num_ints GBINDER_ALIGNED(4);
+} GBINDER_ALIGNED(4) GBinderFds; /* Since 1.1.4 */
+
+/* Actual fds immediately follow GBinderFds: */
+#define gbinder_fds_get_fd(fds,i) (((const int*)((fds) + 1))[i])
+
+#define GBINDER_HIDL_FDS_VERSION (12)
+G_STATIC_ASSERT(sizeof(GBinderFds) == GBINDER_HIDL_FDS_VERSION);
+
+typedef struct gbinder_hidl_handle {
+ union {
+ guint64 value;
+ const GBinderFds* fds;
+ } data;
+ guint8 owns_handle;
+ guint8 pad[7];
+} GBinderHidlHandle; /* Since 1.1.4 */
+
+#define GBINDER_HIDL_HANDLE_VALUE_OFFSET (0)
+G_STATIC_ASSERT(sizeof(GBinderHidlHandle) == 16);
+
+typedef struct gbinder_hidl_memory {
+ union {
+ guint64 value;
+ const GBinderFds* fds;
+ } data;
+ guint8 owns_buffer;
+ guint8 pad[7];
+ guint64 size;
+ GBinderHidlString name;
+} GBinderHidlMemory; /* Since 1.1.4 */
+
+#define GBINDER_HIDL_MEMORY_PTR_OFFSET (0)
+#define GBINDER_HIDL_MEMORY_NAME_OFFSET (24)
+G_STATIC_ASSERT(sizeof(GBinderHidlMemory) == 40);
/*
* Each RPC call is identified by the interface name returned
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_bridge.c
^
|
@@ -0,0 +1,272 @@
+/*
+ * Copyright (C) 2021 Jolla Ltd.
+ * Copyright (C) 2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "gbinder_local_request.h"
+#include "gbinder_local_reply.h"
+#include "gbinder_proxy_object.h"
+#include "gbinder_remote_request_p.h"
+#include "gbinder_remote_reply.h"
+#include "gbinder_remote_object_p.h"
+#include "gbinder_servicename.h"
+#include "gbinder_servicemanager_p.h"
+#include "gbinder_client_p.h"
+#include "gbinder_bridge.h"
+#include "gbinder_ipc.h"
+#include "gbinder_log.h"
+
+#include <gutil_strv.h>
+#include <gutil_macros.h>
+
+#include <errno.h>
+
+typedef struct gbinder_bridge_interface {
+ GBinderBridge* bridge;
+ char* iface;
+ char* fqname;
+ char* src_name;
+ char* dest_name;
+ gulong dest_watch_id;
+ gulong dest_death_id;
+ GBinderRemoteObject* dest_obj;
+ GBinderServiceName* src_service;
+ GBinderProxyObject* proxy;
+} GBinderBridgeInterface;
+
+struct gbinder_bridge {
+ GBinderBridgeInterface** ifaces;
+ GBinderServiceManager* src;
+ GBinderServiceManager* dest;
+};
+
+/*==========================================================================*
+ * Implementation
+ *==========================================================================*/
+
+static
+void
+gbinder_bridge_dest_drop_remote_object(
+ GBinderBridgeInterface* bi)
+{
+ if (bi->dest_obj) {
+ GDEBUG("Detached from %s", bi->fqname);
+ gbinder_remote_object_remove_handler(bi->dest_obj, bi->dest_death_id);
+ gbinder_remote_object_unref(bi->dest_obj);
+ bi->dest_death_id = 0;
+ bi->dest_obj = NULL;
+ }
+}
+
+static
+void
+gbinder_bridge_interface_deactivate(
+ GBinderBridgeInterface* bi)
+{
+ gbinder_bridge_dest_drop_remote_object(bi);
+ if (bi->proxy) {
+ gbinder_local_object_drop(GBINDER_LOCAL_OBJECT(bi->proxy));
+ bi->proxy = NULL;
+ }
+ if (bi->src_service) {
+ gbinder_servicename_unref(bi->src_service);
+ bi->src_service = NULL;
+ }
+}
+
+static
+void
+gbinder_bridge_interface_free(
+ GBinderBridgeInterface* bi)
+{
+ GBinderBridge* bridge = bi->bridge;
+
+ gbinder_bridge_interface_deactivate(bi);
+ gbinder_servicemanager_remove_handler(bridge->dest, bi->dest_watch_id);
+ g_free(bi->iface);
+ g_free(bi->fqname);
+ g_free(bi->src_name);
+ g_free(bi->dest_name);
+ gutil_slice_free(bi);
+}
+
+static
+void
+gbinder_bridge_dest_death_proc(
+ GBinderRemoteObject* obj,
+ void* user_data)
+{
+ GBinderBridgeInterface* bi = user_data;
+
+ GDEBUG("%s has died", bi->fqname);
+ gbinder_bridge_interface_deactivate(bi);
+}
+
+static
+void
+gbinder_bridge_interface_activate(
+ GBinderBridgeInterface* bi)
+{
+ GBinderBridge* bridge = bi->bridge;
+ GBinderServiceManager* src = bridge->src;
+ GBinderServiceManager* dest = bridge->dest;
+
+ if (bi->dest_obj && bi->dest_obj->dead) {
+ gbinder_bridge_dest_drop_remote_object(bi);
+ }
+ if (!bi->dest_obj) {
+ bi->dest_obj = gbinder_servicemanager_get_service_sync(dest,
+ bi->fqname, NULL);
+ if (bi->dest_obj) {
+ GDEBUG("Attached to %s", bi->fqname);
+ gbinder_remote_object_ref(bi->dest_obj);
+ bi->dest_death_id = gbinder_remote_object_add_death_handler
+ (bi->dest_obj, gbinder_bridge_dest_death_proc, bi);
+ }
+ }
+ if (bi->dest_obj && !bi->proxy) {
+ bi->proxy = gbinder_proxy_object_new(gbinder_servicemanager_ipc(src),
+ bi->dest_obj);
+ }
+ if (bi->proxy && !bi->src_service) {
+ bi->src_service = gbinder_servicename_new(src,
+ GBINDER_LOCAL_OBJECT(bi->proxy), bi->src_name);
+ }
+}
+
+static
+void
+gbinder_bridge_dest_registration_proc(
+ GBinderServiceManager* sm,
+ const char* name,
+ void* user_data)
+{
+ GBinderBridgeInterface* bi = user_data;
+
+ if (!g_strcmp0(name, bi->fqname)) {
+ GDEBUG("%s has been registered", bi->fqname);
+ gbinder_bridge_interface_activate(bi);
+ }
+}
+
+static
+GBinderBridgeInterface*
+gbinder_bridge_interface_new(
+ GBinderBridge* self,
+ const char* src_name,
+ const char* dest_name,
+ const char* iface)
+{
+ GBinderBridgeInterface* bi = g_slice_new0(GBinderBridgeInterface);
+
+ bi->bridge = self;
+ bi->iface = g_strdup(iface);
+ bi->fqname = g_strconcat(iface, "/", dest_name, NULL);
+ bi->src_name = g_strdup(src_name);
+ bi->dest_name = g_strdup(dest_name);
+ bi->dest_watch_id = gbinder_servicemanager_add_registration_handler
+ (self->dest, bi->fqname, gbinder_bridge_dest_registration_proc, bi);
+
+ /* Try to activate at startup */
+ gbinder_bridge_interface_activate(bi);
+ return bi;
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_buffer.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018 Jolla Ltd.
- * Copyright (C) 2018 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -113,6 +113,47 @@
}
/*==========================================================================*
+ * GBinderBufferContentsList
+ * It's actually a GSList containing GBinderBufferContents refs.
+ *==========================================================================*/
+
+GBinderBufferContentsList*
+gbinder_buffer_contents_list_add(
+ GBinderBufferContentsList* list,
+ GBinderBufferContents* contents)
+{
+ /* Prepend rather than append for better efficiency */
+ return contents ? (GBinderBufferContentsList*) g_slist_prepend((GSList*)
+ list, gbinder_buffer_contents_ref(contents)) : list;
+}
+
+GBinderBufferContentsList*
+gbinder_buffer_contents_list_dup(
+ GBinderBufferContentsList* list)
+{
+ GSList* out = NULL;
+
+ if (list) {
+ GSList* l = (GSList*) list;
+
+ /* The order gets reversed but it doesn't matter */
+ while (l) {
+ out = g_slist_prepend(out, gbinder_buffer_contents_ref(l->data));
+ l = l->next;
+ }
+ }
+ return (GBinderBufferContentsList*) out;
+}
+
+void
+gbinder_buffer_contents_list_free(
+ GBinderBufferContentsList* list)
+{
+ g_slist_free_full((GSList*) list, (GDestroyNotify)
+ gbinder_buffer_contents_unref);
+}
+
+/*==========================================================================*
* GBinderBuffer
*==========================================================================*/
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_buffer_p.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -88,6 +88,22 @@
GBinderBufferContents* contents)
GBINDER_INTERNAL;
+GBinderBufferContentsList*
+gbinder_buffer_contents_list_add(
+ GBinderBufferContentsList* list,
+ GBinderBufferContents* contents)
+ GBINDER_INTERNAL;
+
+GBinderBufferContentsList*
+gbinder_buffer_contents_list_dup(
+ GBinderBufferContentsList* list)
+ GBINDER_INTERNAL;
+
+void
+gbinder_buffer_contents_list_free(
+ GBinderBufferContentsList* list)
+ GBINDER_INTERNAL;
+
#endif /* GBINDER_BUFFER_PRIVATE_H */
/*
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_client.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -179,6 +179,77 @@
}
/*==========================================================================*
+ * Internal interface
+ *==========================================================================*/
+
+GBinderRemoteReply*
+gbinder_client_transact_sync_reply2(
+ GBinderClient* self,
+ guint32 code,
+ GBinderLocalRequest* req,
+ int* status,
+ const GBinderIpcSyncApi* api)
+{
+ if (G_LIKELY(self)) {
+ GBinderRemoteObject* obj = self->remote;
+
+ if (G_LIKELY(!obj->dead)) {
+ if (!req) {
+ const GBinderClientIfaceRange* r = gbinder_client_find_range
+ (gbinder_client_cast(self), code);
+
+ /* Default empty request (just the header, no parameters) */
+ if (r) {
+ req = r->basic_req;
+ }
+ }
+ if (req) {
+ return api->sync_reply(obj->ipc, obj->handle, code, req,
+ status);
+ } else {
+ GWARN("Unable to build empty request for tx code %u", code);
+ }
+ } else {
+ GDEBUG("Refusing to perform transaction with a dead object");
+ }
+ }
+ return NULL;
+}
+
+int
+gbinder_client_transact_sync_oneway2(
+ GBinderClient* self,
+ guint32 code,
+ GBinderLocalRequest* req,
+ const GBinderIpcSyncApi* api)
+{
+ if (G_LIKELY(self)) {
+ GBinderRemoteObject* obj = self->remote;
+
+ if (G_LIKELY(!obj->dead)) {
+ if (!req) {
+ const GBinderClientIfaceRange* r = gbinder_client_find_range
+ (gbinder_client_cast(self), code);
+
+ /* Default empty request (just the header, no parameters) */
+ if (r) {
+ req = r->basic_req;
+ }
+ }
+ if (req) {
+ return api->sync_oneway(obj->ipc, obj->handle, code, req);
+ } else {
+ GWARN("Unable to build empty request for tx code %u", code);
+ }
+ } else {
+ GDEBUG("Refusing to perform transaction with a dead object");
+ return (-ESTALE);
+ }
+ }
+ return (-EINVAL);
+}
+
+/*==========================================================================*
* Interface
*==========================================================================*/
@@ -319,25 +390,8 @@
GBinderLocalRequest* req,
int* status)
{
- if (G_LIKELY(self)) {
- GBinderRemoteObject* obj = self->remote;
-
- if (G_LIKELY(!obj->dead)) {
- if (!req) {
- const GBinderClientIfaceRange* r = gbinder_client_find_range
- (gbinder_client_cast(self), code);
-
- /* Default empty request (just the header, no parameters) */
- if (r) {
- req = r->basic_req;
- }
- }
- return gbinder_ipc_transact_sync_reply(obj->ipc, obj->handle,
- code, req, status);
- }
- GDEBUG("Refusing to perform transaction with a dead object");
- }
- return NULL;
+ return gbinder_client_transact_sync_reply2(self, code, req, status,
+ &gbinder_ipc_sync_main);
}
int
@@ -346,26 +400,8 @@
guint32 code,
GBinderLocalRequest* req)
{
- if (G_LIKELY(self)) {
- GBinderRemoteObject* obj = self->remote;
-
- if (G_LIKELY(!obj->dead)) {
- if (!req) {
- const GBinderClientIfaceRange* r = gbinder_client_find_range
- (gbinder_client_cast(self), code);
-
- /* Default empty request (just the header, no parameters) */
- if (r) {
- req = r->basic_req;
- }
- }
- return gbinder_ipc_transact_sync_oneway(obj->ipc, obj->handle,
- code, req);
- }
- GDEBUG("Refusing to perform transaction with a dead object");
- return (-ESTALE);
- }
- return (-EINVAL);
+ return gbinder_client_transact_sync_oneway2(self, code, req,
+ &gbinder_ipc_sync_main);
}
gulong
@@ -382,13 +418,6 @@
GBinderRemoteObject* obj = self->remote;
if (G_LIKELY(!obj->dead)) {
- GBinderClientTx* tx = g_slice_new0(GBinderClientTx);
-
- tx->client = gbinder_client_ref(self);
- tx->reply = reply;
- tx->destroy = destroy;
- tx->user_data = user_data;
-
if (!req) {
const GBinderClientIfaceRange* r = gbinder_client_find_range
(gbinder_client_cast(self), code);
@@ -398,12 +427,22 @@
req = r->basic_req;
}
}
+ if (req) {
+ GBinderClientTx* tx = g_slice_new0(GBinderClientTx);
- return gbinder_ipc_transact(obj->ipc, obj->handle, code,
- flags, req, gbinder_client_transact_reply,
- gbinder_client_transact_destroy, tx);
+ tx->client = gbinder_client_ref(self);
+ tx->reply = reply;
+ tx->destroy = destroy;
+ tx->user_data = user_data;
+ return gbinder_ipc_transact(obj->ipc, obj->handle, code,
+ flags, req, gbinder_client_transact_reply,
+ gbinder_client_transact_destroy, tx);
+ } else {
+ GWARN("Unable to build empty request for tx code %u", code);
+ }
+ } else {
+ GDEBUG("Refusing to perform transaction with a dead object");
}
- GDEBUG("Refusing to perform transaction with a dead object");
}
return 0;
}
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_client_p.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -41,6 +41,24 @@
GBinderRemoteObject* remote;
};
+GBinderRemoteReply*
+gbinder_client_transact_sync_reply2(
+ GBinderClient* self,
+ guint32 code,
+ GBinderLocalRequest* req,
+ int* status,
+ const GBinderIpcSyncApi* api)
+ G_GNUC_WARN_UNUSED_RESULT
+ GBINDER_INTERNAL;
+
+int
+gbinder_client_transact_sync_oneway2(
+ GBinderClient* self,
+ guint32 code,
+ GBinderLocalRequest* req,
+ const GBinderIpcSyncApi* api)
+ GBINDER_INTERNAL;
+
#define gbinder_client_ipc(client) ((client)->remote->ipc)
#endif /* GBINDER_CLIENT_PRIVATE_H */
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_config.c
^
|
@@ -0,0 +1,384 @@
+/*
+ * Copyright (C) 2020 Jolla Ltd.
+ * Copyright (C) 2020 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "gbinder_config.h"
+#include "gbinder_eventloop_p.h"
+#include "gbinder_log.h"
+
+#include <gutil_strv.h>
+
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <unistd.h>
+
+/*
+ * The contents of the config file is queried from (at least) two places,
+ * and pretty much always this happens the same stack. Which means that
+ * we can avoid reading the same file twice if we delay dereferencing of
+ * GKeyFile until the next idle loop.
+ */
+
+static GKeyFile* gbinder_config_keyfile = NULL;
+static GBinderEventLoopCallback* gbinder_config_autorelease = NULL;
+
+static const char gbinder_config_suffix[] = ".conf";
+static const char gbinder_config_default_file[] = "/etc/gbinder.conf";
+static const char gbinder_config_default_dir[] = "/etc/gbinder.d";
+
+const char* gbinder_config_file = gbinder_config_default_file;
+const char* gbinder_config_dir = gbinder_config_default_dir;
+
+/*
+ * Presets for particular API level can be chosen with ApiLevel
+ * setting, e.g.
+ *
+ * [General]
+ * ApiLevel=29
+ *
+ */
+
+static const char CONF_GENERAL[] = "General";
+static const char CONG_API_LEVEL[] = "ApiLevel";
+
+typedef struct gbinder_config_preset_entry {
+ const char* key;
+ const char* value;
+} GBinderConfigPresetEntry;
+
+typedef struct gbinder_config_preset_group {
+ const char* name;
+ const GBinderConfigPresetEntry* entries;
+} GBinderConfigPresetGroup;
+
+typedef struct gbinder_config_preset {
+ guint api_level;
+ const GBinderConfigPresetGroup* groups;
+} GBinderConfigPreset;
+
+/* API level 28 */
+
+static const GBinderConfigPresetEntry gbinder_config_28_servicemanager[] = {
+ { "/dev/binder", "aidl2" },
+ { "/dev/vndbinder", "aidl2" },
+ { NULL, NULL }
+};
+
+static const GBinderConfigPresetGroup gbinder_config_28[] = {
+ { GBINDER_CONFIG_GROUP_SERVICEMANAGER, gbinder_config_28_servicemanager },
+ { NULL, NULL }
+};
+
+/* API level 29 */
+
+static const GBinderConfigPresetEntry gbinder_config_29_protocol[] = {
+ { "/dev/binder", "aidl2" },
+ { "/dev/vndbinder", "aidl2" },
+ { NULL, NULL }
+};
+
+#define gbinder_config_29_servicemanager gbinder_config_28_servicemanager
+
+static const GBinderConfigPresetGroup gbinder_config_29[] = {
+ { GBINDER_CONFIG_GROUP_PROTOCOL, gbinder_config_29_protocol },
+ { GBINDER_CONFIG_GROUP_SERVICEMANAGER, gbinder_config_29_servicemanager },
+ { NULL, NULL }
+};
+
+/* Presets sorted by API level in descending order */
+
+static const GBinderConfigPreset gbinder_config_presets[] = {
+ { 29, gbinder_config_29 },
+ { 28, gbinder_config_28 }
+};
+
+static
+char**
+gbinder_config_collect_files(
+ const char* path,
+ const char* suffix)
+{
+ /*
+ * Returns sorted list of regular files in the directory,
+ * optionally having the specified suffix (e.g. ".conf").
+ * Returns NULL if nothing appropriate has been found.
+ */
+ char** files = NULL;
+
+ if (path) {
+ GDir* dir = g_dir_open(path, 0, NULL);
+
+ if (dir) {
+ GPtrArray* list = g_ptr_array_new();
+ const gchar* name;
+
+ while ((name = g_dir_read_name(dir)) != NULL) {
+ if (g_str_has_suffix(name, suffix)) {
+ char* fullname = g_build_filename(path, name, NULL);
+ struct stat st;
+
+ if (!stat(fullname, &st) && S_ISREG(st.st_mode)) {
+ g_ptr_array_add(list, fullname);
+ } else {
+ g_free(fullname);
+ }
+ }
+ }
+
+ if (list->len > 0) {
+ g_ptr_array_add(list, NULL);
+ files = (char**) g_ptr_array_free(list, FALSE);
+ gutil_strv_sort(files, TRUE);
+ } else {
+ g_ptr_array_free(list, TRUE);
+ }
+
+ g_dir_close(dir);
+ }
+ }
+
+ return files;
+}
+
+static
+GKeyFile*
+gbinder_config_merge_keyfiles(
+ GKeyFile* dest,
+ GKeyFile* src)
+{
+ gsize i, ngroups;
+ gchar** groups = g_key_file_get_groups(src, &ngroups);
+
+ for (i = 0; i < ngroups; i++) {
+ gsize k, nkeys;
+ const char* group = groups[i];
+ char** keys = g_key_file_get_keys(src, group, &nkeys, NULL);
+
+ for (k = 0; k < nkeys; k++) {
+ const char* key = keys[k];
+ char* value = g_key_file_get_value(src, group, key, NULL);
+
+ g_key_file_set_value(dest, group, key, value);
+ g_free(value);
+ }
+
+ g_strfreev(keys);
+ }
+
+ g_strfreev(groups);
+ return dest;
+}
+
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_config.h
^
|
@@ -0,0 +1,78 @@
+/*
+ * Copyright (C) 2020 Jolla Ltd.
+ * Copyright (C) 2020 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef GBINDER_CONFIG_H
+#define GBINDER_CONFIG_H
+
+#include "gbinder_types_p.h"
+
+typedef
+gconstpointer
+(*GBinderConfigValueMapFunc)(
+ const char* value);
+
+GHashTable*
+gbinder_config_load(
+ const char* group,
+ GBinderConfigValueMapFunc map)
+ GBINDER_INTERNAL;
+
+GKeyFile* /* autoreleased */
+gbinder_config_get(
+ void)
+ GBINDER_INTERNAL;
+
+/* This one declared strictly for unit tests */
+void
+gbinder_config_exit(
+ void)
+ GBINDER_INTERNAL
+ GBINDER_DESTRUCTOR;
+
+/* And these too */
+extern const char* gbinder_config_file GBINDER_INTERNAL;
+extern const char* gbinder_config_dir GBINDER_INTERNAL;
+
+/* Configuration groups and special value */
+#define GBINDER_CONFIG_GROUP_PROTOCOL "Protocol"
+#define GBINDER_CONFIG_GROUP_SERVICEMANAGER "ServiceManager"
+#define GBINDER_CONFIG_VALUE_DEFAULT "Default"
+
+#endif /* GBINDER_CONFIG_H */
+
+/*
+ * Local Variables:
+ * mode: C
+ * c-basic-offset: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_driver.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -32,6 +32,7 @@
#include "gbinder_driver.h"
#include "gbinder_buffer_p.h"
+#include "gbinder_cleanup.h"
#include "gbinder_handler.h"
#include "gbinder_io.h"
#include "gbinder_local_object_p.h"
@@ -60,6 +61,7 @@
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/mman.h>
+#include <linux/ioctl.h>
/* BINDER_VM_SIZE copied from native/libs/binder/ProcessState.cpp */
#define BINDER_VM_SIZE ((1024*1024) - sysconf(_SC_PAGE_SIZE)*2)
@@ -84,10 +86,30 @@
const GBinderRpcProtocol* protocol;
};
-typedef struct gbinder_io_read_buf {
- GBinderIoBuf buf;
+typedef struct gbinder_driver_read_buf {
+ GBinderIoBuf io;
+ gsize offset;
+} GBinderDriverReadBuf;
+
+typedef struct gbinder_driver_read_data {
+ GBinderDriverReadBuf buf;
guint8 data[GBINDER_IO_READ_BUFFER_SIZE];
-} GBinderIoReadBuf;
+} GBinderDriverReadData;
+
+typedef struct gbinder_driver_context {
+ GBinderDriverReadBuf* rbuf;
+ GBinderObjectRegistry* reg;
+ GBinderHandler* handler;
+ GBinderCleanup* unrefs;
+ GBinderBufferContentsList* bufs;
+} GBinderDriverContext;
+
+static
+int
+gbinder_driver_txstatus(
+ GBinderDriver* self,
+ GBinderDriverContext* context,
+ GBinderRemoteReply* reply);
/*==========================================================================*
* Implementation
@@ -140,18 +162,38 @@
guint n = 0;
while (tx->objects[n]) n++;
if (tx->status) {
- GVERBOSE("> %s %d (%u bytes, %u objects)", name, tx->status,
- (guint)tx->size, n);
+ if (tx->target) {
+ GVERBOSE("> %s %p %d (%u bytes, %u objects)", name,
+ tx->target, tx->status, (guint)tx->size, n);
+ } else {
+ GVERBOSE("> %s %d (%u bytes, %u objects)", name,
+ tx->status, (guint)tx->size, n);
+ }
} else {
- GVERBOSE("> %s (%u bytes, %u objects)", name,
- (guint)tx->size, n);
+ if (tx->target) {
+ GVERBOSE("> %s %p (%u bytes, %u objects)", name,
+ tx->target, (guint)tx->size, n);
+ } else {
+ GVERBOSE("> %s (%u bytes, %u objects)", name, (guint)
+ tx->size, n);
+ }
}
} else {
if (tx->status) {
- GVERBOSE("> %s %d (%u bytes)", name, tx->status,
- (guint)tx->size);
+ if (tx->target) {
+ GVERBOSE("> %s %p %d (%u bytes)", name, tx->target,
+ tx->status, (guint)tx->size);
+ } else {
+ GVERBOSE("> %s %d (%u bytes)", name, tx->status, (guint)
+ tx->size);
+ }
} else {
- GVERBOSE("> %s (%u bytes)", name, (guint)tx->size);
+ if (tx->target) {
+ GVERBOSE("> %s %p (%u bytes)", name, tx->target, (guint)
+ tx->size);
+ } else {
+ GVERBOSE("> %s (%u bytes)", name, (guint)tx->size);
+ }
}
}
}
@@ -175,9 +217,11 @@
gbinder_driver_verbose_dump('<',
buf->ptr + buf->consumed,
buf->size - buf->consumed);
- GVERBOSE_("%u/%u", (guint)buf->consumed, (guint)buf->size);
+ GVERBOSE("gbinder_driver_write(%d) %u/%u", self->fd,
+ (guint)buf->consumed, (guint)buf->size);
err = self->io->write_read(self->fd, buf, NULL);
- GVERBOSE_("%u/%u err %d", (guint)buf->consumed, (guint)buf->size, err);
+ GVERBOSE("gbinder_driver_write(%d) %u/%u err %d", self->fd,
+ (guint)buf->consumed, (guint)buf->size, err);
}
return err;
}
@@ -187,11 +231,24 @@
gbinder_driver_write_read(
GBinderDriver* self,
GBinderIoBuf* write,
- GBinderIoBuf* read)
+ GBinderDriverReadBuf* rbuf)
{
int err = (-EAGAIN);
+ GBinderIoBuf rio;
+ GBinderIoBuf* read;
+
+ /* rbuf is never NULL */
+ if (rbuf->offset) {
+ rio.ptr = rbuf->io.ptr + rbuf->offset;
+ rio.size = rbuf->io.size - rbuf->offset;
+ rio.consumed = rbuf->io.consumed - rbuf->offset;
+ read = &rio;
+ } else {
+ read = &rbuf->io;
+ }
while (err == (-EAGAIN)) {
+
#if GUTIL_LOG_VERBOSE
const gsize were_consumed = read ? read->consumed : 0;
if (GLOG_ENABLED(GLOG_LEVEL_VERBOSE)) {
@@ -200,21 +257,23 @@
write->ptr + write->consumed,
write->size - write->consumed);
}
- GVERBOSE_("write %u/%u read %u/%u",
- (guint)(write ? write->consumed : 0),
- (guint)(write ? write->size : 0),
- (guint)(read ? read->consumed : 0),
- (guint)(read ? read->size : 0));
+ GVERBOSE("gbinder_driver_write_read(%d) "
+ "write %u/%u read %u/%u", self->fd,
+ (guint)(write ? write->consumed : 0),
+ (guint)(write ? write->size : 0),
+ (guint)(read ? read->consumed : 0),
+ (guint)(read ? read->size : 0));
}
#endif /* GUTIL_LOG_VERBOSE */
err = self->io->write_read(self->fd, write, read);
#if GUTIL_LOG_VERBOSE
if (GLOG_ENABLED(GLOG_LEVEL_VERBOSE)) {
- GVERBOSE_("write %u/%u read %u/%u err %d",
- (guint)(write ? write->consumed : 0),
- (guint)(write ? write->size : 0),
- (guint)(read ? read->consumed : 0),
- (guint)(read ? read->size : 0), err);
+ GVERBOSE("gbinder_driver_write_read(%d) "
+ "write %u/%u read %u/%u err %d", self->fd,
+ (guint)(write ? write->consumed : 0),
+ (guint)(write ? write->size : 0),
+ (guint)(read ? read->consumed : 0),
+ (guint)(read ? read->size : 0), err);
if (read) {
gbinder_driver_verbose_dump('>',
read->ptr + were_consumed,
@@ -223,6 +282,10 @@
}
#endif /* GUTIL_LOG_VERBOSE */
}
+
+ if (rbuf->offset) {
+ rbuf->io.consumed = rio.consumed + rbuf->offset;
+ }
return err;
}
@@ -280,55 +343,78 @@
static
gboolean
-gbinder_driver_death_notification(
+gbinder_driver_handle_cookie(
GBinderDriver* self,
guint32 cmd,
GBinderRemoteObject* obj)
{
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_driver.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -53,6 +53,11 @@
GBinderDriver* driver)
GBINDER_INTERNAL;
+void
+gbinder_driver_close(
+ GBinderDriver* driver)
+ GBINDER_INTERNAL;
+
int
gbinder_driver_fd(
GBinderDriver* driver)
@@ -74,6 +79,23 @@
GBinderDriver* driver)
GBINDER_INTERNAL;
+const GBinderRpcProtocol*
+gbinder_driver_protocol(
+ GBinderDriver* driver)
+ GBINDER_INTERNAL;
+
+gboolean
+gbinder_driver_acquire_done(
+ GBinderDriver* driver,
+ GBinderLocalObject* obj)
+ GBINDER_INTERNAL;
+
+gboolean
+gbinder_driver_dead_binder_done(
+ GBinderDriver* driver,
+ GBinderRemoteObject* obj)
+ GBINDER_INTERNAL;
+
gboolean
gbinder_driver_request_death_notification(
GBinderDriver* driver,
@@ -112,7 +134,7 @@
void
gbinder_driver_close_fds(
- GBinderDriver* self,
+ GBinderDriver* driver,
void** objects,
const void* end)
GBINDER_INTERNAL;
@@ -151,17 +173,15 @@
GBinderRemoteReply* reply)
GBINDER_INTERNAL;
-int
-gbinder_driver_ping(
+GBinderLocalRequest*
+gbinder_driver_local_request_new(
GBinderDriver* driver,
- GBinderObjectRegistry* reg,
- guint32 handle)
+ const char* iface)
GBINDER_INTERNAL;
GBinderLocalRequest*
-gbinder_driver_local_request_new(
- GBinderDriver* self,
- const char* iface)
+gbinder_driver_local_request_new_ping(
+ GBinderDriver* self)
GBINDER_INTERNAL;
#endif /* GBINDER_DRIVER_H */
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_eventloop.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2020 Jolla Ltd.
- * Copyright (C) 2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2020-2021 Jolla Ltd.
+ * Copyright (C) 2020-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -34,6 +34,13 @@
#include <gutil_macros.h>
+typedef struct gbinder_idle_callback_data {
+ GBinderEventLoopCallback* cb;
+ GBinderEventLoopCallbackFunc func;
+ GDestroyNotify destroy;
+ gpointer data;
+} GBinderIdleCallbackData;
+
#define GBINDER_DEFAULT_EVENTLOOP (&gbinder_eventloop_glib)
static const GBinderEventLoopIntegration gbinder_eventloop_glib;
@@ -221,6 +228,36 @@
};
/*==========================================================================*
+ * Implementation
+ *==========================================================================*/
+
+static
+void
+gbinder_idle_callback_invoke_proc(
+ void* user_data)
+{
+ GBinderIdleCallbackData* idle = user_data;
+
+ if (idle->func) {
+ idle->func(idle->data);
+ }
+ gbinder_idle_callback_unref(idle->cb);
+}
+
+static
+void
+gbinder_idle_callback_invoke_done(
+ void* user_data)
+{
+ GBinderIdleCallbackData* idle = user_data;
+
+ if (idle->destroy) {
+ idle->destroy(idle->data);
+ }
+ gutil_slice_free(idle);
+}
+
+/*==========================================================================*
* Internal interface
*==========================================================================*/
@@ -325,6 +362,27 @@
}
}
+/* Non-cancellable callback */
+void
+gbinder_idle_callback_invoke_later(
+ GBinderEventLoopCallbackFunc func,
+ gpointer data,
+ GDestroyNotify destroy)
+{
+ GBinderIdleCallbackData* idle = g_slice_new(GBinderIdleCallbackData);
+
+ idle->func = func;
+ idle->data = data;
+ idle->destroy = destroy;
+ idle->cb = gbinder_idle_callback_new(gbinder_idle_callback_invoke_proc,
+ idle, gbinder_idle_callback_invoke_done);
+ gbinder_idle_callback_schedule(idle->cb);
+}
+
+/*==========================================================================*
+ * Public interface
+ *==========================================================================*/
+
void
gbinder_eventloop_set(
const GBinderEventLoopIntegration* loop)
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_eventloop_p.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2020 Jolla Ltd.
- * Copyright (C) 2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2020-2021 Jolla Ltd.
+ * Copyright (C) 2020-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -41,12 +41,14 @@
guint millis,
GSourceFunc func,
gpointer data)
+ G_GNUC_WARN_UNUSED_RESULT
GBINDER_INTERNAL;
GBinderEventLoopTimeout*
gbinder_idle_add(
GSourceFunc func,
gpointer data)
+ G_GNUC_WARN_UNUSED_RESULT
GBINDER_INTERNAL;
void
@@ -59,6 +61,7 @@
GBinderEventLoopCallbackFunc func,
gpointer data,
GDestroyNotify destroy)
+ G_GNUC_WARN_UNUSED_RESULT
GBINDER_INTERNAL;
GBinderEventLoopCallback*
@@ -66,6 +69,7 @@
GBinderEventLoopCallbackFunc func,
gpointer data,
GDestroyNotify destroy)
+ G_GNUC_WARN_UNUSED_RESULT
GBINDER_INTERNAL;
GBinderEventLoopCallback*
@@ -93,6 +97,13 @@
GBinderEventLoopCallback* cb)
GBINDER_INTERNAL;
+void
+gbinder_idle_callback_invoke_later(
+ GBinderEventLoopCallbackFunc func,
+ gpointer data,
+ GDestroyNotify destroy)
+ GBINDER_INTERNAL;
+
#endif /* GBINDER_EVENTLOOP_PRIVATE_H */
/*
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_handler.h
^
|
@@ -36,6 +36,7 @@
#include "gbinder_types_p.h"
typedef struct gbinder_handler_functions {
+ gboolean (*can_loop)(GBinderHandler* handler);
GBinderLocalReply* (*transact)(GBinderHandler* handler,
GBinderLocalObject* obj, GBinderRemoteRequest* req, guint code,
guint flags, int* status);
@@ -48,6 +49,14 @@
/* Inline wrappers */
GBINDER_INLINE_FUNC
+gboolean
+gbinder_handler_can_loop(
+ GBinderHandler* self)
+{
+ return self && self->f->can_loop && self->f->can_loop(self);
+}
+
+GBINDER_INLINE_FUNC
GBinderLocalReply*
gbinder_handler_transact(
GBinderHandler* self,
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_io.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -90,19 +90,49 @@
return ret;
}
+/* Returns size of the object */
+static
+gsize
+GBINDER_IO_FN(object_size)(
+ const void* obj)
+{
+ if (obj) {
+ const struct binder_object_header* hdr = obj;
+
+ switch (hdr->type) {
+ case BINDER_TYPE_BINDER:
+ case BINDER_TYPE_WEAK_BINDER:
+ case BINDER_TYPE_HANDLE:
+ case BINDER_TYPE_WEAK_HANDLE:
+ return sizeof(struct flat_binder_object);
+ case BINDER_TYPE_FD:
+ return sizeof(struct binder_fd_object);
+ case BINDER_TYPE_FDA:
+ return sizeof(struct binder_fd_array_object);
+ case BINDER_TYPE_PTR:
+ return sizeof(struct binder_buffer_object);
+ }
+ }
+ return 0;
+}
+
/* Returns size of the object's extra data */
static
gsize
GBINDER_IO_FN(object_data_size)(
const void* obj)
{
- const struct binder_buffer_object* buf = obj;
+ if (obj) {
+ const struct binder_object_header* hdr = obj;
- if (buf && buf->hdr.type == BINDER_TYPE_PTR) {
- return buf->length;
- } else {
- return 0;
+ switch (hdr->type) {
+ case BINDER_TYPE_PTR:
+ return ((struct binder_buffer_object*)obj)->length;
+ case BINDER_TYPE_FDA:
+ return ((struct binder_fd_array_object*)obj)->num_fds * 4;
+ }
}
+ return 0;
}
/* Writes pointer to the buffer */
@@ -118,7 +148,20 @@
return sizeof(*dest);
}
-/* Encodes flat_buffer_object */
+/* Writes cookie to the buffer */
+static
+guint
+GBINDER_IO_FN(encode_cookie)(
+ void* out,
+ guint64 cookie)
+{
+ binder_uintptr_t* dest = out;
+
+ *dest = (uintptr_t)cookie;
+ return sizeof(*dest);
+}
+
+/* Encodes flat_binder_object */
static
guint
GBINDER_IO_FN(encode_local_object)(
@@ -163,12 +206,12 @@
void* out,
int fd)
{
- struct flat_binder_object* dest = out;
+ struct binder_fd_object* dest = out;
memset(dest, 0, sizeof(*dest));
dest->hdr.type = BINDER_TYPE_FD;
- dest->flags = 0x7f | FLAT_BINDER_FLAG_ACCEPTS_FDS;
- dest->handle = fd;
+ dest->pad_flags = 0x7f | FLAT_BINDER_FLAG_ACCEPTS_FDS;
+ dest->fd = fd;
return sizeof(*dest);
}
@@ -197,7 +240,7 @@
static
guint
-GBINDER_IO_FN(encode_death_notification)(
+GBINDER_IO_FN(encode_handle_cookie)(
void* out,
GBinderRemoteObject* obj)
{
@@ -209,7 +252,21 @@
return sizeof(*dest);
}
-/* Encodes BC_TRANSACTION data */
+static
+guint
+GBINDER_IO_FN(encode_ptr_cookie)(
+ void* out,
+ GBinderLocalObject* obj)
+{
+ struct binder_ptr_cookie* dest = out;
+
+ /* We never send these cookies and don't expect them back */
+ dest->ptr = (uintptr_t)obj;
+ dest->cookie = 0;
+ return sizeof(dest);
+}
+
+/* Fills binder_transaction_data for BC_TRANSACTION/REPLY */
static
void
GBINDER_IO_FN(fill_transaction_data)(
@@ -217,7 +274,7 @@
guint32 handle,
guint32 code,
const GByteArray* payload,
- guint flags,
+ guint tx_flags,
GUtilIntArray* offsets,
void** offsets_buf)
{
@@ -226,9 +283,7 @@
tr->code = code;
tr->data_size = payload->len;
tr->data.ptr.buffer = (uintptr_t)payload->data;
- if (flags & GBINDER_TX_FLAG_ONEWAY) {
- tr->flags |= TF_ONE_WAY;
- }
+ tr->flags = tx_flags;
if (offsets && offsets->count) {
guint i;
binder_size_t* tx_offsets = g_new(binder_size_t, offsets->count);
@@ -244,6 +299,7 @@
}
}
+/* Encodes BC_TRANSACTION data */
static
guint
GBINDER_IO_FN(encode_transaction)(
@@ -257,7 +313,8 @@
{
struct binder_transaction_data* tr = out;
- GBINDER_IO_FN(fill_transaction_data)(tr, handle, code, payload, flags,
+ GBINDER_IO_FN(fill_transaction_data)(tr, handle, code, payload,
+ (flags & GBINDER_TX_FLAG_ONEWAY) ? TF_ONE_WAY : TF_ACCEPT_FDS,
offsets, offsets_buf);
return sizeof(*tr);
}
@@ -278,13 +335,53 @@
struct binder_transaction_data_sg* sg = out;
GBINDER_IO_FN(fill_transaction_data)(&sg->transaction_data, handle, code,
- payload, flags, offsets, offsets_buf);
+ payload, (flags & GBINDER_TX_FLAG_ONEWAY) ? TF_ONE_WAY : TF_ACCEPT_FDS,
+ offsets, offsets_buf);
/* The driver seems to require buffers to be 8-byte aligned */
sg->buffers_size = G_ALIGN8(buffers_size);
return sizeof(*sg);
}
-/* Encode BC_REPLY */
+/* Encodes BC_REPLY data */
+static
+guint
+GBINDER_IO_FN(encode_reply)(
+ void* out,
+ guint32 handle,
+ guint32 code,
+ const GByteArray* payload,
+ GUtilIntArray* offsets,
+ void** offsets_buf)
+{
+ struct binder_transaction_data* tr = out;
+
+ GBINDER_IO_FN(fill_transaction_data)(tr, handle, code, payload, 0,
+ offsets, offsets_buf);
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_io.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -125,7 +125,8 @@
guint failed_reply;
} br;
- /* Size of the object's extra data */
+ /* Size of the object and its extra data */
+ gsize (*object_size)(const void* obj);
gsize (*object_data_size)(const void* obj);
/* Writes pointer to the buffer. The destination buffer must have
@@ -134,6 +135,12 @@
#define GBINDER_MAX_POINTER_SIZE (8)
guint (*encode_pointer)(void* out, const void* pointer);
+ /* Writes cookie to the buffer. The destination buffer must have
+ * at least GBINDER_IO_MAX_COOKIE_SIZE bytes available. The
+ * actual size is returned. */
+#define GBINDER_MAX_COOKIE_SIZE GBINDER_MAX_POINTER_SIZE
+ guint (*encode_cookie)(void* out, guint64 cookie);
+
/* Encode flat_buffer_object */
#define GBINDER_MAX_BINDER_OBJECT_SIZE (24)
guint (*encode_local_object)(void* out, GBinderLocalObject* obj);
@@ -145,32 +152,42 @@
guint (*encode_buffer_object)(void* out, const void* data, gsize size,
const GBinderParent* parent);
- /* Encode death notification */
-#define GBINDER_MAX_DEATH_NOTIFICATION_SIZE (12)
- guint (*encode_death_notification)(void* out, GBinderRemoteObject* obj);
+ /* Encode binder_handle_cookie */
+#define GBINDER_MAX_HANDLE_COOKIE_SIZE (12)
+ guint (*encode_handle_cookie)(void* out, GBinderRemoteObject* obj);
- /* Encode BC_TRANSACTION/REPLY data */
+ /* Encode binder_ptr_cookie */
+#define GBINDER_MAX_PTR_COOKIE_SIZE (16)
+ guint (*encode_ptr_cookie)(void* out, GBinderLocalObject* obj);
+
+ /* Encode BC_TRANSACTION/BC_TRANSACTION_SG data */
#define GBINDER_MAX_BC_TRANSACTION_SIZE (64)
guint (*encode_transaction)(void* out, guint32 handle, guint32 code,
const GByteArray* data, guint flags /* See below */,
GUtilIntArray* offsets, void** offsets_buf);
-
- /* Encode BC_TRANSACTION_SG/REPLY_SG data */
#define GBINDER_MAX_BC_TRANSACTION_SG_SIZE (72)
guint (*encode_transaction_sg)(void* out, guint32 handle, guint32 code,
const GByteArray* data, guint flags /* GBINDER_TX_FLAG_xxx */,
GUtilIntArray* offsets, void** offsets_buf,
gsize buffers_size);
+ /* Encode BC_REPLY/REPLY_SG data */
+#define GBINDER_MAX_BC_REPLY_SIZE GBINDER_MAX_BC_TRANSACTION_SIZE
+ guint (*encode_reply)(void* out, guint32 handle, guint32 code,
+ const GByteArray* data, GUtilIntArray* offsets, void** offsets_buf);
+#define GBINDER_MAX_BC_REPLY_SG_SIZE GBINDER_MAX_BC_TRANSACTION_SG_SIZE
+ guint (*encode_reply_sg)(void* out, guint32 handle, guint32 code,
+ const GByteArray* data, GUtilIntArray* offsets, void** offsets_buf,
+ gsize buffers_size);
+
/* Encode BC_REPLY */
guint (*encode_status_reply)(void* out, gint32* status);
/* Decoders */
void (*decode_transaction_data)(const void* data, GBinderIoTxData* tx);
-
-#define GBINDER_MAX_PTR_COOKIE_SIZE (16)
- void* (*decode_binder_ptr_cookie)(const void* data);
+ void* (*decode_ptr_cookie)(const void* data);
guint (*decode_cookie)(const void* data, guint64* cookie);
+ guint (*decode_binder_handle)(const void* obj, guint32* handle);
guint (*decode_binder_object)(const void* data, gsize size,
GBinderObjectRegistry* reg, GBinderRemoteObject** obj);
guint (*decode_buffer_object)(GBinderBuffer* buf, gsize offset,
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_ipc.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -31,11 +31,13 @@
*/
#define GLIB_DISABLE_DEPRECATION_WARNINGS
+#define _GNU_SOURCE /* pthread_*_np */
#include "gbinder_ipc.h"
#include "gbinder_driver.h"
#include "gbinder_handler.h"
#include "gbinder_io.h"
+#include "gbinder_rpc_protocol.h"
#include "gbinder_object_registry.h"
#include "gbinder_local_object_p.h"
#include "gbinder_local_reply.h"
@@ -53,6 +55,7 @@
#include <pthread.h>
#include <poll.h>
#include <errno.h>
+#include <time.h>
typedef struct gbinder_ipc_looper GBinderIpcLooper;
@@ -61,6 +64,7 @@
GThreadPool* tx_pool;
GHashTable* tx_table;
char* key;
+ const char* name;
GBinderObjectRegistry object_registry;
GMutex remote_objects_mutex;
@@ -90,6 +94,7 @@
#define GBINDER_IPC_MAX_TX_THREADS (15)
#define GBINDER_IPC_MAX_PRIMARY_LOOPERS (5)
#define GBINDER_IPC_LOOPER_START_TIMEOUT_SEC (2)
+#define GBINDER_IPC_LOOPER_JOIN_TIMEOUT_MS (500)
/*
* When looper receives the transaction:
@@ -153,11 +158,12 @@
GBinderHandler handler;
GBinderDriver* driver;
GBinderIpc* ipc; /* Not a reference! */
- GThread* thread;
+ pthread_t thread;
GMutex mutex;
GCond start_cond;
gint exit;
gint started;
+ gint joined;
int pipefd[2];
int txfd[2];
};
@@ -202,13 +208,30 @@
} GBinderIpcTxCustom;
GBINDER_INLINE_FUNC const char* gbinder_ipc_name(GBinderIpc* self)
- { return gbinder_driver_dev(self->driver); }
+ { return self->priv->name; }
static
GBinderIpcLooper*
gbinder_ipc_looper_new(
GBinderIpc* ipc);
+static
+GBinderRemoteReply*
+gbinder_ipc_transact_sync_reply_worker(
+ GBinderIpc* self,
+ guint32 handle,
+ guint32 code,
+ GBinderLocalRequest* req,
+ int* status);
+
+static
+int
+gbinder_ipc_transact_sync_oneway_worker(
+ GBinderIpc* self,
+ guint32 handle,
+ guint32 code,
+ GBinderLocalRequest* req);
+
/*==========================================================================*
* Utilities
*==========================================================================*/
@@ -406,8 +429,8 @@
gbinder_ipc_looper_free(
GBinderIpcLooper* looper)
{
- if (looper->thread) {
- g_thread_unref(looper->thread);
+ if (!looper->joined) {
+ pthread_join(looper->thread, NULL);
}
close(looper->pipefd[0]);
close(looper->pipefd[1]);
@@ -606,6 +629,16 @@
}
static
+gboolean
+gbinder_ipc_looper_can_loop(
+ GBinderHandler* handler)
+{
+ GBinderIpcLooper* looper = G_CAST(handler,GBinderIpcLooper,handler);
+
+ return !g_atomic_int_get(&looper->exit);
+}
+
+static
GBinderLocalReply*
gbinder_ipc_looper_transact(
GBinderHandler* handler,
@@ -653,7 +686,7 @@
/* Lock */
g_mutex_lock(&priv->looper_mutex);
if (gbinder_ipc_looper_remove_primary(looper)) {
- GDEBUG("Primary looper %s is blocked", looper->name);
+ GVERBOSE("Primary looper %s is blocked", looper->name);
looper->next = priv->blocked_loopers;
priv->blocked_loopers = looper;
was_blocked = TRUE;
@@ -680,7 +713,7 @@
/* Block until asynchronous transaction gets completed. */
done = 0;
if (gbinder_ipc_wait(looper->pipefd[0], tx->pipefd[0], &done)) {
- GDEBUG("Looper %s is released", looper->name);
+ GVERBOSE("Looper %s is released", looper->name);
GASSERT(done == TX_DONE);
}
}
@@ -733,6 +766,7 @@
GBinderIpcLooper* looper = data;
GBinderDriver* driver = looper->driver;
+ pthread_setname_np(looper->thread, looper->name);
if (gbinder_driver_enter_looper(driver)) {
struct pollfd pipefd;
int res;
@@ -823,9 +857,9 @@
/* Note: this call can actually fail */
if (!pipe(fd)) {
static const GBinderHandlerFunctions handler_functions = {
+ .can_loop = gbinder_ipc_looper_can_loop,
.transact = gbinder_ipc_looper_transact
};
- GError* error = NULL;
GBinderIpcLooper* looper = g_slice_new0(GBinderIpcLooper);
static gint gbinder_ipc_next_looper_id = 1;
guint id = (guint)g_atomic_int_add(&gbinder_ipc_next_looper_id, 1);
@@ -839,16 +873,14 @@
looper->handler.f = &handler_functions;
looper->ipc = ipc;
looper->driver = gbinder_driver_ref(ipc->driver);
- looper->thread = g_thread_try_new(looper->name,
- gbinder_ipc_looper_thread, looper, &error);
- if (looper->thread) {
+ if (!pthread_create(&looper->thread, NULL, gbinder_ipc_looper_thread,
+ looper)) {
/* gbinder_ipc_looper_thread() will release this reference: */
gbinder_ipc_looper_ref(looper);
GDEBUG("Starting looper %s", looper->name);
return looper;
} else {
- GERR("Failed to create looper thread: %s", GERRMSG(error));
- g_error_free(error);
+ GERR("Failed to create looper thread %s", looper->name);
}
gbinder_ipc_looper_unref(looper);
} else {
@@ -895,13 +927,15 @@
GBinderIpcLooper* looper)
{
/* Caller checks looper for NULL */
- if (looper->thread && looper->thread != g_thread_self()) {
- guint8 done = TX_DONE;
-
+ if (looper->thread) {
GDEBUG("Stopping looper %s", looper->name);
g_atomic_int_set(&looper->exit, TRUE);
- if (write(looper->pipefd[1], &done, sizeof(done)) <= 0) {
- looper->thread = NULL;
+ if (looper->thread != pthread_self()) {
+ guint8 done = TX_DONE;
+
+ if (write(looper->pipefd[1], &done, sizeof(done)) <= 0) {
+ GWARN("Failed to stop looper %s", looper->name);
+ }
}
}
}
@@ -930,9 +964,36 @@
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_ipc.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -60,6 +60,12 @@
};
typedef
+gboolean
+(*GBinderIpcLocalObjectCheckFunc)(
+ GBinderLocalObject* obj,
+ void* user_data);
+
+typedef
void
(*GBinderIpcReplyFunc)(
GBinderIpc* ipc,
@@ -67,10 +73,34 @@
int status,
void* user_data);
+typedef
+GBinderRemoteReply*
+(*GBinderIpcSyncReplyFunc)(
+ GBinderIpc* ipc,
+ guint32 handle,
+ guint32 code,
+ GBinderLocalRequest* req,
+ int* status);
+
+typedef
+int
+(*GBinderIpcSyncOnewayFunc)(
+ GBinderIpc* ipc,
+ guint32 handle,
+ guint32 code,
+ GBinderLocalRequest* req);
+
+struct gbinder_ipc_sync_api {
+ GBinderIpcSyncReplyFunc sync_reply;
+ GBinderIpcSyncOnewayFunc sync_oneway;
+};
+
+extern const GBinderIpcSyncApi gbinder_ipc_sync_main GBINDER_INTERNAL;
+extern const GBinderIpcSyncApi gbinder_ipc_sync_worker GBINDER_INTERNAL;
+
GBinderIpc*
gbinder_ipc_new(
- const char* dev,
- const GBinderRpcProtocol* protocol)
+ const char* dev)
GBINDER_INTERNAL;
GBinderIpc*
@@ -85,7 +115,7 @@
void
gbinder_ipc_looper_check(
- GBinderIpc* ipc)
+ GBinderIpc* ipc)
GBINDER_INTERNAL;
GBinderObjectRegistry*
@@ -93,6 +123,24 @@
GBinderIpc* ipc)
GBINDER_INTERNAL;
+const GBinderIo*
+gbinder_ipc_io(
+ GBinderIpc* ipc)
+ GBINDER_INTERNAL;
+
+const GBinderRpcProtocol*
+gbinder_ipc_protocol(
+ GBinderIpc* ipc)
+ GBINDER_INTERNAL;
+
+GBinderLocalObject*
+gbinder_ipc_find_local_object(
+ GBinderIpc* ipc,
+ GBinderIpcLocalObjectCheckFunc func,
+ void* user_data)
+ GBINDER_INTERNAL
+ G_GNUC_WARN_UNUSED_RESULT;
+
void
gbinder_ipc_register_local_object(
GBinderIpc* ipc,
@@ -100,11 +148,10 @@
GBINDER_INTERNAL;
GBinderRemoteObject*
-gbinder_ipc_get_remote_object(
- GBinderIpc* ipc,
- guint32 handle,
- gboolean maybe_dead)
- GBINDER_INTERNAL;
+gbinder_ipc_get_service_manager(
+ GBinderIpc* self)
+ GBINDER_INTERNAL
+ G_GNUC_WARN_UNUSED_RESULT;
void
gbinder_ipc_invalidate_remote_handle(
@@ -112,21 +159,11 @@
guint32 handle)
GBINDER_INTERNAL;
-GBinderRemoteReply*
-gbinder_ipc_transact_sync_reply(
- GBinderIpc* ipc,
- guint32 handle,
- guint32 code,
- GBinderLocalRequest* req,
- int* status)
- GBINDER_INTERNAL;
-
int
-gbinder_ipc_transact_sync_oneway(
+gbinder_ipc_ping_sync(
GBinderIpc* ipc,
guint32 handle,
- guint32 code,
- GBinderLocalRequest* req)
+ const GBinderIpcSyncApi* api)
GBINDER_INTERNAL;
gulong
@@ -170,12 +207,19 @@
GBinderRemoteObject* obj)
GBINDER_INTERNAL;
+/* Needed by unit tests */
+gboolean
+gbinder_ipc_set_max_threads(
+ GBinderIpc* self,
+ gint max_threads)
+ GBINDER_INTERNAL;
+
/* Declared for unit tests */
-__attribute__((destructor))
void
gbinder_ipc_exit(
void)
- GBINDER_INTERNAL;
+ GBINDER_INTERNAL
+ GBINDER_DESTRUCTOR;
#endif /* GBINDER_IPC_H */
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_local_object.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -34,25 +34,33 @@
#include "gbinder_driver.h"
#include "gbinder_ipc.h"
+#include "gbinder_buffer_p.h"
#include "gbinder_local_object_p.h"
#include "gbinder_local_reply_p.h"
#include "gbinder_remote_request.h"
+#include "gbinder_eventloop_p.h"
#include "gbinder_writer.h"
#include "gbinder_log.h"
#include <gutil_strv.h>
+#include <gutil_macros.h>
#include <errno.h>
struct gbinder_local_object_priv {
- GMainContext* context;
char** ifaces;
GBinderLocalTransactFunc txproc;
void* user_data;
};
+typedef struct gbinder_local_object_acquire_data {
+ GBinderLocalObject* object;
+ GBinderBufferContentsList* bufs;
+} GBinderLocalObjectAcquireData;
+
G_DEFINE_TYPE(GBinderLocalObject, gbinder_local_object, G_TYPE_OBJECT)
+#define PARENT_CLASS gbinder_local_object_parent_class
#define GBINDER_LOCAL_OBJECT_GET_CLASS(obj) \
G_TYPE_INSTANCE_GET_CLASS((obj), GBINDER_TYPE_LOCAL_OBJECT, \
GBinderLocalObjectClass)
@@ -258,71 +266,113 @@
static
void
+gbinder_local_object_default_drop(
+ GBinderLocalObject* self)
+{
+ GBinderLocalObjectPriv* priv = self->priv;
+
+ /* Clear the transaction callback */
+ priv->txproc = NULL;
+ priv->user_data = NULL;
+}
+
+static
+void
gbinder_local_object_handle_later(
GBinderLocalObject* self,
- GSourceFunc function)
+ GBinderEventLoopCallbackFunc function)
{
if (G_LIKELY(self)) {
- GBinderLocalObjectPriv* priv = self->priv;
-
- g_main_context_invoke_full(priv->context, G_PRIORITY_DEFAULT, function,
+ gbinder_idle_callback_invoke_later(function,
gbinder_local_object_ref(self), g_object_unref);
}
}
static
-gboolean
-gbinder_local_object_handle_increfs_proc(
- gpointer local)
+void
+gbinder_local_object_increfs_proc(
+ gpointer user_data)
{
- GBinderLocalObject* self = GBINDER_LOCAL_OBJECT(local);
+ GBinderLocalObject* self = GBINDER_LOCAL_OBJECT(user_data);
self->weak_refs++;
g_signal_emit(self, gbinder_local_object_signals
[SIGNAL_WEAK_REFS_CHANGED], 0);
- return G_SOURCE_REMOVE;
}
static
-gboolean
-gbinder_local_object_handle_decrefs_proc(
- gpointer local)
+void
+gbinder_local_object_decrefs_proc(
+ gpointer user_data)
{
- GBinderLocalObject* self = GBINDER_LOCAL_OBJECT(local);
+ GBinderLocalObject* self = GBINDER_LOCAL_OBJECT(user_data);
GASSERT(self->weak_refs > 0);
self->weak_refs--;
g_signal_emit(self, gbinder_local_object_signals
[SIGNAL_WEAK_REFS_CHANGED], 0);
- return G_SOURCE_REMOVE;
}
static
-gboolean
-gbinder_local_object_handle_acquire_proc(
- gpointer local)
+void
+gbinder_local_object_default_acquire(
+ GBinderLocalObject* self)
{
- GBinderLocalObject* self = GBINDER_LOCAL_OBJECT(local);
-
self->strong_refs++;
+ gbinder_local_object_ref(self);
+ GVERBOSE_("%p => %d", self, self->strong_refs);
g_signal_emit(self, gbinder_local_object_signals
[SIGNAL_STRONG_REFS_CHANGED], 0);
- return G_SOURCE_REMOVE;
}
static
-gboolean
-gbinder_local_object_handle_release_proc(
- gpointer local)
+void
+gbinder_local_object_acquire_proc(
+ gpointer user_data)
{
- GBinderLocalObject* self = GBINDER_LOCAL_OBJECT(local);
+ GBinderLocalObjectAcquireData* data = user_data;
+ GBinderLocalObject* self = data->object;
- GASSERT(self->strong_refs > 0);
- self->strong_refs--;
- g_signal_emit(self, gbinder_local_object_signals
- [SIGNAL_STRONG_REFS_CHANGED], 0);
+ GBINDER_LOCAL_OBJECT_GET_CLASS(self)->acquire(self);
+}
+
+static
+void
+gbinder_local_object_acquire_done(
+ gpointer user_data)
+{
+ GBinderLocalObjectAcquireData* data = user_data;
+ GBinderLocalObject* self = data->object;
+
+ gbinder_driver_acquire_done(self->ipc->driver, self);
gbinder_local_object_unref(self);
- return G_SOURCE_REMOVE;
+ gbinder_buffer_contents_list_free(data->bufs);
+ return gutil_slice_free(data);
+}
+
+static
+void
+gbinder_local_object_default_release(
+ GBinderLocalObject* self)
+{
+ GASSERT(self->strong_refs > 0);
+ if (self->strong_refs > 0) {
+ self->strong_refs--;
+ GVERBOSE_("%p => %d", self, self->strong_refs);
+ g_signal_emit(self, gbinder_local_object_signals
+ [SIGNAL_STRONG_REFS_CHANGED], 0);
+ gbinder_local_object_unref(self);
+ }
+}
+
+static
+void
+gbinder_local_object_release_proc(
+ gpointer obj)
+{
+ GBinderLocalObject* self = GBINDER_LOCAL_OBJECT(obj);
+
+ GBINDER_LOCAL_OBJECT_GET_CLASS(self)->release(self);
}
/*==========================================================================*
@@ -336,41 +386,64 @@
GBinderLocalTransactFunc txproc,
void* user_data) /* Since 1.0.30 */
{
- if (G_LIKELY(ipc)) {
- GBinderLocalObject* self = g_object_new
- (GBINDER_TYPE_LOCAL_OBJECT, NULL);
- GBinderLocalObjectPriv* priv = self->priv;
- guint i = 0, n = gutil_strv_length((char**)ifaces);
- gboolean append_base_interface;
-
- if (g_strcmp0(gutil_strv_last((char**)ifaces), hidl_base_interface)) {
- append_base_interface = TRUE;
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_local_object_p.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -40,8 +40,9 @@
#include <glib-object.h>
/*
- * Some if this stuff may become public if we decide to allow the clients
- * to derive their classes from GBinderLocalObject
+ * Some of this stuff may become public if we decide to allow the clients
+ * to derive their own classes from GBinderLocalObject. For now it's all
+ * private.
*/
typedef
@@ -76,6 +77,9 @@
GBinderLocalReply* (*handle_looper_transaction)
(GBinderLocalObject* self, GBinderRemoteRequest* req, guint code,
guint flags, int* status);
+ void (*acquire)(GBinderLocalObject* self);
+ void (*release)(GBinderLocalObject* self);
+ void (*drop)(GBinderLocalObject* self);
/* Need to add some placeholders if this class becomes public */
} GBinderLocalObjectClass;
@@ -83,10 +87,30 @@
#define GBINDER_TYPE_LOCAL_OBJECT (gbinder_local_object_get_type())
#define GBINDER_LOCAL_OBJECT(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), \
GBINDER_TYPE_LOCAL_OBJECT, GBinderLocalObject))
+#define GBINDER_LOCAL_OBJECT_CLASS(klass) G_TYPE_CHECK_CLASS_CAST((klass), \
+ GBINDER_TYPE_LOCAL_OBJECT, GBinderLocalObjectClass)
#define gbinder_local_object_dev(obj) (gbinder_driver_dev((obj)->ipc->driver))
#define gbinder_local_object_io(obj) (gbinder_driver_io((obj)->ipc->driver))
+GBinderLocalObject*
+gbinder_local_object_new_with_type(
+ GType type,
+ GBinderIpc* ipc,
+ const char* const* ifaces,
+ GBinderLocalTransactFunc txproc,
+ void* user_data)
+ GBINDER_INTERNAL;
+
+void
+gbinder_local_object_init_base(
+ GBinderLocalObject* self,
+ GBinderIpc* ipc,
+ const char* const* ifaces,
+ GBinderLocalTransactFunc txproc,
+ void* user_data)
+ GBINDER_INTERNAL;
+
gulong
gbinder_local_object_add_weak_refs_changed_handler(
GBinderLocalObject* obj,
@@ -144,7 +168,8 @@
void
gbinder_local_object_handle_acquire(
- GBinderLocalObject* obj)
+ GBinderLocalObject* obj,
+ GBinderBufferContentsList* bufs)
GBINDER_INTERNAL;
void
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_local_reply.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018 Jolla Ltd.
- * Copyright (C) 2018 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -43,6 +43,7 @@
gint refcount;
GBinderWriterData data;
GBinderOutputData out;
+ GBinderBufferContents* contents;
};
GBINDER_INLINE_FUNC
@@ -94,14 +95,16 @@
}
GBinderLocalReply*
-gbinder_local_reply_new_from_data(
- GBinderBuffer* buffer)
+gbinder_local_reply_set_contents(
+ GBinderLocalReply* self,
+ GBinderBuffer* buffer,
+ GBinderObjectConverter* convert)
{
- const GBinderIo* io = gbinder_buffer_io(buffer);
- GBinderLocalReply* self = gbinder_local_reply_new(io);
-
if (self) {
- gbinder_writer_data_set_contents(&self->data, buffer);
+ gbinder_writer_data_set_contents(&self->data, buffer, convert);
+ gbinder_buffer_contents_unref(self->contents);
+ self->contents = gbinder_buffer_contents_ref
+ (gbinder_buffer_contents(buffer));
}
return self;
}
@@ -116,7 +119,8 @@
gutil_int_array_free(data->offsets, TRUE);
g_byte_array_free(data->bytes, TRUE);
gbinder_cleanup_free(data->cleanup);
- g_slice_free(GBinderLocalReply, self);
+ gbinder_buffer_contents_unref(self->contents);
+ gutil_slice_free(self);
}
GBinderLocalReply*
@@ -149,6 +153,13 @@
return G_LIKELY(self) ? &self->out : NULL;
}
+GBinderBufferContents*
+gbinder_local_reply_contents(
+ GBinderLocalReply* self)
+{
+ return G_LIKELY(self) ? self->contents : NULL;
+}
+
void
gbinder_local_reply_cleanup(
GBinderLocalReply* self,
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_local_reply_p.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -47,9 +47,16 @@
GBinderLocalReply* reply)
GBINDER_INTERNAL;
+GBinderBufferContents*
+gbinder_local_reply_contents(
+ GBinderLocalReply* reply)
+ GBINDER_INTERNAL;
+
GBinderLocalReply*
-gbinder_local_reply_new_from_data(
- GBinderBuffer* buffer)
+gbinder_local_reply_set_contents(
+ GBinderLocalReply* reply,
+ GBinderBuffer* buffer,
+ GBinderObjectConverter* convert)
GBINDER_INTERNAL;
#endif /* GBINDER_LOCAL_REPLY_PRIVATE_H */
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_local_request.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018 Jolla Ltd.
- * Copyright (C) 2018 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -31,6 +31,7 @@
*/
#include "gbinder_local_request_p.h"
+#include "gbinder_rpc_protocol.h"
#include "gbinder_output_data.h"
#include "gbinder_writer_p.h"
#include "gbinder_buffer_p.h"
@@ -91,6 +92,7 @@
if (init) {
gsize size;
gconstpointer data = g_bytes_get_data(init, &size);
+
writer->bytes = g_byte_array_sized_new(size);
g_byte_array_append(writer->bytes, data, size);
} else {
@@ -104,18 +106,48 @@
}
GBinderLocalRequest*
+gbinder_local_request_new_iface(
+ const GBinderIo* io,
+ const GBinderRpcProtocol* protocol,
+ const char* iface)
+{
+ GBinderLocalRequest* self = gbinder_local_request_new(io, NULL);
+
+ if (self && G_LIKELY(protocol) && G_LIKELY(iface)) {
+ GBinderWriter writer;
+
+ gbinder_local_request_init_writer(self, &writer);
+ protocol->write_rpc_header(&writer, iface);
+ }
+ return self;
+}
+
+GBinderLocalRequest*
gbinder_local_request_new_from_data(
- GBinderBuffer* buffer)
+ GBinderBuffer* buffer,
+ GBinderObjectConverter* convert)
{
GBinderLocalRequest* self = gbinder_local_request_new
(gbinder_buffer_io(buffer), NULL);
if (self) {
- gbinder_writer_data_set_contents(&self->data, buffer);
+ gbinder_writer_data_append_contents(&self->data, buffer, 0, convert);
}
return self;
}
+void
+gbinder_local_request_append_contents(
+ GBinderLocalRequest* self,
+ GBinderBuffer* buffer,
+ gsize off,
+ GBinderObjectConverter* convert)
+{
+ if (self) {
+ gbinder_writer_data_append_contents(&self->data, buffer, off, convert);
+ }
+}
+
static
void
gbinder_local_request_free(
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_local_request_p.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -43,14 +43,30 @@
GBytes* init)
GBINDER_INTERNAL;
+GBinderLocalRequest*
+gbinder_local_request_new_iface(
+ const GBinderIo* io,
+ const GBinderRpcProtocol* protocol,
+ const char* iface)
+ GBINDER_INTERNAL;
+
+GBinderLocalRequest*
+gbinder_local_request_new_from_data(
+ GBinderBuffer* buffer,
+ GBinderObjectConverter* convert)
+ GBINDER_INTERNAL;
+
GBinderOutputData*
gbinder_local_request_data(
GBinderLocalRequest* req)
GBINDER_INTERNAL;
-GBinderLocalRequest*
-gbinder_local_request_new_from_data(
- GBinderBuffer* buffer)
+void
+gbinder_local_request_append_contents(
+ GBinderLocalRequest* req,
+ GBinderBuffer* buffer,
+ gsize offset,
+ GBinderObjectConverter* convert)
GBINDER_INTERNAL;
#endif /* GBINDER_LOCAL_REQUEST_PRIVATE_H */
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_object_converter.h
^
|
@@ -0,0 +1,67 @@
+/*
+ * Copyright (C) 2021 Jolla Ltd.
+ * Copyright (C) 2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef GBINDER_OBJECT_CONVERTER_H
+#define GBINDER_OBJECT_CONVERTER_H
+
+#include "gbinder_types_p.h"
+
+typedef struct gbinder_object_converter_functions {
+ GBinderLocalObject* (*handle_to_local)(GBinderObjectConverter*, guint32);
+} GBinderObjectConverterFunctions;
+
+struct gbinder_object_converter {
+ const GBinderObjectConverterFunctions* f;
+ const GBinderIo* io;
+ const GBinderRpcProtocol* protocol;
+};
+
+/* Inline wrappers */
+
+GBINDER_INLINE_FUNC
+GBinderLocalObject*
+gbinder_object_converter_handle_to_local(
+ GBinderObjectConverter* convert,
+ guint32 handle)
+{
+ return convert ? convert->f->handle_to_local(convert, handle) : NULL;
+}
+
+#endif /* GBINDER_OBJECT_CONVERTER_H */
+
+/*
+ * Local Variables:
+ * mode: C
+ * c-basic-offset: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_object_registry.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -35,13 +35,19 @@
#include "gbinder_types_p.h"
+typedef enum gbinder_remote_registry_create {
+ REMOTE_REGISTRY_DONT_CREATE,
+ REMOTE_REGISTRY_CAN_CREATE,
+ REMOTE_REGISTRY_CAN_CREATE_AND_ACQUIRE
+} REMOTE_REGISTRY_CREATE;
+
typedef struct gbinder_object_registry_functions {
void (*ref)(GBinderObjectRegistry* reg);
void (*unref)(GBinderObjectRegistry* reg);
GBinderLocalObject* (*get_local)(GBinderObjectRegistry* reg,
void* pointer);
GBinderRemoteObject* (*get_remote)(GBinderObjectRegistry* reg,
- guint32 handle);
+ guint32 handle, REMOTE_REGISTRY_CREATE create);
} GBinderObjectRegistryFunctions;
struct gbinder_object_registry {
@@ -81,9 +87,10 @@
GBinderRemoteObject*
gbinder_object_registry_get_remote(
GBinderObjectRegistry* reg,
- guint32 handle)
+ guint32 handle,
+ REMOTE_REGISTRY_CREATE create)
{
- return reg ? reg->f->get_remote(reg, handle) : NULL;
+ return reg ? reg->f->get_remote(reg, handle, create) : NULL;
}
#endif /* GBINDER_OBJECT_REGISTRY_H */
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_proxy_object.c
^
|
@@ -0,0 +1,522 @@
+/*
+ * Copyright (C) 2021 Jolla Ltd.
+ * Copyright (C) 2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#define GLIB_DISABLE_DEPRECATION_WARNINGS
+
+#include "gbinder_proxy_object.h"
+#include "gbinder_local_object_p.h"
+#include "gbinder_local_request.h"
+#include "gbinder_local_reply.h"
+#include "gbinder_remote_object_p.h"
+#include "gbinder_remote_request_p.h"
+#include "gbinder_remote_reply_p.h"
+#include "gbinder_object_converter.h"
+#include "gbinder_object_registry.h"
+#include "gbinder_driver.h"
+#include "gbinder_ipc.h"
+#include "gbinder_log.h"
+
+#include <gutil_macros.h>
+
+#include <errno.h>
+
+typedef GBinderLocalObjectClass GBinderProxyObjectClass;
+typedef struct gbinder_proxy_tx GBinderProxyTx;
+
+struct gbinder_proxy_tx {
+ GBinderProxyTx* next;
+ GBinderRemoteRequest* req;
+ GBinderProxyObject* proxy;
+ gulong id;
+};
+
+struct gbinder_proxy_object_priv {
+ gulong remote_death_id;
+ gboolean dropped;
+ GBinderProxyTx* tx;
+ GMutex mutex; /* Protects the hashtable below */
+ GHashTable* subproxies;
+};
+
+G_DEFINE_TYPE(GBinderProxyObject, gbinder_proxy_object, \
+ GBINDER_TYPE_LOCAL_OBJECT)
+#define GBINDER_IS_PROXY_OBJECT(obj) G_TYPE_CHECK_INSTANCE_TYPE(obj, \
+ GBINDER_TYPE_PROXY_OBJECT)
+
+#define THIS(obj) GBINDER_PROXY_OBJECT(obj)
+#define THIS_TYPE GBINDER_TYPE_PROXY_OBJECT
+#define PARENT_CLASS gbinder_proxy_object_parent_class
+
+static
+void
+gbinder_proxy_object_subproxy_gone(
+ gpointer proxy,
+ GObject* subproxy)
+{
+ GBinderProxyObject* self = THIS(proxy);
+ GBinderProxyObjectPriv* priv = self->priv;
+
+ /* Lock */
+ g_mutex_lock(&priv->mutex);
+ g_hash_table_remove(priv->subproxies, subproxy);
+ if (g_hash_table_size(priv->subproxies) == 0) {
+ g_hash_table_unref(priv->subproxies);
+ priv->subproxies = NULL;
+ }
+ g_mutex_unlock(&priv->mutex);
+ /* Unlock */
+}
+
+static
+void
+gbinder_proxy_object_drop_subproxies(
+ GBinderProxyObject* self)
+{
+ GBinderProxyObjectPriv* priv = self->priv;
+ GSList* list = NULL;
+
+ /* Lock */
+ g_mutex_lock(&priv->mutex);
+ if (priv->subproxies) {
+ GHashTableIter it;
+ gpointer value;
+
+ g_hash_table_iter_init(&it, priv->subproxies);
+ while (g_hash_table_iter_next(&it, NULL, &value)) {
+ list = g_slist_append(list, gbinder_local_object_ref(value));
+ g_object_weak_unref(G_OBJECT(value),
+ gbinder_proxy_object_subproxy_gone, self);
+ }
+ g_hash_table_destroy(priv->subproxies);
+ priv->subproxies = NULL;
+ }
+ g_mutex_unlock(&priv->mutex);
+ /* Unlock */
+
+ /* Drop (and possibly destroy) the objects outside of the lock */
+ g_slist_free_full(list, (GDestroyNotify) gbinder_local_object_drop);
+}
+
+static
+void
+gbinder_proxy_remote_death_proc(
+ GBinderRemoteObject* obj,
+ void* proxy)
+{
+ GBinderProxyObject* self = THIS(proxy);
+ GBinderProxyObjectPriv* priv = self->priv;
+
+ GDEBUG("Remote object %u died on %s", obj->handle, obj->ipc->dev);
+ gbinder_remote_object_remove_handler(obj, priv->remote_death_id);
+ priv->remote_death_id = 0;
+ /* Drop the implicit reference */
+ gbinder_local_object_unref(&self->parent);
+}
+
+/*==========================================================================*
+ * Converter
+ *==========================================================================*/
+
+typedef struct gbinder_proxy_object_converter {
+ GBinderObjectConverter pub;
+ GBinderProxyObject* proxy;
+ GBinderIpc* remote;
+ GBinderIpc* local;
+} GBinderProxyObjectConverter;
+
+GBINDER_INLINE_FUNC
+GBinderProxyObjectConverter*
+gbinder_proxy_object_converter_cast(
+ GBinderObjectConverter* pub)
+{
+ return G_CAST(pub, GBinderProxyObjectConverter, pub);
+}
+
+static
+gboolean
+gbinder_proxy_object_converter_check(
+ GBinderLocalObject* obj,
+ void* remote)
+{
+ if (GBINDER_IS_PROXY_OBJECT(obj) && THIS(obj)->remote == remote) {
+ /* Found matching proxy object */
+ return TRUE;
+ }
+ /* Keep looking */
+ return FALSE;
+}
+
+static
+GBinderLocalObject*
+gbinder_proxy_object_converter_handle_to_local(
+ GBinderObjectConverter* pub,
+ guint32 handle)
+{
+ GBinderProxyObjectConverter* c = gbinder_proxy_object_converter_cast(pub);
+ GBinderProxyObject* proxy = c->proxy;
+ GBinderProxyObjectPriv* priv = proxy->priv;
+ GBinderObjectRegistry* reg = gbinder_ipc_object_registry(c->remote);
+ GBinderRemoteObject* remote = gbinder_object_registry_get_remote(reg,
+ handle, REMOTE_REGISTRY_CAN_CREATE /* but don't acquire */);
+ GBinderLocalObject* local = gbinder_ipc_find_local_object(c->local,
+ gbinder_proxy_object_converter_check, remote);
+
+ if (!local && !remote->dead) {
+ /* GBinderProxyObject will reference GBinderRemoteObject */
+ GBinderProxyObject* subp = gbinder_proxy_object_new(c->local, remote);
+
+ /*
+ * Auto-created proxies may get spontaneously destroyed and
+ * not necessarily on the UI thread.
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_proxy_object.h
^
|
@@ -0,0 +1,66 @@
+/*
+ * Copyright (C) 2021 Jolla Ltd.
+ * Copyright (C) 2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef GBINDER_PROXY_OBJECT_H
+#define GBINDER_PROXY_OBJECT_H
+
+#include "gbinder_local_object_p.h"
+
+typedef struct gbinder_proxy_object_priv GBinderProxyObjectPriv;
+
+struct gbinder_proxy_object {
+ GBinderLocalObject parent;
+ GBinderProxyObjectPriv* priv;
+ GBinderRemoteObject* remote;
+};
+
+GType gbinder_proxy_object_get_type(void) GBINDER_INTERNAL;
+#define GBINDER_TYPE_PROXY_OBJECT gbinder_proxy_object_get_type()
+#define GBINDER_PROXY_OBJECT(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), \
+ GBINDER_TYPE_PROXY_OBJECT, GBinderProxyObject))
+
+/* Registers with src and forwards all transactions to the remote */
+GBinderProxyObject*
+gbinder_proxy_object_new(
+ GBinderIpc* src,
+ GBinderRemoteObject* remote)
+ GBINDER_INTERNAL;
+
+#endif /* GBINDER_PROXY_OBJECT_H */
+
+/*
+ * Local Variables:
+ * mode: C
+ * c-basic-offset: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_remote_object.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -36,19 +36,20 @@
#include "gbinder_ipc.h"
#include "gbinder_remote_object_p.h"
#include "gbinder_servicemanager_p.h"
+#include "gbinder_eventloop_p.h"
#include "gbinder_log.h"
struct gbinder_remote_object_priv {
- GMainContext* context;
+ gboolean acquired;
};
typedef GObjectClass GBinderRemoteObjectClass;
+GType gbinder_remote_object_get_type(void) GBINDER_INTERNAL;
G_DEFINE_TYPE(GBinderRemoteObject, gbinder_remote_object, G_TYPE_OBJECT)
-GType gbinder_remote_object_get_type(void);
-#define GBINDER_TYPE_REMOTE_OBJECT (gbinder_remote_object_get_type())
-#define GBINDER_REMOTE_OBJECT(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), \
- GBINDER_TYPE_REMOTE_OBJECT, GBinderRemoteObject))
+#define PARENT_CLASS gbinder_remote_object_parent_class
+#define THIS_TYPE (gbinder_remote_object_get_type())
+#define THIS(obj) G_TYPE_CHECK_INSTANCE_CAST(obj,THIS_TYPE,GBinderRemoteObject)
enum gbinder_remote_object_signal {
SIGNAL_DEATH,
@@ -65,34 +66,31 @@
static
void
-gbinder_remote_object_died_on_main_thread(
- GBinderRemoteObject* self)
+gbinder_remote_object_handle_death_on_main_thread(
+ gpointer user_data)
{
- GBinderIpc* ipc = self->ipc;
- GBinderDriver* driver = ipc->driver;
+ GBinderRemoteObject* self = THIS(user_data);
- GASSERT(!self->dead);
if (!self->dead) {
+ GBinderIpc* ipc = self->ipc;
+ GBinderDriver* driver = ipc->driver;
+ GBinderRemoteObjectPriv* priv = self->priv;
+
self->dead = TRUE;
+ if (priv->acquired) {
+ priv->acquired = FALSE;
+ /* Release the dead node */
+ gbinder_driver_release(driver, self->handle);
+ }
/* ServiceManager always has the same handle, and can be reanimated. */
if (self->handle != GBINDER_SERVICEMANAGER_HANDLE) {
- gbinder_ipc_invalidate_remote_handle(self->ipc, self->handle);
+ gbinder_ipc_invalidate_remote_handle(ipc, self->handle);
}
- gbinder_driver_clear_death_notification(driver, self);
- gbinder_driver_release(driver, self->handle);
+ gbinder_driver_dead_binder_done(driver, self);
g_signal_emit(self, gbinder_remote_object_signals[SIGNAL_DEATH], 0);
}
}
-static
-gboolean
-gbinder_remote_object_died_handle(
- gpointer self)
-{
- gbinder_remote_object_died_on_main_thread(GBINDER_REMOTE_OBJECT(self));
- return G_SOURCE_REMOVE;
-}
-
/*==========================================================================*
* Internal interface
*==========================================================================*/
@@ -108,15 +106,20 @@
*/
if (self->dead) {
GBinderIpc* ipc = self->ipc;
- GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
+ guint32 handle = self->handle;
/* Kick the horse */
GASSERT(self->handle == GBINDER_SERVICEMANAGER_HANDLE);
- if (gbinder_driver_ping(ipc->driver, reg, self->handle) == 0) {
+ if (gbinder_ipc_ping_sync(ipc, handle, &gbinder_ipc_sync_main) == 0) {
+ GBinderRemoteObjectPriv* priv = self->priv;
+ GBinderDriver* driver = ipc->driver;
+
/* Wow, it's alive! */
self->dead = FALSE;
- gbinder_driver_acquire(ipc->driver, self->handle);
- gbinder_driver_request_death_notification(ipc->driver, self);
+ priv->acquired = TRUE;
+ gbinder_ipc_looper_check(ipc); /* For death notifications */
+ gbinder_driver_acquire(driver, handle);
+ gbinder_driver_request_death_notification(driver, self);
}
}
return !self->dead;
@@ -129,9 +132,33 @@
/* This function is invoked from the looper thread, the caller has
* checked the object pointer */
GVERBOSE_("%p %u", self, self->handle);
- g_main_context_invoke_full(self->priv->context, G_PRIORITY_DEFAULT,
- gbinder_remote_object_died_handle, gbinder_remote_object_ref(self),
- g_object_unref);
+ gbinder_idle_callback_invoke_later
+ (gbinder_remote_object_handle_death_on_main_thread,
+ gbinder_remote_object_ref(self), g_object_unref);
+}
+
+void
+gbinder_remote_object_commit_suicide(
+ GBinderRemoteObject* self)
+{
+ /* This function is only invoked by GBinderProxyObject in context of
+ * the main thread, the object pointer is checked by the caller */
+ if (!self->dead) {
+ GBinderIpc* ipc = self->ipc;
+ GBinderDriver* driver = ipc->driver;
+ GBinderRemoteObjectPriv* priv = self->priv;
+
+ self->dead = TRUE;
+ if (priv->acquired) {
+ priv->acquired = FALSE;
+ /* Release the dead node */
+ gbinder_driver_release(driver, self->handle);
+ }
+ GVERBOSE_("%p %u", self, self->handle);
+ gbinder_ipc_invalidate_remote_handle(self->ipc, self->handle);
+ /* Don't submit BC_DEAD_BINDER_DONE because this is a suicide */
+ g_signal_emit(self, gbinder_remote_object_signals[SIGNAL_DEATH], 0);
+ }
}
/*==========================================================================*
@@ -142,16 +169,29 @@
gbinder_remote_object_new(
GBinderIpc* ipc,
guint32 handle,
- gboolean dead)
+ REMOTE_OBJECT_CREATE create)
{
if (G_LIKELY(ipc)) {
- GBinderRemoteObject* self = g_object_new
- (GBINDER_TYPE_REMOTE_OBJECT, NULL);
+ GBinderRemoteObject* self = g_object_new(THIS_TYPE, NULL);
+ GBinderRemoteObjectPriv* priv = self->priv;
self->ipc = gbinder_ipc_ref(ipc);
self->handle = handle;
- if (!(self->dead = dead)) {
- gbinder_driver_acquire(ipc->driver, handle);
+ switch (create) {
+ case REMOTE_OBJECT_CREATE_DEAD:
+ self->dead = TRUE;
+ break;
+ case REMOTE_OBJECT_CREATE_ACQUIRED:
+ priv->acquired = TRUE;
+ /* fallthrough */
+ case REMOTE_OBJECT_CREATE_ALIVE:
+ break;
+ }
+ if (!self->dead) {
+ gbinder_ipc_looper_check(self->ipc); /* For death notifications */
+ if (priv->acquired) {
+ gbinder_driver_acquire(ipc->driver, handle);
+ }
gbinder_driver_request_death_notification(ipc->driver, self);
}
return self;
@@ -164,7 +204,7 @@
GBinderRemoteObject* self)
{
if (G_LIKELY(self)) {
- g_object_ref(GBINDER_REMOTE_OBJECT(self));
+ g_object_ref(THIS(self));
return self;
} else {
return NULL;
@@ -176,7 +216,7 @@
GBinderRemoteObject* self)
{
if (G_LIKELY(self)) {
- g_object_unref(GBINDER_REMOTE_OBJECT(self));
+ g_object_unref(THIS(self));
}
}
@@ -228,38 +268,40 @@
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_remote_object_p.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -51,11 +51,17 @@
#define gbinder_remote_object_dev(obj) (gbinder_driver_dev((obj)->ipc->driver))
#define gbinder_remote_object_io(obj) (gbinder_driver_io((obj)->ipc->driver))
+typedef enum gbinder_remote_object_create {
+ REMOTE_OBJECT_CREATE_DEAD,
+ REMOTE_OBJECT_CREATE_ALIVE,
+ REMOTE_OBJECT_CREATE_ACQUIRED
+} REMOTE_OBJECT_CREATE;
+
GBinderRemoteObject*
gbinder_remote_object_new(
GBinderIpc* ipc,
guint32 handle,
- gboolean maybe_dead)
+ REMOTE_OBJECT_CREATE create)
GBINDER_INTERNAL;
gboolean
@@ -68,6 +74,11 @@
GBinderRemoteObject* obj)
GBINDER_INTERNAL;
+void
+gbinder_remote_object_commit_suicide(
+ GBinderRemoteObject* self)
+ GBINDER_INTERNAL;
+
#endif /* GBINDER_REMOTE_OBJECT_PRIVATE_H */
/*
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_remote_reply.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018 Jolla Ltd.
- * Copyright (C) 2018 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -118,10 +118,22 @@
gbinder_remote_reply_copy_to_local(
GBinderRemoteReply* self)
{
+ return gbinder_remote_reply_convert_to_local(self, NULL);
+}
+
+GBinderLocalReply*
+gbinder_remote_reply_convert_to_local(
+ GBinderRemoteReply* self,
+ GBinderObjectConverter* convert)
+{
if (G_LIKELY(self)) {
GBinderReaderData* d = &self->data;
+ GBinderObjectRegistry* reg = d->reg;
- return gbinder_local_reply_new_from_data(d->buffer);
+ if (reg) {
+ return gbinder_local_reply_set_contents
+ (gbinder_local_reply_new(reg->io), d->buffer, convert);
+ }
}
return NULL;
}
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_remote_reply_p.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -42,6 +42,12 @@
GBinderObjectRegistry* reg)
GBINDER_INTERNAL;
+GBinderLocalReply*
+gbinder_remote_reply_convert_to_local(
+ GBinderRemoteReply* reply,
+ GBinderObjectConverter* convert)
+ GBINDER_INTERNAL;
+
void
gbinder_remote_reply_set_data(
GBinderRemoteReply* reply,
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_remote_request.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018 Jolla Ltd.
- * Copyright (C) 2018 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -34,8 +34,10 @@
#include "gbinder_reader_p.h"
#include "gbinder_rpc_protocol.h"
#include "gbinder_local_request_p.h"
+#include "gbinder_object_converter.h"
#include "gbinder_object_registry.h"
#include "gbinder_buffer_p.h"
+#include "gbinder_driver.h"
#include "gbinder_log.h"
#include <gutil_macros.h>
@@ -85,7 +87,33 @@
if (G_LIKELY(self)) {
GBinderReaderData* d = &self->data;
- return gbinder_local_request_new_from_data(d->buffer);
+ return gbinder_local_request_new_from_data(d->buffer, NULL);
+ }
+ return NULL;
+}
+
+GBinderLocalRequest*
+gbinder_remote_request_convert_to_local(
+ GBinderRemoteRequest* req,
+ GBinderObjectConverter* convert)
+{
+ GBinderRemoteRequestPriv* self = gbinder_remote_request_cast(req);
+
+ if (G_LIKELY(self)) {
+ GBinderReaderData* data = &self->data;
+
+ if (!convert || convert->protocol == self->protocol) {
+ /* The same protocol, the same format of RPC header */
+ return gbinder_local_request_new_from_data(data->buffer, convert);
+ } else {
+ /* Need to translate to another format */
+ GBinderLocalRequest* local = gbinder_local_request_new_iface
+ (convert->io, convert->protocol, self->iface);
+
+ gbinder_local_request_append_contents(local, data->buffer,
+ self->header_size, convert);
+ return local;
+ }
}
return NULL;
}
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_remote_request_p.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -56,6 +56,12 @@
GBinderBuffer* buffer)
GBINDER_INTERNAL;
+GBinderLocalRequest*
+gbinder_remote_request_convert_to_local(
+ GBinderRemoteRequest* req,
+ GBinderObjectConverter* convert)
+ GBINDER_INTERNAL;
+
#endif /* GBINDER_REMOTE_REQUEST_PRIVATE_H */
/*
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_rpc_protocol.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2020 Jolla Ltd.
+ * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -33,6 +33,12 @@
#include "gbinder_rpc_protocol.h"
#include "gbinder_reader.h"
#include "gbinder_writer.h"
+#include "gbinder_config.h"
+#include "gbinder_log.h"
+
+#define STRICT_MODE_PENALTY_GATHER (0x40 << 16)
+#define BINDER_RPC_FLAGS (STRICT_MODE_PENALTY_GATHER)
+#define UNSET_WORK_SOURCE (-1)
/*==========================================================================*
* GBinderIpcProtocol callbacks (see Parcel::writeInterfaceToken in Android)
@@ -40,19 +46,39 @@
*
* platform/system/libhwbinder/Parcel.cpp
* platform/frameworks/native/libs/binder/Parcel.cpp
+ *
+ * which mutate from version to version. Specific device => protocol
+ * mapping can be optionally configured in /etc/gbinder.conf file.
+ * The default protocol configuration looks like this:
+ *
+ * [Protocol]
+ * Default = aidl
+ * /dev/binder = aidl
+ * /dev/hwbinder = hidl
+ *
*==========================================================================*/
+#define CONF_GROUP GBINDER_CONFIG_GROUP_PROTOCOL
+#define CONF_DEFAULT GBINDER_CONFIG_VALUE_DEFAULT
+
+static GHashTable* gbinder_rpc_protocol_map = NULL;
+
+/*
+ * Default protocol for those binder devices which which haven't been
+ * explicitely mapped.
+ */
+#define DEFAULT_PROTOCOL gbinder_rpc_protocol_aidl
+static const GBinderRpcProtocol DEFAULT_PROTOCOL;
+static const GBinderRpcProtocol* gbinder_rpc_protocol_default =
+ &DEFAULT_PROTOCOL;
+
/*==========================================================================*
- * /dev/binder
+ * The original AIDL protocol.
*==========================================================================*/
-/* No idea what that is... */
-#define STRICT_MODE_PENALTY_GATHER (0x40 << 16)
-#define BINDER_RPC_FLAGS (STRICT_MODE_PENALTY_GATHER)
-
static
void
-gbinder_rpc_protocol_binder_write_ping(
+gbinder_rpc_protocol_aidl_write_ping(
GBinderWriter* writer)
{
/* No payload */
@@ -60,7 +86,7 @@
static
void
-gbinder_rpc_protocol_binder_write_rpc_header(
+gbinder_rpc_protocol_aidl_write_rpc_header(
GBinderWriter* writer,
const char* iface)
{
@@ -75,7 +101,7 @@
static
const char*
-gbinder_rpc_protocol_binder_read_rpc_header(
+gbinder_rpc_protocol_aidl_read_rpc_header(
GBinderReader* reader,
guint32 txcode,
char** iface)
@@ -91,13 +117,69 @@
return *iface;
}
+static const GBinderRpcProtocol gbinder_rpc_protocol_aidl = {
+ .name = "aidl",
+ .ping_tx = GBINDER_PING_TRANSACTION,
+ .write_ping = gbinder_rpc_protocol_aidl_write_ping,
+ .write_rpc_header = gbinder_rpc_protocol_aidl_write_rpc_header,
+ .read_rpc_header = gbinder_rpc_protocol_aidl_read_rpc_header
+};
+
+/*==========================================================================*
+ * AIDL protocol appeared in Android 10 (API level 29)
+ *==========================================================================*/
+
+static
+void
+gbinder_rpc_protocol_aidl2_write_rpc_header(
+ GBinderWriter* writer,
+ const char* iface)
+{
+ /*
+ * writeInt32(IPCThreadState::self()->getStrictModePolicy() |
+ * STRICT_MODE_PENALTY_GATHER);
+ * writeInt32(IPCThreadState::kUnsetWorkSource);
+ * writeString16(interface);
+ */
+ gbinder_writer_append_int32(writer, BINDER_RPC_FLAGS);
+ gbinder_writer_append_int32(writer, UNSET_WORK_SOURCE);
+ gbinder_writer_append_string16(writer, iface);
+}
+
+static
+const char*
+gbinder_rpc_protocol_aidl2_read_rpc_header(
+ GBinderReader* reader,
+ guint32 txcode,
+ char** iface)
+{
+ if (txcode > GBINDER_TRANSACTION(0,0,0)) {
+ /* Internal transaction e.g. GBINDER_DUMP_TRANSACTION etc. */
+ *iface = NULL;
+ } else if (gbinder_reader_read_int32(reader, NULL) /* flags */ &&
+ gbinder_reader_read_int32(reader, NULL) /* work source */) {
+ *iface = gbinder_reader_read_string16(reader);
+ } else {
+ *iface = NULL;
+ }
+ return *iface;
+}
+
+static const GBinderRpcProtocol gbinder_rpc_protocol_aidl2 = {
+ .name = "aidl2",
+ .ping_tx = GBINDER_PING_TRANSACTION,
+ .write_ping = gbinder_rpc_protocol_aidl_write_ping, /* no payload */
+ .write_rpc_header = gbinder_rpc_protocol_aidl2_write_rpc_header,
+ .read_rpc_header = gbinder_rpc_protocol_aidl2_read_rpc_header
+};
+
/*==========================================================================*
- * /dev/hwbinder
+ * The original /dev/hwbinder protocol.
*==========================================================================*/
static
void
-gbinder_rpc_protocol_hwbinder_write_rpc_header(
+gbinder_rpc_protocol_hidl_write_rpc_header(
GBinderWriter* writer,
const char* iface)
{
@@ -109,16 +191,16 @@
static
void
-gbinder_rpc_protocol_hwbinder_write_ping(
+gbinder_rpc_protocol_hidl_write_ping(
GBinderWriter* writer)
{
- gbinder_rpc_protocol_hwbinder_write_rpc_header(writer,
+ gbinder_rpc_protocol_hidl_write_rpc_header(writer,
"android.hidl.base@1.0::IBase");
}
static
const char*
-gbinder_rpc_protocol_hwbinder_read_rpc_header(
+gbinder_rpc_protocol_hidl_read_rpc_header(
GBinderReader* reader,
guint32 txcode,
char** iface)
@@ -127,30 +209,126 @@
return gbinder_reader_read_string8(reader);
}
+static const GBinderRpcProtocol gbinder_rpc_protocol_hidl = {
+ .name = "hidl",
+ .ping_tx = HIDL_PING_TRANSACTION,
+ .write_ping = gbinder_rpc_protocol_hidl_write_ping,
+ .write_rpc_header = gbinder_rpc_protocol_hidl_write_rpc_header,
+ .read_rpc_header = gbinder_rpc_protocol_hidl_read_rpc_header
+};
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_rpc_protocol.h
^
|
@@ -13,7 +13,6 @@
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
- * documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
* contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
@@ -37,11 +36,12 @@
#include "gbinder_types_p.h"
/*
- * For whatever reason services communicating via /dev/binder
- * and /dev/hwbinder use slightly different RPC headers.
+ * There are several versions of binder RPC protocol with diffferent
+ * transaction headers and transaction codes.
*/
struct gbinder_rpc_protocol {
+ const char* name;
guint32 ping_tx;
void (*write_ping)(GBinderWriter* writer);
void (*write_rpc_header)(GBinderWriter* writer, const char* iface);
@@ -49,15 +49,19 @@
char** iface);
};
-extern const GBinderRpcProtocol gbinder_rpc_protocol_binder GBINDER_INTERNAL;
-extern const GBinderRpcProtocol gbinder_rpc_protocol_hwbinder GBINDER_INTERNAL;
-
/* Returns one of the above based on the device name */
const GBinderRpcProtocol*
gbinder_rpc_protocol_for_device(
const char* dev)
GBINDER_INTERNAL;
+/* Runs at exit, declared here strictly for unit tests */
+void
+gbinder_rpc_protocol_exit(
+ void)
+ GBINDER_DESTRUCTOR
+ GBINDER_INTERNAL;
+
#endif /* GBINDER_RPC_PROTOCOL_H */
/*
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_servicemanager.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -34,6 +34,7 @@
#include "gbinder_servicemanager_p.h"
#include "gbinder_client_p.h"
+#include "gbinder_config.h"
#include "gbinder_local_object_p.h"
#include "gbinder_remote_object_p.h"
#include "gbinder_eventloop_p.h"
@@ -47,6 +48,51 @@
#include <errno.h>
+/*==========================================================================*
+ *
+ * Different versions of Android come with different flavors of service
+ * managers. They are usually based on these two more or less independent
+ * variants:
+ *
+ * platform/frameworks/native/cmds/servicemanager/ServiceManager.cpp
+ * platform/system/hwservicemanager/ServiceManager.cpp
+ *
+ * They are talking slightly different protocols which slightly mutate
+ * from version to version. If that's not complex enough, different
+ * kinds of service managers can be running simultaneously, serving
+ * different binder devices. Specific device => servicemanager mapping
+ * can be optionally configured in /etc/gbinder.conf file. The default
+ * service manager configuration looks like this:
+ *
+ * [ServiceManager]
+ * Default = aidl
+ * /dev/binder = aidl
+ * /dev/hwbinder = hidl
+ *
+ *==========================================================================*/
+
+#define CONF_GROUP GBINDER_CONFIG_GROUP_SERVICEMANAGER
+#define CONF_DEFAULT GBINDER_CONFIG_VALUE_DEFAULT
+
+typedef struct gbinder_servicemanager_type {
+ const char* name;
+ GType (*get_type)(void);
+} GBinderServiceManagerType;
+
+static const GBinderServiceManagerType gbinder_servicemanager_types[] = {
+ { "aidl", gbinder_servicemanager_aidl_get_type },
+ { "aidl2", gbinder_servicemanager_aidl2_get_type },
+ { "hidl", gbinder_servicemanager_hidl_get_type }
+};
+
+#define SERVICEMANAGER_TYPE_AIDL (gbinder_servicemanager_types + 0)
+#define SERVICEMANAGER_TYPE_HIDL (gbinder_servicemanager_types + 2)
+#define SERVICEMANAGER_TYPE_DEFAULT SERVICEMANAGER_TYPE_AIDL
+
+static GHashTable* gbinder_servicemanager_map = NULL;
+static const GBinderServiceManagerType* gbinder_servicemanager_default =
+ SERVICEMANAGER_TYPE_DEFAULT;
+
#define PRESENSE_WAIT_MS_MIN (100)
#define PRESENSE_WAIT_MS_MAX (1000)
#define PRESENSE_WAIT_MS_STEP (100)
@@ -75,9 +121,6 @@
#define GBINDER_SERVICEMANAGER(obj) \
G_TYPE_CHECK_INSTANCE_CAST((obj), GBINDER_TYPE_SERVICEMANAGER, \
GBinderServiceManager)
-#define GBINDER_SERVICEMANAGER_CLASS(klass) \
- G_TYPE_CHECK_CLASS_CAST((klass), GBINDER_TYPE_SERVICEMANAGER, \
- GBinderServiceManagerClass)
#define GBINDER_SERVICEMANAGER_GET_CLASS(obj) \
G_TYPE_INSTANCE_GET_CLASS((obj), GBINDER_TYPE_SERVICEMANAGER, \
GBinderServiceManagerClass)
@@ -156,7 +199,8 @@
{
GBinderServiceManagerListTxData* data = tx->user_data;
- data->result = GBINDER_SERVICEMANAGER_GET_CLASS(data->sm)->list(data->sm);
+ data->result = GBINDER_SERVICEMANAGER_GET_CLASS(data->sm)->
+ list(data->sm, &gbinder_ipc_sync_worker);
}
static
@@ -200,8 +244,9 @@
{
GBinderServiceManagerGetServiceTxData* data = tx->user_data;
- data->obj = GBINDER_SERVICEMANAGER_GET_CLASS(data->sm)->get_service
- (data->sm, data->name, &data->status);
+ data->obj = GBINDER_SERVICEMANAGER_GET_CLASS(data->sm)->
+ get_service(data->sm, data->name, &data->status,
+ &gbinder_ipc_sync_worker);
}
static
@@ -243,8 +288,8 @@
{
GBinderServiceManagerAddServiceTxData* data = tx->user_data;
- data->status = GBINDER_SERVICEMANAGER_GET_CLASS(data->sm)->add_service
- (data->sm, data->name, data->obj);
+ data->status = GBINDER_SERVICEMANAGER_GET_CLASS(data->sm)->
+ add_service(data->sm, data->name, data->obj, &gbinder_ipc_sync_worker);
}
static
@@ -408,6 +453,64 @@
g_slist_free_full(list, g_object_unref);
}
+static
+void
+gbinder_servicemanager_map_add_default(
+ GHashTable* map,
+ const char* dev,
+ const GBinderServiceManagerType* type)
+{
+ if (!g_hash_table_contains(map, dev)) {
+ g_hash_table_insert(map, g_strdup(dev), (gpointer) type);
+ }
+}
+
+static
+gconstpointer
+gbinder_servicemanager_value_map(
+ const char* name)
+{
+ guint i;
+
+ for (i = 0; i < G_N_ELEMENTS(gbinder_servicemanager_types); i++) {
+ const GBinderServiceManagerType* t = gbinder_servicemanager_types + i;
+
+ if (!g_strcmp0(name, t->name)) {
+ return t;
+ }
+ }
+ return NULL;
+}
+
+static
+GHashTable*
+gbinder_servicemanager_load_config()
+{
+ GHashTable* map = gbinder_config_load(CONF_GROUP,
+ gbinder_servicemanager_value_map);
+
+ /* Add default configuration if it's not overridden */
+ gbinder_servicemanager_map_add_default(map,
+ GBINDER_DEFAULT_BINDER, SERVICEMANAGER_TYPE_AIDL);
+ gbinder_servicemanager_map_add_default(map,
+ GBINDER_DEFAULT_HWBINDER, SERVICEMANAGER_TYPE_HIDL);
+
+ return map;
+}
+
+/* Runs at exit */
+void
+gbinder_servicemanager_exit(
+ void)
+{
+ if (gbinder_servicemanager_map) {
+ g_hash_table_destroy(gbinder_servicemanager_map);
+ gbinder_servicemanager_map = NULL;
+ }
+ /* Reset the default too, mostly for unit testing */
+ gbinder_servicemanager_default = SERVICEMANAGER_TYPE_DEFAULT;
+}
+
/*==========================================================================*
* Internal interface
*==========================================================================*/
@@ -424,11 +527,10 @@
GBinderIpc* ipc;
if (!dev) dev = klass->default_device;
- ipc = gbinder_ipc_new(dev, klass->rpc_protocol);
+ ipc = gbinder_ipc_new(dev);
if (ipc) {
- /* Create a possible dead remote object */
- GBinderRemoteObject* object = gbinder_ipc_get_remote_object
- (ipc, GBINDER_SERVICEMANAGER_HANDLE, TRUE);
+ /* Create a (possibly) dead service manager object */
+ GBinderRemoteObject* object = gbinder_ipc_get_service_manager(ipc);
if (object) {
gboolean first_ref;
@@ -517,11 +619,35 @@
gbinder_servicemanager_new(
const char* dev)
{
- if (!g_strcmp0(dev, GBINDER_DEFAULT_HWBINDER)) {
- return gbinder_hwservicemanager_new(dev);
- } else {
- return gbinder_defaultservicemanager_new(dev);
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_servicemanager_aidl.c
^
|
@@ -0,0 +1,343 @@
+/*
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#define GLIB_DISABLE_DEPRECATION_WARNINGS
+
+#include "gbinder_servicemanager_aidl.h"
+#include "gbinder_servicepoll.h"
+#include "gbinder_eventloop_p.h"
+#include "gbinder_client_p.h"
+#include "gbinder_log.h"
+
+#include <gbinder_local_request.h>
+#include <gbinder_remote_reply.h>
+
+typedef struct gbinder_servicemanager_aidl_watch {
+ GBinderServicePoll* poll;
+ char* name;
+ gulong handler_id;
+ GBinderEventLoopTimeout* notify;
+} GBinderServiceManagerAidlWatch;
+
+struct gbinder_servicemanager_aidl_priv {
+ GBinderServicePoll* poll;
+ GHashTable* watch_table;
+};
+
+G_DEFINE_TYPE(GBinderServiceManagerAidl,
+ gbinder_servicemanager_aidl,
+ GBINDER_TYPE_SERVICEMANAGER)
+
+#define PARENT_CLASS gbinder_servicemanager_aidl_parent_class
+#define GBINDER_SERVICEMANAGER_AIDL(obj) \
+ G_TYPE_CHECK_INSTANCE_CAST((obj), GBINDER_TYPE_SERVICEMANAGER_AIDL, \
+ GBinderServiceManagerAidl)
+#define GBINDER_SERVICEMANAGER_AIDL_GET_CLASS(obj) \
+ G_TYPE_INSTANCE_GET_CLASS((obj), GBINDER_TYPE_SERVICEMANAGER_AIDL, \
+ GBinderServiceManagerAidlClass)
+
+enum gbinder_servicemanager_aidl_calls {
+ GET_SERVICE_TRANSACTION = GBINDER_FIRST_CALL_TRANSACTION,
+ CHECK_SERVICE_TRANSACTION,
+ ADD_SERVICE_TRANSACTION,
+ LIST_SERVICES_TRANSACTION
+};
+
+#define SERVICEMANAGER_AIDL_IFACE "android.os.IServiceManager"
+
+static
+void
+gbinder_servicemanager_aidl_watch_proc(
+ GBinderServicePoll* poll,
+ const char* name_added,
+ void* user_data)
+{
+ GBinderServiceManagerAidlWatch* watch = user_data;
+
+ if (!g_strcmp0(name_added, watch->name)) {
+ GBinderServiceManager* manager =
+ gbinder_servicepoll_manager(watch->poll);
+
+ if (watch->notify) {
+ gbinder_timeout_remove(watch->notify);
+ watch->notify = NULL;
+ }
+ gbinder_servicemanager_service_registered(manager, name_added);
+ }
+}
+
+static
+gboolean
+gbinder_servicemanager_aidl_watch_notify(
+ gpointer user_data)
+{
+ GBinderServiceManagerAidlWatch* watch = user_data;
+ GBinderServiceManager* manager = gbinder_servicepoll_manager(watch->poll);
+ char* name = g_strdup(watch->name);
+
+ GASSERT(watch->notify);
+ watch->notify = NULL;
+ gbinder_servicemanager_service_registered(manager, name);
+ g_free(name);
+ return G_SOURCE_REMOVE;
+}
+
+static
+void
+gbinder_servicemanager_aidl_watch_free(
+ gpointer user_data)
+{
+ GBinderServiceManagerAidlWatch* watch = user_data;
+
+ gbinder_timeout_remove(watch->notify);
+ gbinder_servicepoll_remove_handler(watch->poll, watch->handler_id);
+ gbinder_servicepoll_unref(watch->poll);
+ g_free(watch->name);
+ g_slice_free(GBinderServiceManagerAidlWatch, watch);
+}
+
+static
+GBinderServiceManagerAidlWatch*
+gbinder_servicemanager_aidl_watch_new(
+ GBinderServiceManagerAidl* self,
+ const char* name)
+{
+ GBinderServiceManagerAidlPriv* priv = self->priv;
+ GBinderServiceManagerAidlWatch* watch =
+ g_slice_new0(GBinderServiceManagerAidlWatch);
+
+ watch->name = g_strdup(name);
+ watch->poll = gbinder_servicepoll_new(&self->manager, &priv->poll);
+ watch->handler_id = gbinder_servicepoll_add_handler(priv->poll,
+ gbinder_servicemanager_aidl_watch_proc, watch);
+ return watch;
+}
+
+static
+GBinderLocalRequest*
+gbinder_servicemanager_aidl_list_services_req(
+ GBinderClient* client,
+ gint32 index)
+{
+ GBinderLocalRequest* req = gbinder_client_new_request(client);
+
+ gbinder_local_request_append_int32(req, index);
+ return req;
+}
+
+static
+GBinderLocalRequest*
+gbinder_servicemanager_aidl_add_service_req(
+ GBinderClient* client,
+ const char* name,
+ GBinderLocalObject* obj)
+{
+ GBinderLocalRequest* req = gbinder_client_new_request(client);
+
+ gbinder_local_request_append_string16(req, name);
+ gbinder_local_request_append_local_object(req, obj);
+ gbinder_local_request_append_int32(req, 0);
+ return req;
+}
+
+static
+char**
+gbinder_servicemanager_aidl_list(
+ GBinderServiceManager* manager,
+ const GBinderIpcSyncApi* api)
+{
+ GPtrArray* list = g_ptr_array_new();
+ GBinderClient* client = manager->client;
+ GBinderServiceManagerAidlClass* klass =
+ GBINDER_SERVICEMANAGER_AIDL_GET_CLASS(manager);
+ GBinderLocalRequest* req = klass->list_services_req(client, 0);
+ GBinderRemoteReply* reply;
+
+ while ((reply = gbinder_client_transact_sync_reply2(client,
+ LIST_SERVICES_TRANSACTION, req, NULL, api)) != NULL) {
+ char* service = gbinder_remote_reply_read_string16(reply);
+
+ gbinder_remote_reply_unref(reply);
+ if (service) {
+ g_ptr_array_add(list, service);
+ gbinder_local_request_unref(req);
+ req = klass->list_services_req(client, list->len);
+ } else {
+ break;
+ }
+ }
+
+ gbinder_local_request_unref(req);
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_servicemanager_aidl.h
^
|
@@ -0,0 +1,66 @@
+/*
+ * Copyright (C) 2020 Jolla Ltd.
+ * Copyright (C) 2020 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef GBINDER_SERVICEMANAGER_AIDL_H
+#define GBINDER_SERVICEMANAGER_AIDL_H
+
+#include "gbinder_servicemanager_p.h"
+
+typedef struct gbinder_servicemanager_aidl_priv GBinderServiceManagerAidlPriv;
+typedef struct gbinder_servicemanager_aidl {
+ GBinderServiceManager manager;
+ GBinderServiceManagerAidlPriv* priv;
+} GBinderServiceManagerAidl;
+
+typedef struct gbinder_servicemanager_aidl_class {
+ GBinderServiceManagerClass parent;
+ GBinderLocalRequest* (*list_services_req)
+ (GBinderClient* client, gint32 index);
+ GBinderLocalRequest* (*add_service_req)
+ (GBinderClient* client, const char* name, GBinderLocalObject* obj);
+} GBinderServiceManagerAidlClass;
+
+#define GBINDER_TYPE_SERVICEMANAGER_AIDL \
+ gbinder_servicemanager_aidl_get_type()
+#define GBINDER_SERVICEMANAGER_AIDL_CLASS(klass) \
+ G_TYPE_CHECK_CLASS_CAST((klass), GBINDER_TYPE_SERVICEMANAGER_AIDL, \
+ GBinderServiceManagerAidlClass)
+
+#endif /* GBINDER_SERVICEMANAGER_AIDL_H */
+
+/*
+ * Local Variables:
+ * mode: C
+ * c-basic-offset: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_servicemanager_aidl2.c
^
|
@@ -0,0 +1,102 @@
+/*
+ * Copyright (C) 2020 Jolla Ltd.
+ * Copyright (C) 2020 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "gbinder_servicemanager_aidl.h"
+
+#include <gbinder_client.h>
+#include <gbinder_local_request.h>
+
+/* Variant of AIDL servicemanager appeared in Android 9 (API level 28) */
+
+typedef GBinderServiceManagerAidl GBinderServiceManagerAidl2;
+typedef GBinderServiceManagerAidlClass GBinderServiceManagerAidl2Class;
+
+G_DEFINE_TYPE(GBinderServiceManagerAidl2,
+ gbinder_servicemanager_aidl2,
+ GBINDER_TYPE_SERVICEMANAGER_AIDL)
+
+#define PARENT_CLASS gbinder_servicemanager_aidl2_parent_class
+#define DUMP_FLAG_PRIORITY_DEFAULT (0x08)
+#define DUMP_FLAG_PRIORITY_ALL (0x0f)
+
+static
+GBinderLocalRequest*
+gbinder_servicemanager_aidl2_list_services_req(
+ GBinderClient* client,
+ gint32 index)
+{
+ GBinderLocalRequest* req = gbinder_client_new_request(client);
+
+ gbinder_local_request_append_int32(req, index);
+ gbinder_local_request_append_int32(req, DUMP_FLAG_PRIORITY_ALL);
+ return req;
+}
+
+static
+GBinderLocalRequest*
+gbinder_servicemanager_aidl2_add_service_req(
+ GBinderClient* client,
+ const char* name,
+ GBinderLocalObject* obj)
+{
+ GBinderLocalRequest* req = gbinder_client_new_request(client);
+
+ gbinder_local_request_append_string16(req, name);
+ gbinder_local_request_append_local_object(req, obj);
+ gbinder_local_request_append_int32(req, 0);
+ gbinder_local_request_append_int32(req, DUMP_FLAG_PRIORITY_DEFAULT);
+ return req;
+}
+
+static
+void
+gbinder_servicemanager_aidl2_init(
+ GBinderServiceManagerAidl* self)
+{
+}
+
+static
+void
+gbinder_servicemanager_aidl2_class_init(
+ GBinderServiceManagerAidl2Class* cls)
+{
+ cls->list_services_req = gbinder_servicemanager_aidl2_list_services_req;
+ cls->add_service_req = gbinder_servicemanager_aidl2_add_service_req;
+}
+
+/*
+ * Local Variables:
+ * mode: C
+ * c-basic-offset: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_servicemanager_hidl.c
^
|
@@ -0,0 +1,393 @@
+/*
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "gbinder_servicemanager_p.h"
+#include "gbinder_client_p.h"
+#include "gbinder_log.h"
+
+#include <gbinder_local_object.h>
+#include <gbinder_local_request.h>
+#include <gbinder_remote_reply.h>
+#include <gbinder_remote_request.h>
+#include <gbinder_reader.h>
+
+#include <errno.h>
+
+typedef struct gbinder_servicemanager_hidl_watch {
+ char* name;
+ GBinderLocalObject* callback;
+} GBinderServiceManagerHidlWatch;
+
+typedef GBinderServiceManagerClass GBinderServiceManagerHidlClass;
+typedef struct gbinder_servicemanager_hidl {
+ GBinderServiceManager manager;
+ GHashTable* watch_table;
+} GBinderServiceManagerHidl;
+
+G_DEFINE_TYPE(GBinderServiceManagerHidl,
+ gbinder_servicemanager_hidl,
+ GBINDER_TYPE_SERVICEMANAGER)
+
+#define PARENT_CLASS gbinder_servicemanager_hidl_parent_class
+#define GBINDER_TYPE_SERVICEMANAGER_HIDL \
+ gbinder_servicemanager_hidl_get_type()
+#define GBINDER_SERVICEMANAGER_HIDL(obj) \
+ G_TYPE_CHECK_INSTANCE_CAST((obj), GBINDER_TYPE_SERVICEMANAGER_HIDL, \
+ GBinderServiceManagerHidl)
+
+enum gbinder_servicemanager_hidl_calls {
+ GET_TRANSACTION = GBINDER_FIRST_CALL_TRANSACTION,
+ ADD_TRANSACTION,
+ GET_TRANSPORT_TRANSACTION,
+ LIST_TRANSACTION,
+ LIST_BY_INTERFACE_TRANSACTION,
+ REGISTER_FOR_NOTIFICATIONS_TRANSACTION,
+ DEBUG_DUMP_TRANSACTION,
+ REGISTER_PASSTHROUGH_CLIENT_TRANSACTION
+};
+
+enum gbinder_servicemanager_hidl_notifications {
+ ON_REGISTRATION_TRANSACTION = GBINDER_FIRST_CALL_TRANSACTION
+};
+
+#define SERVICEMANAGER_HIDL_IFACE "android.hidl.manager@1.0::IServiceManager"
+#define SERVICEMANAGER_HIDL_NOTIFICATION_IFACE \
+ "android.hidl.manager@1.0::IServiceNotification"
+
+static
+void
+gbinder_servicemanager_hidl_handle_registration(
+ GBinderServiceManagerHidl* self,
+ GBinderReader* reader)
+{
+ char* fqname = gbinder_reader_read_hidl_string(reader);
+ char* name = gbinder_reader_read_hidl_string(reader);
+ gboolean preexisting;
+
+ /* (string fqName, string name, bool preexisting) */
+ if (fqname && name && gbinder_reader_read_bool(reader, &preexisting) &&
+ gbinder_reader_at_end(reader)) {
+ char* full_name = g_strconcat(fqname, "/", name, NULL);
+
+ GDEBUG("%s %s", full_name, preexisting ? "true" : "false");
+ gbinder_servicemanager_service_registered(&self->manager, full_name);
+ g_free(full_name);
+ } else {
+ GWARN("Failed to parse IServiceNotification::onRegistration payload");
+ }
+ g_free(fqname);
+ g_free(name);
+}
+
+static
+GBinderLocalReply*
+gbinder_servicemanager_hidl_notification(
+ GBinderLocalObject* obj,
+ GBinderRemoteRequest* req,
+ guint code,
+ guint flags,
+ int* status,
+ void* user_data)
+{
+ GBinderServiceManagerHidl* self = GBINDER_SERVICEMANAGER_HIDL(user_data);
+ const char* iface = gbinder_remote_request_interface(req);
+
+ if (!g_strcmp0(iface, SERVICEMANAGER_HIDL_NOTIFICATION_IFACE)) {
+ GBinderReader reader;
+
+ gbinder_remote_request_init_reader(req, &reader);
+ switch (code) {
+ case ON_REGISTRATION_TRANSACTION:
+ GDEBUG(SERVICEMANAGER_HIDL_NOTIFICATION_IFACE " %u onRegistration",
+ code);
+ gbinder_servicemanager_hidl_handle_registration(self, &reader);
+ *status = GBINDER_STATUS_OK;
+ break;
+ default:
+ GDEBUG(SERVICEMANAGER_HIDL_NOTIFICATION_IFACE " %u", code);
+ *status = GBINDER_STATUS_FAILED;
+ break;
+ }
+ } else {
+ GDEBUG("%s %u", iface, code);
+ *status = GBINDER_STATUS_FAILED;
+ }
+ return NULL;
+}
+
+static
+char**
+gbinder_servicemanager_hidl_list(
+ GBinderServiceManager* self,
+ const GBinderIpcSyncApi* api)
+{
+ GBinderLocalRequest* req = gbinder_client_new_request(self->client);
+ GBinderRemoteReply* reply = gbinder_client_transact_sync_reply2
+ (self->client, LIST_TRANSACTION, req, NULL, api);
+
+ gbinder_local_request_unref(req);
+ if (reply) {
+ GBinderReader reader;
+ char** result = NULL;
+ int status = -1;
+
+ gbinder_remote_reply_init_reader(reply, &reader);
+
+ /* Read status */
+ GVERIFY(gbinder_reader_read_int32(&reader, &status));
+ GASSERT(status == GBINDER_STATUS_OK);
+
+ /* Followed by hidl_vec<string> */
+ result = gbinder_reader_read_hidl_string_vec(&reader);
+ gbinder_remote_reply_unref(reply);
+ return result;
+ }
+ return NULL;
+}
+
+static
+GBinderRemoteObject*
+gbinder_servicemanager_hidl_get_service(
+ GBinderServiceManager* self,
+ const char* fqinstance,
+ int* status,
+ const GBinderIpcSyncApi* api)
+{
+ /* e.g. "android.hardware.radio@1.1::IRadio/slot1" */
+ const char* sep = strchr(fqinstance, '/');
+ GBinderRemoteObject* obj = NULL;
+
+ if (sep) {
+ GBinderRemoteReply* reply;
+ GBinderLocalRequest* req = gbinder_client_new_request(self->client);
+ char* fqname = g_strndup(fqinstance, sep - fqinstance);
+ const char* name = sep + 1;
+
+ gbinder_local_request_append_hidl_string(req, fqname);
+ gbinder_local_request_append_hidl_string(req, name);
+
+ reply = gbinder_client_transact_sync_reply2(self->client,
+ GET_TRANSACTION, req, status, api);
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_servicemanager_p.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -39,9 +39,6 @@
#include <glib-object.h>
-/* As a special case, ServiceManager's handle is zero */
-#define GBINDER_SERVICEMANAGER_HANDLE (0)
-
typedef struct gbinder_servicemanager_priv GBinderServiceManagerPriv;
typedef struct gbinder_servicemanager {
@@ -64,15 +61,13 @@
const char* iface;
const char* default_device;
- const GBinderRpcProtocol* rpc_protocol;
/* Methods (synchronous) */
- char** (*list)(GBinderServiceManager* self);
- GBinderRemoteObject* (*get_service)
- (GBinderServiceManager* self, const char* name, int* status);
- int (*add_service)
- (GBinderServiceManager* self, const char* name,
- GBinderLocalObject* obj);
+ char** (*list)(GBinderServiceManager* self, const GBinderIpcSyncApi* api);
+ GBinderRemoteObject* (*get_service)(GBinderServiceManager* self,
+ const char* name, int* status, const GBinderIpcSyncApi* api);
+ int (*add_service)(GBinderServiceManager* self, const char* name,
+ GBinderLocalObject* obj, const GBinderIpcSyncApi* api);
/* Checking/normalizing watch names */
GBINDER_SERVICEMANAGER_NAME_CHECK (*check_name)
@@ -86,6 +81,11 @@
GType gbinder_servicemanager_get_type(void) GBINDER_INTERNAL;
#define GBINDER_TYPE_SERVICEMANAGER (gbinder_servicemanager_get_type())
+#define GBINDER_SERVICEMANAGER_CLASS(klass) \
+ G_TYPE_CHECK_CLASS_CAST((klass), GBINDER_TYPE_SERVICEMANAGER, \
+ GBinderServiceManagerClass)
+
+#define gbinder_servicemanager_ipc(sm) gbinder_client_ipc(sm->client)
GBinderServiceManager*
gbinder_servicemanager_new_with_type(
@@ -99,6 +99,19 @@
const char* name)
GBINDER_INTERNAL;
+/* Declared for unit tests */
+void
+gbinder_servicemanager_exit(
+ void)
+ GBINDER_INTERNAL
+ GBINDER_DESTRUCTOR;
+
+/* Derived types */
+
+GType gbinder_servicemanager_aidl_get_type(void) GBINDER_INTERNAL;
+GType gbinder_servicemanager_aidl2_get_type(void) GBINDER_INTERNAL;
+GType gbinder_servicemanager_hidl_get_type(void) GBINDER_INTERNAL;
+
#endif /* GBINDER_SERVICEMANAGER_PRIVATE_H */
/*
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_servicename.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2019 Jolla Ltd.
- * Copyright (C) 2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2019-2021 Jolla Ltd.
+ * Copyright (C) 2019-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -31,6 +31,7 @@
*/
#include "gbinder_types_p.h"
+#include "gbinder_eventloop_p.h"
#include "gbinder_servicename.h"
#include "gbinder_servicemanager.h"
#include "gbinder_local_object.h"
@@ -40,16 +41,24 @@
/* Since 1.0.26 */
+#define GBINDER_SERVICENAME_RETRY_INTERVAL_MS (500)
+
typedef struct gbinder_servicename_priv {
GBinderServiceName pub;
gint refcount;
char* name;
GBinderLocalObject* object;
GBinderServiceManager* sm;
+ GBinderEventLoopTimeout* retry_timer;
gulong presence_id;
gulong add_call_id;
} GBinderServiceNamePriv;
+static
+void
+gbinder_servicename_add_service(
+ GBinderServiceNamePriv* priv);
+
GBINDER_INLINE_FUNC GBinderServiceNamePriv*
gbinder_servicename_cast(GBinderServiceName* pub)
{ return G_CAST(pub, GBinderServiceNamePriv, pub); }
@@ -59,6 +68,18 @@
*==========================================================================*/
static
+gboolean
+gbinder_servicename_add_service_retry(
+ gpointer user_data)
+{
+ GBinderServiceNamePriv* priv = user_data;
+
+ priv->retry_timer = NULL;
+ gbinder_servicename_add_service(priv);
+ return G_SOURCE_REMOVE;
+}
+
+static
void
gbinder_servicename_add_service_done(
GBinderServiceManager* sm,
@@ -71,6 +92,10 @@
priv->add_call_id = 0;
if (status) {
GWARN("Error %d adding name \"%s\"", status, priv->name);
+ gbinder_timeout_remove(priv->retry_timer);
+ priv->retry_timer =
+ gbinder_timeout_add(GBINDER_SERVICENAME_RETRY_INTERVAL_MS,
+ gbinder_servicename_add_service_retry, priv);
} else {
GDEBUG("Service \"%s\" has been registered", priv->name);
}
@@ -97,9 +122,15 @@
if (gbinder_servicemanager_is_present(sm)) {
gbinder_servicename_add_service(priv);
- } else if (priv->add_call_id) {
- gbinder_servicemanager_cancel(priv->sm, priv->add_call_id);
- priv->add_call_id = 0;
+ } else {
+ if (priv->add_call_id) {
+ gbinder_servicemanager_cancel(priv->sm, priv->add_call_id);
+ priv->add_call_id = 0;
+ }
+ if (priv->retry_timer) {
+ gbinder_timeout_remove(priv->retry_timer);
+ priv->retry_timer = NULL;
+ }
}
}
@@ -158,8 +189,9 @@
gbinder_servicemanager_remove_handler(priv->sm, priv->presence_id);
gbinder_servicemanager_unref(priv->sm);
gbinder_local_object_unref(priv->object);
+ gbinder_timeout_remove(priv->retry_timer);
g_free(priv->name);
- g_slice_free(GBinderServiceName, self);
+ gutil_slice_free(priv);
}
}
}
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_system.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018 Jolla Ltd.
- * Contact: Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -13,9 +13,9 @@
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
- * 3. Neither the name of Jolla Ltd nor the names of its contributors may
- * be used to endorse or promote products derived from this software
- * without specific prior written permission.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -34,6 +34,7 @@
#include <unistd.h>
#include <fcntl.h>
+#include <errno.h>
#include <sys/ioctl.h>
#include <sys/mman.h>
@@ -58,7 +59,10 @@
int request,
void* data)
{
- return ioctl(fd, request, data);
+ int ret;
+
+ while ((ret = ioctl(fd, request, data)) < 0 && errno == EINTR);
+ return ret >= 0 ? 0 : -errno;
}
void*
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_types_p.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -36,18 +36,23 @@
#include <gbinder_types.h>
typedef struct gbinder_buffer_contents GBinderBufferContents;
+typedef struct gbinder_buffer_contents_list GBinderBufferContentsList;
typedef struct gbinder_cleanup GBinderCleanup;
typedef struct gbinder_driver GBinderDriver;
typedef struct gbinder_handler GBinderHandler;
typedef struct gbinder_io GBinderIo;
+typedef struct gbinder_object_converter GBinderObjectConverter;
typedef struct gbinder_object_registry GBinderObjectRegistry;
typedef struct gbinder_output_data GBinderOutputData;
+typedef struct gbinder_proxy_object GBinderProxyObject;
typedef struct gbinder_rpc_protocol GBinderRpcProtocol;
typedef struct gbinder_servicepoll GBinderServicePoll;
typedef struct gbinder_ipc_looper_tx GBinderIpcLooperTx;
+typedef struct gbinder_ipc_sync_api GBinderIpcSyncApi;
#define GBINDER_INLINE_FUNC static inline
#define GBINDER_INTERNAL G_GNUC_INTERNAL
+#define GBINDER_DESTRUCTOR __attribute__((destructor))
#define GBINDER_TRANSACTION(c2,c3,c4) GBINDER_FOURCC('_',c2,c3,c4)
#define GBINDER_PING_TRANSACTION GBINDER_TRANSACTION('P','N','G')
@@ -69,6 +74,9 @@
#define HIDL_DEBUG_TRANSACTION HIDL_FOURCC('D','B','G')
#define HIDL_HASH_CHAIN_TRANSACTION HIDL_FOURCC('H','S','H')
+/* As a special case, ServiceManager's handle is zero */
+#define GBINDER_SERVICEMANAGER_HANDLE (0)
+
#endif /* GBINDER_TYPES_PRIVATE_H */
/*
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_writer.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -32,12 +32,15 @@
#include "gbinder_writer_p.h"
#include "gbinder_buffer_p.h"
+#include "gbinder_local_object.h"
+#include "gbinder_object_converter.h"
#include "gbinder_io.h"
#include "gbinder_log.h"
#include <gutil_intarray.h>
#include <gutil_macros.h>
#include <gutil_strv.h>
+#include <gutil_misc.h>
#include <unistd.h>
#include <stdint.h>
@@ -55,52 +58,88 @@
GBINDER_INLINE_FUNC GBinderWriterData* gbinder_writer_data(GBinderWriter* pub)
{ return G_LIKELY(pub) ? gbinder_writer_cast(pub)->data : NULL; }
-static
-void
-gbinder_writer_data_buffer_cleanup(
- gpointer data)
-{
- gbinder_buffer_contents_unref((GBinderBufferContents*)data);
-}
-
void
gbinder_writer_data_set_contents(
GBinderWriterData* data,
- GBinderBuffer* buffer)
+ GBinderBuffer* buffer,
+ GBinderObjectConverter* convert)
{
- gsize bufsize;
- const guint8* bufdata = gbinder_buffer_data(buffer, &bufsize);
- const GBinderIo* io = gbinder_buffer_io(buffer);
- GBinderBufferContents* contents = gbinder_buffer_contents(buffer);
-
- GASSERT(data->io == io);
g_byte_array_set_size(data->bytes, 0);
gutil_int_array_set_count(data->offsets, 0);
data->buffers_size = 0;
gbinder_cleanup_reset(data->cleanup);
+ gbinder_writer_data_append_contents(data, buffer, 0, convert);
+}
+
+void
+gbinder_writer_data_append_contents(
+ GBinderWriterData* data,
+ GBinderBuffer* buffer,
+ gsize off,
+ GBinderObjectConverter* convert)
+{
+ GBinderBufferContents* contents = gbinder_buffer_contents(buffer);
- g_byte_array_append(data->bytes, bufdata, bufsize);
if (contents) {
+ gsize bufsize;
+ GByteArray* dest = data->bytes;
+ const guint8* bufdata = gbinder_buffer_data(buffer, &bufsize);
void** objects = gbinder_buffer_objects(buffer);
- data->cleanup = gbinder_cleanup_add(data->cleanup,
- gbinder_writer_data_buffer_cleanup,
+ data->cleanup = gbinder_cleanup_add(data->cleanup, (GDestroyNotify)
+ gbinder_buffer_contents_unref,
gbinder_buffer_contents_ref(contents));
if (objects && *objects) {
+ const GBinderIo* io = gbinder_buffer_io(buffer);
+
+ /* GBinderIo must be the same because it's defined by the kernel */
+ GASSERT(io == data->io);
if (!data->offsets) {
data->offsets = gutil_int_array_new();
}
while (*objects) {
const guint8* obj = *objects++;
- gsize offset = obj - bufdata;
- gsize objsize = io->object_data_size(obj);
+ gsize objsize, offset = obj - bufdata;
+ GBinderLocalObject* local;
+ guint32 handle;
+
+ GASSERT(offset >= off && offset < bufsize);
+ if (offset > off) {
+ /* Copy serialized data preceeding this object */
+ g_byte_array_append(dest, bufdata + off, offset - off);
+ off = offset;
+ }
+ /* Offset in the destination buffer */
+ gutil_int_array_append(data->offsets, dest->len);
+
+ /* Convert remote object into local if necessary */
+ if (convert && io->decode_binder_handle(obj, &handle) &&
+ (local = gbinder_object_converter_handle_to_local
+ (convert, handle))) {
+ const guint pos = dest->len;
+
+ g_byte_array_set_size(dest, pos +
+ GBINDER_MAX_BINDER_OBJECT_SIZE);
+ objsize = io->encode_local_object(dest->data + pos, local);
+ g_byte_array_set_size(dest, pos + objsize);
+
+ /* Keep the reference */
+ data->cleanup = gbinder_cleanup_add(data->cleanup,
+ (GDestroyNotify) gbinder_local_object_unref, local);
+ } else {
+ objsize = io->object_size(obj);
+ g_byte_array_append(dest, obj, objsize);
+ }
- GASSERT(offset > 0 && offset < bufsize);
- gutil_int_array_append(data->offsets, (int)offset);
/* Size of each buffer has to be 8-byte aligned */
- data->buffers_size += G_ALIGN8(objsize);
+ data->buffers_size += G_ALIGN8(io->object_data_size(obj));
+ off += objsize;
}
}
+ if (off < bufsize) {
+ /* Copy remaining data */
+ g_byte_array_append(dest, bufdata + off, bufsize - off);
+ }
}
}
@@ -671,7 +710,7 @@
GBinderParent vec_parent;
GBinderHidlVec* vec = g_new0(GBinderHidlVec, 1);
const gsize total = count * elemsize;
- void* buf = g_memdup(base, total);
+ void* buf = gutil_memdup(base, total);
/* Prepare parent descriptor for the string data */
vec_parent.index = gbinder_writer_data_prepare(data);
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/src/gbinder_writer_p.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -54,7 +54,16 @@
void
gbinder_writer_data_set_contents(
GBinderWriterData* data,
- GBinderBuffer* buffer)
+ GBinderBuffer* buffer,
+ GBinderObjectConverter* convert)
+ GBINDER_INTERNAL;
+
+void
+gbinder_writer_data_append_contents(
+ GBinderWriterData* data,
+ GBinderBuffer* buffer,
+ gsize data_offset,
+ GBinderObjectConverter* convert)
GBINDER_INTERNAL;
void
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/test/Makefile
^
|
@@ -2,6 +2,7 @@
all:
%:
+ @$(MAKE) -C binder-bridge $*
@$(MAKE) -C binder-client $*
@$(MAKE) -C binder-dump $*
@$(MAKE) -C binder-list $*
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/test/binder-bridge/Makefile
^
|
@@ -0,0 +1,154 @@
+# -*- Mode: makefile-gmake -*-
+
+.PHONY: all debug release clean cleaner
+.PHONY: libgbinder-release libgbinder-debug
+
+#
+# Required packages
+#
+
+PKGS = glib-2.0 gio-2.0 gio-unix-2.0 libglibutil
+
+#
+# Default target
+#
+
+all: debug release
+
+#
+# Executable
+#
+
+EXE = binder-bridge
+
+#
+# Sources
+#
+
+SRC = $(EXE).c
+
+#
+# Directories
+#
+
+SRC_DIR = .
+BUILD_DIR = build
+LIB_DIR = ../..
+DEBUG_BUILD_DIR = $(BUILD_DIR)/debug
+RELEASE_BUILD_DIR = $(BUILD_DIR)/release
+
+#
+# Tools and flags
+#
+
+CC ?= $(CROSS_COMPILE)gcc
+LD = $(CC)
+WARNINGS = -Wall
+INCLUDES = -I$(LIB_DIR)/include
+BASE_FLAGS = -fPIC
+CFLAGS = $(BASE_FLAGS) $(DEFINES) $(WARNINGS) $(INCLUDES) -MMD -MP \
+ $(shell pkg-config --cflags $(PKGS))
+LDFLAGS = $(BASE_FLAGS) $(shell pkg-config --libs $(PKGS))
+QUIET_MAKE = make --no-print-directory
+DEBUG_FLAGS = -g
+RELEASE_FLAGS =
+
+ifndef KEEP_SYMBOLS
+KEEP_SYMBOLS = 0
+endif
+
+ifneq ($(KEEP_SYMBOLS),0)
+RELEASE_FLAGS += -g
+SUBMAKE_OPTS += KEEP_SYMBOLS=1
+endif
+
+DEBUG_LDFLAGS = $(LDFLAGS) $(DEBUG_FLAGS)
+RELEASE_LDFLAGS = $(LDFLAGS) $(RELEASE_FLAGS)
+DEBUG_CFLAGS = $(CFLAGS) $(DEBUG_FLAGS) -DDEBUG
+RELEASE_CFLAGS = $(CFLAGS) $(RELEASE_FLAGS) -O2
+
+#
+# Files
+#
+
+DEBUG_OBJS = $(SRC:%.c=$(DEBUG_BUILD_DIR)/%.o)
+RELEASE_OBJS = $(SRC:%.c=$(RELEASE_BUILD_DIR)/%.o)
+DEBUG_SO_FILE := $(shell $(QUIET_MAKE) -C $(LIB_DIR) print_debug_so)
+RELEASE_SO_FILE := $(shell $(QUIET_MAKE) -C $(LIB_DIR) print_release_so)
+DEBUG_LINK_FILE := $(shell $(QUIET_MAKE) -C $(LIB_DIR) print_debug_link)
+RELEASE_LINK_FILE := $(shell $(QUIET_MAKE) -C $(LIB_DIR) print_release_link)
+DEBUG_SO = $(LIB_DIR)/$(DEBUG_SO_FILE)
+RELEASE_SO = $(LIB_DIR)/$(RELEASE_SO_FILE)
+
+#
+# Dependencies
+#
+
+DEPS = $(DEBUG_OBJS:%.o=%.d) $(RELEASE_OBJS:%.o=%.d)
+ifneq ($(MAKECMDGOALS),clean)
+ifneq ($(strip $(DEPS)),)
+-include $(DEPS)
+endif
+endif
+
+$(DEBUG_OBJS): | $(DEBUG_BUILD_DIR)
+$(RELEASE_OBJS): | $(RELEASE_BUILD_DIR)
+
+#
+# Rules
+#
+
+DEBUG_EXE = $(DEBUG_BUILD_DIR)/$(EXE)
+RELEASE_EXE = $(RELEASE_BUILD_DIR)/$(EXE)
+
+debug: libgbinder-debug $(DEBUG_EXE)
+
+release: libgbinder-release $(RELEASE_EXE)
+
+clean:
+ rm -f *~
+ rm -fr $(BUILD_DIR)
+
+cleaner: clean
+ @make -C $(LIB_DIR) clean
+
+$(DEBUG_BUILD_DIR):
+ mkdir -p $@
+
+$(RELEASE_BUILD_DIR):
+ mkdir -p $@
+
+$(DEBUG_BUILD_DIR)/%.o : $(SRC_DIR)/%.c
+ $(CC) -c $(DEBUG_CFLAGS) -MT"$@" -MF"$(@:%.o=%.d)" $< -o $@
+
+$(RELEASE_BUILD_DIR)/%.o : $(SRC_DIR)/%.c
+ $(CC) -c $(RELEASE_CFLAGS) -MT"$@" -MF"$(@:%.o=%.d)" $< -o $@
+
+$(DEBUG_EXE): $(DEBUG_SO) $(DEBUG_BUILD_DIR) $(DEBUG_OBJS)
+ $(LD) $(DEBUG_OBJS) $(DEBUG_LDFLAGS) $< -o $@
+
+$(RELEASE_EXE): $(RELEASE_SO) $(RELEASE_BUILD_DIR) $(RELEASE_OBJS)
+ $(LD) $(RELEASE_OBJS) $(RELEASE_LDFLAGS) $< -o $@
+ifeq ($(KEEP_SYMBOLS),0)
+ strip $@
+endif
+
+libgbinder-debug:
+ @make $(SUBMAKE_OPTS) -C $(LIB_DIR) $(DEBUG_SO_FILE) $(DEBUG_LINK_FILE)
+
+libgbinder-release:
+ @make $(SUBMAKE_OPTS) -C $(LIB_DIR) $(RELEASE_SO_FILE) $(RELEASE_LINK_FILE)
+
+#
+# Install
+#
+
+INSTALL = install
+
+INSTALL_BIN_DIR = $(DESTDIR)/usr/bin
+
+install: release $(INSTALL_BIN_DIR)
+ $(INSTALL) -m 755 $(RELEASE_EXE) $(INSTALL_BIN_DIR)
+
+$(INSTALL_BIN_DIR):
+ $(INSTALL) -d $@
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/test/binder-bridge/binder-bridge.c
^
|
@@ -0,0 +1,196 @@
+/*
+ * Copyright (C) 2021 Jolla Ltd.
+ * Copyright (C) 2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include <gbinder.h>
+
+#include <gutil_log.h>
+
+#include <glib-unix.h>
+
+#define RET_OK (0)
+#define RET_NODEV (1)
+#define RET_INVARG (2)
+
+typedef struct app_options {
+ const char* src;
+ const char* dest;
+ char* src_name;
+ const char* dest_name;
+ const char** ifaces;
+} AppOptions;
+
+static
+gboolean
+app_signal(
+ gpointer loop)
+{
+ GINFO("Caught signal, shutting down...");
+ g_main_loop_quit(loop);
+ return G_SOURCE_CONTINUE;
+}
+
+static
+int
+app_run(
+ const AppOptions* opt)
+{
+ int ret = RET_NODEV;
+ GBinderServiceManager* src = gbinder_servicemanager_new(opt->src);
+
+ if (src) {
+ GBinderServiceManager* dest = gbinder_servicemanager_new(opt->dest);
+
+ if (dest) {
+ GMainLoop* loop = g_main_loop_new(NULL, TRUE);
+ guint sigtrm = g_unix_signal_add(SIGTERM, app_signal, loop);
+ guint sigint = g_unix_signal_add(SIGINT, app_signal, loop);
+ GBinderBridge* bridge = gbinder_bridge_new2
+ (opt->src_name, opt->dest_name, opt->ifaces, src, dest);
+
+ g_main_loop_run(loop);
+
+ if (sigtrm) g_source_remove(sigtrm);
+ if (sigint) g_source_remove(sigint);
+ g_main_loop_unref(loop);
+ gbinder_bridge_free(bridge);
+ gbinder_servicemanager_unref(dest);
+ ret = RET_OK;
+ } else {
+ GERR("No servicemanager at %s", opt->dest);
+ }
+ gbinder_servicemanager_unref(src);
+ } else {
+ GERR("No servicemanager at %s", opt->src);
+ }
+ return ret;
+}
+
+static
+gboolean
+app_log_verbose(
+ const gchar* name,
+ const gchar* value,
+ gpointer data,
+ GError** error)
+{
+ gutil_log_default.level = GLOG_LEVEL_VERBOSE;
+ return TRUE;
+}
+
+static
+gboolean
+app_log_quiet(
+ const gchar* name,
+ const gchar* value,
+ gpointer data,
+ GError** error)
+{
+ gutil_log_default.level = GLOG_LEVEL_NONE;
+ return TRUE;
+}
+
+static
+gboolean
+app_init(
+ AppOptions* opt,
+ int argc,
+ char* argv[])
+{
+ gboolean ok = FALSE;
+ GOptionEntry entries[] = {
+ { "source", 's', 0, G_OPTION_ARG_STRING, &opt->src_name,
+ "Register a different name on source", "NAME" },
+ { "verbose", 'v', G_OPTION_FLAG_NO_ARG, G_OPTION_ARG_CALLBACK,
+ app_log_verbose, "Enable verbose output", NULL },
+ { "quiet", 'q', G_OPTION_FLAG_NO_ARG, G_OPTION_ARG_CALLBACK,
+ app_log_quiet, "Be quiet", NULL },
+ { NULL }
+ };
+
+ GError* error = NULL;
+ GOptionContext* options = g_option_context_new("SRC DST NAME IFACES...");
+
+ gutil_log_default.level = GLOG_LEVEL_DEFAULT;
+
+ g_option_context_add_main_entries(options, entries, NULL);
+ g_option_context_set_summary(options,
+ "Forwards calls from device SRC to device DST.");
+
+ if (g_option_context_parse(options, &argc, &argv, &error)) {
+ if (argc >= 5) {
+ int i;
+ const int first_iface = 4;
+
+ opt->src = argv[1];
+ opt->dest = argv[2];
+ opt->dest_name = argv[3];
+ opt->ifaces = g_new(const char*, argc - first_iface + 1);
+ for (i = first_iface; i < argc; i++) {
+ opt->ifaces[i - first_iface] = argv[i];
+ }
+ opt->ifaces[i - first_iface] = NULL;
+ ok = TRUE;
+ } else {
+ char* help = g_option_context_get_help(options, TRUE, NULL);
+
+ fprintf(stderr, "%s", help);
+ g_free(help);
+ }
+ } else {
+ GERR("%s", error->message);
+ g_error_free(error);
+ }
+ g_option_context_free(options);
+ return ok;
+}
+
+int main(int argc, char* argv[])
+{
+ AppOptions opt;
+ int ret = RET_INVARG;
+
+ memset(&opt, 0, sizeof(opt));
+ if (app_init(&opt, argc, argv)) {
+ ret = app_run(&opt);
+ }
+ g_free(opt.src_name);
+ g_free(opt.ifaces);
+ return ret;
+}
+
+/*
+ * Local Variables:
+ * mode: C
+ * c-basic-offset: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/Makefile
^
|
@@ -2,9 +2,11 @@
all:
%:
+ @$(MAKE) -C unit_bridge $*
@$(MAKE) -C unit_buffer $*
@$(MAKE) -C unit_cleanup $*
@$(MAKE) -C unit_client $*
+ @$(MAKE) -C unit_config $*
@$(MAKE) -C unit_driver $*
@$(MAKE) -C unit_eventloop $*
@$(MAKE) -C unit_ipc $*
@@ -13,11 +15,15 @@
@$(MAKE) -C unit_local_request $*
@$(MAKE) -C unit_log $*
@$(MAKE) -C unit_protocol $*
+ @$(MAKE) -C unit_proxy_object $*
@$(MAKE) -C unit_reader $*
@$(MAKE) -C unit_remote_object $*
@$(MAKE) -C unit_remote_reply $*
@$(MAKE) -C unit_remote_request $*
@$(MAKE) -C unit_servicemanager $*
+ @$(MAKE) -C unit_servicemanager_aidl $*
+ @$(MAKE) -C unit_servicemanager_aidl2 $*
+ @$(MAKE) -C unit_servicemanager_hidl $*
@$(MAKE) -C unit_servicename $*
@$(MAKE) -C unit_servicepoll $*
@$(MAKE) -C unit_writer $*
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/common/Makefile
^
|
@@ -44,7 +44,7 @@
CC ?= $(CROSS_COMPILE)gcc
LD = $(CC)
-WARNINGS += -Wall
+WARNINGS += -Wall -Wno-deprecated-declarations
INCLUDES += -I$(COMMON_DIR) -I$(LIB_DIR)/src -I$(LIB_DIR)/include
BASE_FLAGS = -fPIC
BASE_LDFLAGS = $(BASE_FLAGS) $(LDFLAGS)
@@ -52,7 +52,7 @@
FULL_CFLAGS = $(BASE_CFLAGS) $(DEFINES) $(WARNINGS) $(INCLUDES) -MMD -MP \
$(shell pkg-config --cflags $(PKGS))
FULL_LDFLAGS = $(BASE_LDFLAGS)
-LIBS = $(shell pkg-config --libs $(PKGS))
+LIBS = $(shell pkg-config --libs $(PKGS)) -lpthread
QUIET_MAKE = make --no-print-directory
DEBUG_FLAGS = -g
RELEASE_FLAGS =
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/common/test_binder.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -30,36 +30,66 @@
* THE POSSIBILITY OF SUCH DAMAGE.
*/
+#include "test_binder.h"
+#include "gbinder_local_object_p.h"
#include "gbinder_system.h"
#define GLOG_MODULE_NAME test_binder_log
#include <gutil_log.h>
GLOG_MODULE_DEFINE2("test_binder", gutil_log_default);
+#include <glib-object.h>
+
#include <unistd.h>
#include <fcntl.h>
#include <errno.h>
#include <sys/ioctl.h>
#include <sys/socket.h>
#include <sys/types.h>
+#include <sys/syscall.h>
+
+#define gettid() ((int)syscall(SYS_gettid))
static GHashTable* test_fd_map = NULL;
static GHashTable* test_node_map = NULL;
-static GPrivate test_looper;
+static GPrivate test_looper = G_PRIVATE_INIT(NULL);
+static GPrivate test_tx_state = G_PRIVATE_INIT(NULL);
+
+G_LOCK_DEFINE_STATIC(test_binder);
+static GMainLoop* test_binder_exit_loop = NULL;
-#define public_fd fd[0]
-#define private_fd fd[1]
+#define PUBLIC (0)
+#define PRIVATE (1)
+#define public_fd node[PUBLIC].fd
+#define private_fd node[PRIVATE].fd
#define BINDER_VERSION _IOWR('b', 9, gint32)
#define BINDER_SET_MAX_THREADS _IOW('b', 5, guint32)
+#define BINDER_BUFFER_FLAG_HAS_PARENT 0x01
+
+#define B_TYPE_LARGE 0x85
+#define BINDER_TYPE_BINDER GBINDER_FOURCC('s', 'b', '*', B_TYPE_LARGE)
+#define BINDER_TYPE_HANDLE GBINDER_FOURCC('s', 'h', '*', B_TYPE_LARGE)
+#define BINDER_TYPE_PTR GBINDER_FOURCC('p', 't', '*', B_TYPE_LARGE)
#define TF_ONE_WAY 0x01
#define TF_ROOT_OBJECT 0x04
#define TF_STATUS_CODE 0x08
#define TF_ACCEPT_FDS 0x10
+#define READ_FLAG_TX_COMPLETION (0x01)
+#define READ_FLAG_TX_INCOMING (0x02)
+#define READ_FLAG_TX_REPLY (0x04)
+#define READ_FLAG_TX_ERROR (0x08)
+#define READ_FLAG_TX_OTHER (0x10)
+#define READ_FLAGS_ALL (\
+ READ_FLAG_TX_COMPLETION | \
+ READ_FLAG_TX_INCOMING | \
+ READ_FLAG_TX_REPLY | \
+ READ_FLAG_TX_ERROR | \
+ READ_FLAG_TX_OTHER)
+
typedef struct test_binder_io TestBinderIo;
-typedef struct test_binder TestBinder;
typedef
void
@@ -76,24 +106,55 @@
TestBinder* binder;
} TestBinderSubmitThread;
-typedef struct test_binder_node {
+typedef enum test_tx_state {
+ TEST_TX_STATE_NONE,
+ TEST_TX_STATE_ONEWAY,
+ TEST_TX_STATE_ACTIVE,
+ TEST_TX_STATE_REPLY
+} TEST_TX_STATE;
+
+/* TestBinderTxState has to be stacked to support nested transactions */
+typedef struct test_binder_tx_state {
+ int tid;
+ int depth;
+ TEST_TX_STATE* stack;
+} TestBinderTxState;
+
+typedef struct test_binder_node TestBinderNode;
+struct test_binder_node {
+ int fd;
char* path;
- int refcount;
- const TestBinderIo* io;
+ TestBinder* binder;
+ TestBinderNode* other;
+ TEST_LOOPER looper_enabled;
+ TestBinderTxState* tx_state;
+ gint looper_count;
+ GMutex mutex; /* Protects reads and next_cmd */
+ guint32* next_cmd;
+};
+
+typedef struct test_binder_fd {
+ int fd;
GHashTable* destroy_map;
-} TestBinderNode;
+ TestBinderNode* node;
+} TestBinderFd;
typedef struct test_binder {
- TestBinderNode* node;
+ gint refcount;
+ const TestBinderIo* io;
+ GHashTable* object_map; /* GBinderLocalObject* => handle */
+ GHashTable* handle_map; /* handle => GBinderLocalObject* */
TestBinderSubmitThread* submit_thread;
- gboolean looper_enabled;
- int fd[2];
+ guint32 last_auto_handle;
+ GMutex mutex;
+ gboolean passthrough;
+ TestBinderNode node[2];
} TestBinder;
struct test_binder_io {
int version;
int write_read_request;
- int (*handle_write_read)(TestBinder* binder, void* data);
+ int (*handle_write_read)(TestBinderFd* fd, void* data);
};
typedef struct binder_write_read_64 {
@@ -118,16 +179,37 @@
guint64 data_offsets;
} BinderTransactionData64;
+typedef struct binder_transaction_data_sg_64 {
+ BinderTransactionData64 tx;
+ guint64 buffers_size;
+} BinderTransactionDataSg64;
+
typedef struct binder_pre_cookie_64 {
guint64 ptr;
guint64 cookie;
} BinderPtrCookie64;
typedef struct binder_handle_cookie_64 {
- guint32 handle;
- guint64 cookie;
+ guint32 handle;
+ guint64 cookie;
} __attribute__((packed)) BinderHandleCookie64;
+typedef struct binder_object_64 {
+ guint32 type; /* BINDER_TYPE_BINDER */
+ guint32 flags;
+ guint64 object;
+ guint64 cookie;
+} BinderObject64;
+
+typedef struct binder_buffer_64 {
+ guint32 type; /* BINDER_TYPE_PTR */
+ guint32 flags;
+ guint64 buffer;
+ guint64 length;
+ guint64 parent;
+ guint64 parent_offset;
+} BinderBuffer64;
+
#define BC_TRANSACTION_64 _IOW('c', 0, BinderTransactionData64)
#define BC_REPLY_64 _IOW('c', 1, BinderTransactionData64)
#define BC_FREE_BUFFER_64 _IOW('c', 3, guint64)
@@ -139,6 +221,9 @@
#define BC_EXIT_LOOPER _IO('c', 13)
#define BC_REQUEST_DEATH_NOTIFICATION_64 _IOW('c', 14, BinderHandleCookie64)
#define BC_CLEAR_DEATH_NOTIFICATION_64 _IOW('c', 15, BinderHandleCookie64)
+#define BC_DEAD_BINDER_DONE _IOW('c', 16, guint64)
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/common/test_binder.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -35,6 +35,8 @@
#include "test_common.h"
+typedef struct test_binder TestBinder;
+
void
test_binder_br_noop(
int fd);
@@ -111,10 +113,44 @@
int fd,
gint32 status);
+typedef enum test_looper {
+ TEST_LOOPER_DISABLE,
+ TEST_LOOPER_ENABLE,
+ TEST_LOOPER_ENABLE_ONE
+} TEST_LOOPER;
+
void
test_binder_set_looper_enabled(
int fd,
- gboolean enabled);
+ TEST_LOOPER value);
+
+void
+test_binder_set_passthrough(
+ int fd,
+ gboolean passthrough);
+
+int
+test_binder_handle(
+ int fd,
+ GBinderLocalObject* obj);
+
+GBinderLocalObject*
+test_binder_object(
+ int fd,
+ guint handle)
+ G_GNUC_WARN_UNUSED_RESULT; /* Need to unref */
+
+guint
+test_binder_register_object(
+ int fd,
+ GBinderLocalObject* obj,
+ guint handle);
+
+#define AUTO_HANDLE ((guint)-1)
+
+void
+test_binder_unregister_objects(
+ int fd);
void
test_binder_set_destroy(
@@ -122,6 +158,11 @@
gpointer ptr,
GDestroyNotify destroy);
+void
+test_binder_exit_wait(
+ const TestOpt* opt,
+ GMainLoop* loop);
+
#endif /* TEST_BINDER_H */
/*
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/common/test_common.h
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018 Jolla Ltd.
- * Contact: Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -13,9 +13,9 @@
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
- * 3. Neither the name of Jolla Ltd nor the names of its contributors may
- * be used to endorse or promote products derived from this software
- * without specific prior written permission.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -58,6 +58,23 @@
test_quit_later(
GMainLoop* loop);
+/* Quits the event loop after n iterations */
+void
+test_quit_later_n(
+ GMainLoop* loop,
+ guint n);
+
+/*
+ * Makes sure that we own the context for the entire duration of the test.
+ * That prevents many race conditions - all callbacks that are supposed to
+ * be invoked on the main thread, are actually invoked on the main thread
+ * (rather than a random worker thread which happens to acquire the context).
+ */
+void
+test_run_in_context(
+ const TestOpt* opt,
+ GTestFunc func);
+
#define TEST_TIMEOUT_SEC (20)
/* Helper macros */
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/common/test_main.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018 Jolla Ltd.
- * Contact: Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2020 Jolla Ltd.
+ * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -13,9 +13,9 @@
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
- * 3. Neither the name of Jolla Ltd nor the names of its contributors may
- * be used to endorse or promote products derived from this software
- * without specific prior written permission.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -34,6 +34,16 @@
#include <gutil_log.h>
+typedef struct test_quit_later_data{
+ GMainLoop* loop;
+ guint n;
+} TestQuitLaterData;
+
+typedef struct test_context_data{
+ GMainLoop* loop;
+ GTestFunc func;
+} TestContextData;
+
static
gboolean
test_timeout_expired(
@@ -44,6 +54,46 @@
}
static
+void
+test_quit_later_n_free(
+ gpointer user_data)
+{
+ TestQuitLaterData* data = user_data;
+
+ g_main_loop_unref(data->loop);
+ g_free(data);
+}
+
+static
+gboolean
+test_quit_later_n_func(
+ gpointer user_data)
+{
+ TestQuitLaterData* data = user_data;
+
+ if (data->n > 0) {
+ data->n--;
+ return G_SOURCE_CONTINUE;
+ } else {
+ g_main_loop_quit(data->loop);
+ return G_SOURCE_REMOVE;
+ }
+}
+
+void
+test_quit_later_n(
+ GMainLoop* loop,
+ guint n)
+{
+ TestQuitLaterData* data = g_new0(TestQuitLaterData, 1);
+
+ data->loop = g_main_loop_ref(loop);
+ data->n = n;
+ g_idle_add_full(G_PRIORITY_DEFAULT_IDLE, test_quit_later_n_func, data,
+ test_quit_later_n_free);
+}
+
+static
gboolean
test_quit_later_cb(
gpointer data)
@@ -59,6 +109,40 @@
g_idle_add(test_quit_later_cb, loop);
}
+static
+gboolean
+test_run_in_context_cb(
+ gpointer data)
+{
+ TestContextData* test = data;
+
+ test->func();
+ g_main_loop_quit(test->loop);
+ return G_SOURCE_REMOVE;
+}
+
+void
+test_run_in_context(
+ const TestOpt* opt,
+ GTestFunc func)
+{
+ TestContextData test;
+
+ test.loop = g_main_loop_new(NULL, FALSE);
+ test.func = func;
+
+ /*
+ * This makes sure that we own the context for the entire duration
+ * of the test. That prevents many race conditions - all callbacks
+ * that are supposed to be invoked on the main thread, are actually
+ * invoked on the main thread (rather than a random worker thread
+ * which happens to acquire the context).
+ */
+ g_idle_add(test_run_in_context_cb, &test);
+ test_run(opt, test.loop);
+ g_main_loop_unref(test.loop);
+}
+
void
test_run(
const TestOpt* opt,
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/common/test_servicemanager_hidl.c
^
|
@@ -0,0 +1,567 @@
+/*
+ * Copyright (C) 2021 Jolla Ltd.
+ * Copyright (C) 2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "test_servicemanager_hidl.h"
+
+#include "gbinder_local_object_p.h"
+#include "gbinder_local_reply.h"
+#include "gbinder_local_request.h"
+#include "gbinder_remote_request.h"
+#include "gbinder_remote_reply.h"
+#include "gbinder_remote_object.h"
+#include "gbinder_reader.h"
+#include "gbinder_writer.h"
+#include "gbinder_client.h"
+#include "gbinder_ipc.h"
+
+#include <gutil_log.h>
+#include <gutil_strv.h>
+
+/*==========================================================================*
+ * Test service manager
+ *==========================================================================*/
+
+#define BASE_IFACE "android.hidl.base@1.0::IBase"
+#define MANAGER_IFACE "android.hidl.manager@1.0::IServiceManager"
+#define NOTIFICATION_IFACE "android.hidl.manager@1.0::IServiceNotification"
+
+const char* const servicemanager_hidl_ifaces[] = { MANAGER_IFACE, NULL };
+
+enum servicemanager_hidl_tx {
+ GET_TRANSACTION = GBINDER_FIRST_CALL_TRANSACTION,
+ ADD_TRANSACTION,
+ GET_TRANSPORT_TRANSACTION,
+ LIST_TRANSACTION,
+ LIST_BY_INTERFACE_TRANSACTION,
+ REGISTER_FOR_NOTIFICATIONS_TRANSACTION,
+ DEBUG_DUMP_TRANSACTION,
+ REGISTER_PASSTHROUGH_CLIENT_TRANSACTION
+};
+
+enum servicemanager_hidl_notify_tx {
+ ON_REGISTRATION_TRANSACTION = GBINDER_FIRST_CALL_TRANSACTION
+};
+
+typedef GBinderLocalObjectClass TestServiceManagerHidlClass;
+struct test_servicemanager_hidl {
+ GBinderLocalObject parent;
+ GHashTable* objects;
+ GPtrArray* watchers;
+ GMutex mutex;
+};
+
+typedef struct test_servicemanager_hidl_add {
+ TestServiceManagerHidl* manager;
+ GBinderRemoteObject* object;
+ char* instance;
+} TestServiceManagerHidlAdd;
+
+struct test_servicemanager_hidl_watcher {
+ GBinderClient* client;
+ char* iface;
+ char* name;
+} TestServiceManagerHidlWatcher;
+
+#define THIS_TYPE test_servicemanager_hidl_get_type()
+#define PARENT_CLASS test_servicemanager_hidl_parent_class
+#define THIS(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), THIS_TYPE, \
+ TestServiceManagerHidl))
+G_DEFINE_TYPE(TestServiceManagerHidl, test_servicemanager_hidl, \
+ GBINDER_TYPE_LOCAL_OBJECT)
+
+static
+void
+test_servicemanager_hidl_notify(
+ TestServiceManagerHidl* self,
+ GBinderClient* watcher,
+ const char* iface,
+ const char* instance,
+ gboolean preexisting)
+{
+ GBinderLocalRequest* notify = gbinder_client_new_request(watcher);
+ GBinderWriter writer;
+ char* iface2 = g_strdup(iface);
+ char* instance2 = g_strdup(instance);
+
+ gbinder_local_request_init_writer(notify, &writer);
+ gbinder_writer_append_hidl_string(&writer, iface2);
+ gbinder_writer_append_hidl_string(&writer, instance2);
+ gbinder_writer_append_bool(&writer, preexisting);
+
+ gbinder_writer_add_cleanup(&writer, g_free, iface2);
+ gbinder_writer_add_cleanup(&writer, g_free, instance2);
+
+ gbinder_client_transact(watcher, ON_REGISTRATION_TRANSACTION,
+ GBINDER_TX_FLAG_ONEWAY, notify, NULL, NULL, NULL);
+ gbinder_local_request_unref(notify);
+}
+
+static
+void
+test_servicemanager_hidl_notify_all(
+ TestServiceManagerHidl* self,
+ const char* iface,
+ const char* instance,
+ gboolean preexisting)
+{
+ GPtrArray* watchers = self->watchers;
+ guint i;
+
+ /* For unit test purposes, just always notify all watchers */
+ for (i = 0; i < watchers->len; i++) {
+ test_servicemanager_hidl_notify(self, watchers->pdata[i],
+ iface, instance, preexisting);
+ }
+}
+
+static
+void
+test_servicemanager_hidl_add_complete2(
+ GBinderClient* client,
+ GBinderRemoteReply* reply,
+ int status,
+ void* user_data)
+{
+ TestServiceManagerHidlAdd* add = user_data;
+ TestServiceManagerHidl* self = add->manager;
+ const char* instance = add->instance;
+
+ g_mutex_lock(&self->mutex);
+ /* Remove the temporary entry */
+ GDEBUG("Dropping '%s'", instance);
+ g_hash_table_remove(self->objects, instance);
+ if (reply) {
+ GBinderReader reader;
+ gint32 status;
+
+ gbinder_remote_reply_init_reader(reply, &reader);
+ if (gbinder_reader_read_int32(&reader, &status) && status == 0) {
+ char** ifaces = gbinder_reader_read_hidl_string_vec(&reader);
+
+ if (ifaces) {
+ char** ptr = ifaces;
+
+ while (*ptr) {
+ const char* iface = *ptr++;
+ char* fqinstance = g_strconcat(iface, "/", instance, NULL);
+
+ /* Add permanent entries */
+ GDEBUG("Adding '%s'", fqinstance);
+ g_hash_table_replace(self->objects, fqinstance,
+ gbinder_remote_object_ref(add->object));
+ test_servicemanager_hidl_notify_all(self, iface,
+ instance, FALSE);
+ }
+ g_strfreev(ifaces);
+ }
+ }
+ }
+ g_mutex_unlock(&self->mutex);
+}
+
+static
+void
+test_servicemanager_hidl_add_done(
+ gpointer data)
+{
+ TestServiceManagerHidlAdd* add = data;
+
+ gbinder_remote_object_unref(add->object);
+ g_object_unref(add->manager);
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/common/test_servicemanager_hidl.h
^
|
@@ -0,0 +1,69 @@
+/*
+ * Copyright (C) 2021 Jolla Ltd.
+ * Copyright (C) 2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef TEST_SERVICEMANAGER_HIDL_H
+#define TEST_SERVICEMANAGER_HIDL_H
+
+#include <gbinder_types.h>
+
+typedef struct test_servicemanager_hidl TestServiceManagerHidl;
+
+TestServiceManagerHidl*
+test_servicemanager_hidl_new(
+ GBinderIpc* ipc);
+
+void
+test_servicemanager_hidl_free(
+ TestServiceManagerHidl* sm);
+
+GBinderIpc*
+test_servicemanager_hidl_ipc(
+ TestServiceManagerHidl* self);
+
+guint
+test_servicemanager_hidl_object_count(
+ TestServiceManagerHidl* self);
+
+GBinderRemoteObject*
+test_servicemanager_hidl_lookup(
+ TestServiceManagerHidl* self,
+ const char* name);
+
+#endif /* TEST_SERVICEMANAGER_HIDL_H */
+
+/*
+ * Local Variables:
+ * mode: C
+ * c-basic-offset: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/coverage/run
^
|
@@ -4,9 +4,11 @@
#
TESTS="\
+unit_bridge \
unit_buffer \
unit_cleanup \
unit_client \
+unit_config \
unit_driver \
unit_eventloop \
unit_ipc \
@@ -15,11 +17,15 @@
unit_local_request \
unit_log \
unit_protocol \
+unit_proxy_object \
unit_reader \
unit_remote_object \
unit_remote_reply \
unit_remote_request \
unit_servicemanager \
+unit_servicemanager_aidl \
+unit_servicemanager_aidl2 \
+unit_servicemanager_hidl \
unit_servicename \
unit_servicepoll \
unit_writer"
@@ -58,9 +64,13 @@
popd
done
+# Sometimes you need this, sometimes that :S
+BASE_DIR="$TOP_DIR"
+#BASE_DIR="$TOP_DIR/src"
+
FULL_COV="$COV_DIR/full.gcov"
LIB_COV="$COV_DIR/lib.gcov"
rm -f "$FULL_COV" "$LIB_COV"
-lcov $LCOV_OPT -c -d "$TOP_DIR/build/coverage" -b "$TOP_DIR/src" -o "$FULL_COV" || exit 1
-lcov $LCOV_OPT -e "$FULL_COV" "$TOP_DIR/src/*" -o "$LIB_COV" || exit 1
+lcov $LCOV_OPT -c -d "$TOP_DIR/build/coverage" -b "$BASE_DIR" -o "$FULL_COV" || exit 1
+lcov $LCOV_OPT -e "$FULL_COV" "$BASE_DIR/*" -o "$LIB_COV" || exit 1
genhtml $GENHTML_OPT "$LIB_COV" -t "libgbinder" --output-directory "$COV_DIR/report" || exit 1
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_bridge/Makefile
^
|
@@ -0,0 +1,6 @@
+# -*- Mode: makefile-gmake -*-
+
+EXE = unit_bridge
+COMMON_SRC = test_binder.c test_main.c test_servicemanager_hidl.c
+
+include ../common/Makefile
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_bridge/unit_bridge.c
^
|
@@ -0,0 +1,498 @@
+/*
+ * Copyright (C) 2021 Jolla Ltd.
+ * Copyright (C) 2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "test_binder.h"
+#include "test_servicemanager_hidl.h"
+
+#include "gbinder_ipc.h"
+#include "gbinder_client.h"
+#include "gbinder_config.h"
+#include "gbinder_driver.h"
+#include "gbinder_bridge.h"
+#include "gbinder_reader.h"
+#include "gbinder_local_reply.h"
+#include "gbinder_local_request.h"
+#include "gbinder_proxy_object.h"
+#include "gbinder_remote_object_p.h"
+#include "gbinder_remote_reply.h"
+#include "gbinder_remote_request.h"
+#include "gbinder_servicemanager_p.h"
+
+#include <gutil_log.h>
+
+static TestOpt test_opt;
+
+#define SRC_DEV "/dev/srcbinder"
+#define SRC_PRIV_DEV SRC_DEV "-private"
+#define DEST_DEV "/dev/dstbinder"
+#define DEST_PRIV_DEV DEST_DEV "-private"
+#define TEST_IFACE "gbinder@1.0::ITest"
+
+#define TX_CODE GBINDER_FIRST_CALL_TRANSACTION
+#define TX_PARAM 0x11111111
+#define TX_RESULT 0x22222222
+
+static const char TMP_DIR_TEMPLATE[] = "gbinder-test-bridge-XXXXXX";
+static const char* TEST_IFACES[] = { TEST_IFACE, NULL };
+static const char DEFAULT_CONFIG_DATA[] =
+ "[Protocol]\n"
+ "Default = hidl\n"
+ "[ServiceManager]\n"
+ "Default = hidl\n";
+
+typedef struct test_config {
+ char* dir;
+ char* file;
+} TestConfig;
+
+/*==========================================================================*
+ * Test object (registered with two GBinderIpc's)
+ *==========================================================================*/
+
+typedef GBinderLocalObjectClass TestLocalObjectClass;
+typedef struct test_local_object {
+ GBinderLocalObject parent;
+ GBinderIpc* ipc2;
+} TestLocalObject;
+G_DEFINE_TYPE(TestLocalObject, test_local_object, GBINDER_TYPE_LOCAL_OBJECT)
+#define TEST_TYPE_LOCAL_OBJECT test_local_object_get_type()
+#define TEST_LOCAL_OBJECT(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), \
+ TEST_TYPE_LOCAL_OBJECT, TestLocalObject))
+
+TestLocalObject*
+test_local_object_new(
+ GBinderIpc* ipc,
+ GBinderIpc* ipc2,
+ const char* const* ifaces,
+ GBinderLocalTransactFunc txproc,
+ void* user_data)
+{
+ TestLocalObject* self = TEST_LOCAL_OBJECT
+ (gbinder_local_object_new_with_type(TEST_TYPE_LOCAL_OBJECT,
+ ipc, ifaces, txproc, user_data));
+
+ self->ipc2 = gbinder_ipc_ref(ipc2);
+ gbinder_ipc_register_local_object(ipc2, &self->parent);
+ return self;
+}
+
+static
+void
+test_local_object_dispose(
+ GObject* object)
+{
+ TestLocalObject* self = TEST_LOCAL_OBJECT(object);
+
+ gbinder_ipc_local_object_disposed(self->ipc2, &self->parent);
+ G_OBJECT_CLASS(test_local_object_parent_class)->dispose(object);
+}
+
+static
+void
+test_local_object_finalize(
+ GObject* object)
+{
+ gbinder_ipc_unref(TEST_LOCAL_OBJECT(object)->ipc2);
+ G_OBJECT_CLASS(test_local_object_parent_class)->finalize(object);
+}
+
+static
+void
+test_local_object_init(
+ TestLocalObject* self)
+{
+}
+
+static
+void
+test_local_object_class_init(
+ TestLocalObjectClass* klass)
+{
+ GObjectClass* object_class = G_OBJECT_CLASS(klass);
+
+ object_class->dispose = test_local_object_dispose;
+ object_class->finalize = test_local_object_finalize;
+}
+
+/*==========================================================================*
+ * Common
+ *==========================================================================*/
+
+static
+void
+test_config_init(
+ TestConfig* config,
+ char* config_data)
+{
+ config->dir = g_dir_make_tmp(TMP_DIR_TEMPLATE, NULL);
+ config->file = g_build_filename(config->dir, "test.conf", NULL);
+ g_assert(g_file_set_contents(config->file, config_data ? config_data :
+ DEFAULT_CONFIG_DATA, -1, NULL));
+
+ gbinder_config_exit();
+ gbinder_config_dir = config->dir;
+ gbinder_config_file = config->file;
+ GDEBUG("Wrote config to %s", config->file);
+}
+
+static
+void
+test_config_deinit(
+ TestConfig* config)
+{
+ gbinder_config_exit();
+
+ remove(config->file);
+ g_free(config->file);
+
+ remove(config->dir);
+ g_free(config->dir);
+}
+
+static
+TestServiceManagerHidl*
+test_servicemanager_impl_new(
+ const char* dev)
+{
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
+ const int fd = gbinder_driver_fd(ipc->driver);
+ TestServiceManagerHidl* sm = test_servicemanager_hidl_new(ipc);
+
+ test_binder_set_looper_enabled(fd, TRUE);
+ test_binder_register_object(fd, GBINDER_LOCAL_OBJECT(sm),
+ GBINDER_SERVICEMANAGER_HANDLE);
+ gbinder_ipc_unref(ipc);
+ return sm;
+}
+
+/*==========================================================================*
+ * null
+ *==========================================================================*/
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_buffer/unit_buffer.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018 Jolla Ltd.
- * Copyright (C) 2018 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -68,16 +68,48 @@
gbinder_buffer_free(buf2);
gbinder_buffer_free(NULL);
+ gbinder_buffer_contents_list_free(NULL);
g_assert(!gbinder_buffer_driver(NULL));
g_assert(!gbinder_buffer_objects(NULL));
g_assert(!gbinder_buffer_io(NULL));
g_assert(!gbinder_buffer_data(NULL, NULL));
g_assert(!gbinder_buffer_data(NULL, &size));
+ g_assert(!gbinder_buffer_contents(NULL));
+ g_assert(!gbinder_buffer_contents_list_add(NULL, NULL));
+ g_assert(!gbinder_buffer_contents_list_dup(NULL));
g_assert(!size);
gbinder_driver_unref(driver);
}
/*==========================================================================*
+ * list
+ *==========================================================================*/
+
+static
+void
+test_list(
+ void)
+{
+ static const guint8 data[] = { 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07 };
+ void* ptr = g_memdup(data, sizeof(data));
+ GBinderDriver* driver = gbinder_driver_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderBuffer* buf = gbinder_buffer_new(driver, ptr, sizeof(data), NULL);
+ GBinderBufferContents* contents = gbinder_buffer_contents(buf);
+ GBinderBufferContentsList* list = gbinder_buffer_contents_list_add
+ (NULL, contents);
+ GBinderBufferContentsList* list2 = gbinder_buffer_contents_list_dup(list);
+
+ g_assert(contents);
+ g_assert(list);
+ g_assert(list2);
+
+ gbinder_buffer_free(buf);
+ gbinder_buffer_contents_list_free(list);
+ gbinder_buffer_contents_list_free(list2);
+ gbinder_driver_unref(driver);
+}
+
+/*==========================================================================*
* parent
*==========================================================================*/
@@ -112,12 +144,14 @@
*==========================================================================*/
#define TEST_PREFIX "/buffer/"
+#define TEST_(t) TEST_PREFIX t
int main(int argc, char* argv[])
{
g_test_init(&argc, &argv, NULL);
- g_test_add_func(TEST_PREFIX "null", test_null);
- g_test_add_func(TEST_PREFIX "parent", test_parent);
+ g_test_add_func(TEST_("null"), test_null);
+ g_test_add_func(TEST_("list"), test_list);
+ g_test_add_func(TEST_("parent"), test_parent);
test_init(&test_opt, argc, argv);
return g_test_run();
}
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_client/unit_client.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -51,12 +51,12 @@
static
GBinderClient*
test_client_new(
- guint handle,
+ guint h,
const char* iface)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
- GBinderRemoteObject* obj = gbinder_object_registry_get_remote(reg, handle);
+ GBinderRemoteObject* obj = gbinder_object_registry_get_remote(reg, h, TRUE);
GBinderClient* client = gbinder_client_new(obj, iface);
g_assert(client);
@@ -97,9 +97,9 @@
test_basic(
void)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
- GBinderRemoteObject* obj = gbinder_object_registry_get_remote(reg, 0);
+ GBinderRemoteObject* obj = gbinder_object_registry_get_remote(reg, 0, TRUE);
const char* iface = "foo";
GBinderClient* client = gbinder_client_new(obj, iface);
@@ -123,9 +123,9 @@
test_interfaces(
void)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
- GBinderRemoteObject* obj = gbinder_object_registry_get_remote(reg, 0);
+ GBinderRemoteObject* obj = gbinder_object_registry_get_remote(reg, 0, TRUE);
static const GBinderClientIfaceInfo ifaces[] = {
{"33", 33 }, { "11", 11 }, { "22", 22 }
};
@@ -139,6 +139,11 @@
g_assert_cmpstr(gbinder_client_interface2(client, 33), == ,"33");
g_assert(!gbinder_client_interface2(client, 34));
g_assert(!gbinder_client_new_request2(client, 34));
+ /* Those fail to allocate default request for out-of-range codes: */
+ g_assert(!gbinder_client_transact_sync_reply(client, 34, NULL, NULL));
+ g_assert_cmpint(gbinder_client_transact_sync_oneway(client, 34, NULL),
+ == ,-EINVAL);
+ g_assert(!gbinder_client_transact(client, 34, 0, NULL, NULL, NULL, NULL));
gbinder_client_unref(client);
/* Client with no interface info */
@@ -198,7 +203,7 @@
gbinder_remote_object_add_death_handler(obj, test_dead_done, loop);
test_binder_br_dead_binder(fd, handle);
- test_binder_set_looper_enabled(fd, TRUE);
+ test_binder_set_looper_enabled(fd, TEST_LOOPER_ENABLE);
test_run(&test_opt, loop);
g_assert(gbinder_remote_object_is_dead(obj));
@@ -207,6 +212,8 @@
g_assert(!gbinder_client_transact(client, 0, 0, NULL, NULL, NULL, NULL));
gbinder_client_unref(client);
+ gbinder_ipc_exit();
+ test_binder_exit_wait(&test_opt, loop);
g_main_loop_unref(loop);
}
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_config/Makefile
^
|
@@ -0,0 +1,5 @@
+# -*- Mode: makefile-gmake -*-
+
+EXE = unit_config
+
+include ../common/Makefile
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_config/unit_config.c
^
|
@@ -0,0 +1,505 @@
+/*
+ * Copyright (C) 2020 Jolla Ltd.
+ * Copyright (C) 2020 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "test_common.h"
+
+#include "gbinder_config.h"
+
+#include <gutil_strv.h>
+#include <gutil_log.h>
+
+#include <sys/stat.h>
+#include <sys/types.h>
+
+static TestOpt test_opt;
+static const char TMP_DIR_TEMPLATE[] = "gbinder-test-config-XXXXXX";
+
+static
+const char*
+test_value(
+ GKeyFile* keyfile,
+ const char* group,
+ const char* key,
+ GString* buf)
+{
+ char* value = g_key_file_get_value(keyfile, group, key, NULL);
+
+ g_string_set_size(buf, 0);
+ if (value) {
+ g_string_append(buf, value);
+ g_free(value);
+ return buf->str;
+ } else {
+ return NULL;
+ }
+}
+
+static
+gboolean
+test_keyfiles_equal(
+ GKeyFile* keyfile1,
+ GKeyFile* keyfile2)
+{
+ gboolean equal = FALSE;
+ gsize ngroups;
+ char** groups = g_key_file_get_groups(keyfile1, &ngroups);
+ char** groups2 = g_key_file_get_groups(keyfile2, NULL);
+
+ gutil_strv_sort(groups, TRUE);
+ gutil_strv_sort(groups2, TRUE);
+ if (gutil_strv_equal(groups, groups2)) {
+ gsize i;
+
+ equal = TRUE;
+ for (i = 0; i < ngroups && equal; i++) {
+ const char* group = groups[i];
+ gsize nkeys;
+ char** keys = g_key_file_get_keys(keyfile1, group, &nkeys, NULL);
+ char** keys2 = g_key_file_get_keys(keyfile2, group, &nkeys, NULL);
+
+ equal = FALSE;
+ gutil_strv_sort(keys, TRUE);
+ gutil_strv_sort(keys2, TRUE);
+ if (gutil_strv_equal(keys, keys2)) {
+ gsize k;
+
+ equal = TRUE;
+ for (k = 0; k < nkeys && equal; k++) {
+ const char* key = keys[k];
+ char* v1 = g_key_file_get_value(keyfile1, group, key, NULL);
+ char* v2 = g_key_file_get_value(keyfile2, group, key, NULL);
+
+ if (g_strcmp0(v1, v2)) {
+ equal = FALSE;
+ GDEBUG("Values for %s/%s don't match ('%s' vs '%s')",
+ group, key, v1, v2);
+ }
+ g_free(v1);
+ g_free(v2);
+ }
+ } else {
+ GDEBUG("Keys for %s don't match", group);
+ }
+ g_strfreev(keys);
+ g_strfreev(keys2);
+ }
+ } else {
+ GDEBUG("Groups don't match");
+ }
+ g_strfreev(groups);
+ g_strfreev(groups2);
+ if (!equal) {
+ char* data1 = g_key_file_to_data(keyfile1, NULL, NULL);
+ char* data2 = g_key_file_to_data(keyfile2, NULL, NULL);
+
+ GDEBUG("This:");
+ GDEBUG("%s", data1);
+ GDEBUG("Doesn't match this:");
+ GDEBUG("%s", data2);
+ g_free(data1);
+ g_free(data2);
+ }
+ return equal;
+}
+
+/*==========================================================================*
+ * null
+ *==========================================================================*/
+
+static
+void
+test_null(
+ void)
+{
+ const char* default_name = gbinder_config_file;
+
+ /* Reset the state */
+ gbinder_config_exit();
+ gbinder_config_file = NULL;
+ gbinder_config_dir = NULL;
+ g_assert(!gbinder_config_get());
+
+ /* Reset the state again */
+ gbinder_config_file = default_name;
+}
+
+/*==========================================================================*
+ * non_exist
+ *==========================================================================*/
+
+static
+void
+test_non_exit(
+ void)
+{
+ const char* default_name = gbinder_config_file;
+ char* dir = g_dir_make_tmp(TMP_DIR_TEMPLATE, NULL);
+ char* file = g_build_filename(dir, "test.conf", NULL);
+
+ /* Reset the state */
+ gbinder_config_exit();
+
+ gbinder_config_file = file;
+ g_assert(!gbinder_config_get());
+
+ /* Reset the state again */
+ gbinder_config_file = default_name;
+
+ g_free(file);
+ remove(dir);
+ g_free(dir);
+}
+
+/*==========================================================================*
+ * bad_config
+ *==========================================================================*/
+
+static
+void
+test_bad_config(
+ void)
+{
+ const char* default_name = gbinder_config_file;
+ char* dir = g_dir_make_tmp(TMP_DIR_TEMPLATE, NULL);
+ char* file = g_build_filename(dir, "test.conf", NULL);
+ static const char garbage[] = "foo";
+
+ /* Reset the state */
+ gbinder_config_exit();
+
+ /* Try to load the garbage */
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_driver/unit_driver.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -36,6 +36,7 @@
#include "gbinder_handler.h"
#include "gbinder_local_request_p.h"
#include "gbinder_output_data.h"
+#include "gbinder_rpc_protocol.h"
#include <poll.h>
@@ -60,6 +61,9 @@
driver = gbinder_driver_new(dev, NULL);
g_assert(driver);
g_assert(!g_strcmp0(dev, gbinder_driver_dev(driver)));
+ g_assert(gbinder_driver_protocol(driver));
+ g_assert(gbinder_driver_protocol(driver) ==
+ gbinder_rpc_protocol_for_device(dev));
g_assert(gbinder_driver_ref(driver) == driver);
gbinder_driver_unref(driver);
gbinder_driver_free_buffer(driver, NULL);
@@ -72,9 +76,11 @@
g_assert(gbinder_driver_exit_looper(driver));
g_assert(!gbinder_driver_request_death_notification(driver, NULL));
g_assert(!gbinder_driver_clear_death_notification(driver, NULL));
+ g_assert(!gbinder_driver_dead_binder_done(NULL, NULL));
gbinder_driver_unref(driver);
g_assert(!gbinder_handler_transact(NULL, NULL, NULL, 0, 0, NULL));
+ g_assert(!gbinder_handler_can_loop(NULL));
}
/*==========================================================================*
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_eventloop/unit_eventloop.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2020 Jolla Ltd.
- * Copyright (C) 2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2020-2021 Jolla Ltd.
+ * Copyright (C) 2020-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -48,6 +48,14 @@
return G_SOURCE_CONTINUE;
}
+static
+void
+test_quit_cb(
+ gpointer data)
+{
+ g_main_loop_quit((GMainLoop*)data);
+}
+
/*==========================================================================*
* Test event loop integration
*==========================================================================*/
@@ -214,14 +222,6 @@
static
void
-test_quit_cb(
- gpointer data)
-{
- g_main_loop_quit((GMainLoop*)data);
-}
-
-static
-void
test_callback(
void)
{
@@ -230,6 +230,8 @@
gbinder_eventloop_set(NULL);
cb = gbinder_idle_callback_new(test_quit_cb, loop, NULL);
+ g_assert(gbinder_idle_callback_ref(cb) == cb);
+ gbinder_idle_callback_unref(cb);
gbinder_idle_callback_schedule(cb);
test_run(&test_opt, loop);
gbinder_idle_callback_unref(cb);
@@ -237,6 +239,28 @@
}
/*==========================================================================*
+ * invoke
+ *==========================================================================*/
+
+static
+void
+test_invoke(
+ void)
+{
+ GMainLoop* loop = g_main_loop_new(NULL, FALSE);
+
+ gbinder_eventloop_set(NULL);
+ gbinder_idle_callback_invoke_later(test_quit_cb, loop, NULL);
+ test_run(&test_opt, loop);
+
+ gbinder_eventloop_set(NULL);
+ gbinder_idle_callback_invoke_later(NULL, loop, test_quit_cb);
+ test_run(&test_opt, loop);
+
+ g_main_loop_unref(loop);
+}
+
+/*==========================================================================*
* Common
*==========================================================================*/
@@ -249,6 +273,7 @@
g_test_add_func(TEST_("idle"), test_idle);
g_test_add_func(TEST_("timeout"), test_timeout);
g_test_add_func(TEST_("callback"), test_callback);
+ g_test_add_func(TEST_("invoke"), test_invoke);
test_init(&test_opt, argc, argv);
return g_test_run();
}
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_ipc/unit_ipc.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -84,10 +84,16 @@
g_assert(!gbinder_ipc_ref(null));
gbinder_ipc_unref(null);
- g_assert(!gbinder_ipc_transact_sync_reply(null, 0, 0, NULL, NULL));
- g_assert(!gbinder_ipc_transact_sync_reply(null, 0, 0, NULL, &status));
- g_assert(status == (-EINVAL));
- g_assert(gbinder_ipc_transact_sync_oneway(null, 0, 0, NULL) == (-EINVAL));
+ g_assert(!gbinder_ipc_sync_main.sync_reply(null, 0, 0, NULL, NULL));
+ g_assert(!gbinder_ipc_sync_main.sync_reply(null, 0, 0, NULL, &status));
+ g_assert_cmpint(status, == ,-EINVAL);
+ g_assert(!gbinder_ipc_sync_worker.sync_reply(null, 0, 0, NULL, NULL));
+ g_assert(!gbinder_ipc_sync_worker.sync_reply(null, 0, 0, NULL, &status));
+ g_assert_cmpint(status, == ,-EINVAL);
+ g_assert_cmpint(gbinder_ipc_sync_main.sync_oneway(null, 0, 0, NULL), == ,
+ -EINVAL);
+ g_assert_cmpint(gbinder_ipc_sync_worker.sync_oneway(null, 0, 0, NULL), == ,
+ -EINVAL);
g_assert(!gbinder_ipc_transact(null, 0, 0, 0, NULL, NULL, NULL, NULL));
g_assert(!gbinder_ipc_transact_custom(null, NULL, NULL, NULL, NULL));
g_assert(!gbinder_ipc_object_registry(null));
@@ -97,7 +103,8 @@
g_assert(!gbinder_object_registry_ref(NULL));
gbinder_object_registry_unref(NULL);
g_assert(!gbinder_object_registry_get_local(NULL, NULL));
- g_assert(!gbinder_object_registry_get_remote(NULL, 0));
+ g_assert(!gbinder_object_registry_get_remote(NULL, 0, FALSE));
+ g_assert(!gbinder_ipc_find_local_object(NULL, NULL, NULL));
}
/*==========================================================================*
@@ -105,12 +112,21 @@
*==========================================================================*/
static
+gboolean
+test_basic_find_none(
+ GBinderLocalObject* obj,
+ void* user_data)
+{
+ return FALSE;
+}
+
+static
void
test_basic(
void)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
- GBinderIpc* ipc2 = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
+ GBinderIpc* ipc2 = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
g_assert(ipc);
g_assert(ipc2);
@@ -118,17 +134,21 @@
gbinder_ipc_cancel(ipc2, 0); /* not a valid transaction */
gbinder_ipc_unref(ipc2);
+ g_assert(!gbinder_ipc_find_local_object(NULL, test_basic_find_none, NULL));
+ g_assert(!gbinder_ipc_find_local_object(ipc, test_basic_find_none, NULL));
+
/* Second gbinder_ipc_new returns the same (default) object */
- g_assert(gbinder_ipc_new(NULL, NULL) == ipc);
- g_assert(gbinder_ipc_new("", NULL) == ipc);
+ g_assert(gbinder_ipc_new(NULL) == ipc);
+ g_assert(gbinder_ipc_new("") == ipc);
gbinder_ipc_unref(ipc);
gbinder_ipc_unref(ipc);
gbinder_ipc_unref(ipc);
/* Invalid path */
- g_assert(!gbinder_ipc_new("invalid path", NULL));
+ g_assert(!gbinder_ipc_new("invalid path"));
gbinder_ipc_exit();
+ test_binder_exit_wait(&test_opt, NULL);
}
/*==========================================================================*
@@ -153,7 +173,7 @@
test_async_oneway(
void)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
const GBinderIo* io = gbinder_driver_io(ipc->driver);
const int fd = gbinder_driver_fd(ipc->driver);
GBinderLocalRequest* req = gbinder_local_request_new(io, NULL);
@@ -180,17 +200,17 @@
test_sync_oneway(
void)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
const GBinderIo* io = gbinder_driver_io(ipc->driver);
const int fd = gbinder_driver_fd(ipc->driver);
GBinderLocalRequest* req = gbinder_local_request_new(io, NULL);
test_binder_br_transaction_complete(fd);
- g_assert(gbinder_ipc_transact_sync_oneway(ipc, 0, 1, req) ==
- GBINDER_STATUS_OK);
+ g_assert_cmpint(gbinder_ipc_sync_main.sync_oneway(ipc, 0, 1, req), == ,0);
gbinder_local_request_unref(req);
gbinder_ipc_unref(ipc);
gbinder_ipc_exit();
+ test_binder_exit_wait(&test_opt, NULL);
}
/*==========================================================================*
@@ -202,7 +222,7 @@
test_sync_reply_ok_status(
int* status)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
const GBinderIo* io = gbinder_driver_io(ipc->driver);
const int fd = gbinder_driver_fd(ipc->driver);
GBinderLocalRequest* req = gbinder_local_request_new(io, NULL);
@@ -223,7 +243,7 @@
test_binder_br_noop(fd);
test_binder_br_reply(fd, handle, code, data->bytes);
- tx_reply = gbinder_ipc_transact_sync_reply(ipc, handle, code, req, status);
+ tx_reply = gbinder_ipc_sync_main.sync_reply(ipc, handle, code, req, status);
g_assert(tx_reply);
result_out = gbinder_remote_reply_read_string16(tx_reply);
@@ -235,6 +255,7 @@
gbinder_local_reply_unref(reply);
gbinder_ipc_unref(ipc);
gbinder_ipc_exit();
+ test_binder_exit_wait(&test_opt, NULL);
}
static
@@ -258,13 +279,14 @@
test_sync_reply_error(
void)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
const GBinderIo* io = gbinder_driver_io(ipc->driver);
const int fd = gbinder_driver_fd(ipc->driver);
GBinderLocalRequest* req = gbinder_local_request_new(io, NULL);
const guint32 handle = 0;
const guint32 code = 1;
- const gint expected_status = GBINDER_STATUS_FAILED;
+ const gint expected_status = (-EINVAL);
+ const gint unexpected_status = GBINDER_STATUS_FAILED;
int status = INT_MAX;
test_binder_br_noop(fd);
@@ -272,12 +294,22 @@
test_binder_br_noop(fd);
test_binder_br_reply_status(fd, expected_status);
- g_assert(!gbinder_ipc_transact_sync_reply(ipc, handle, code, req, &status));
- g_assert(status == expected_status);
+ g_assert(!gbinder_ipc_sync_main.sync_reply(ipc,handle,code,req,&status));
+ g_assert_cmpint(status, == ,expected_status);
+
+ /* GBINDER_STATUS_FAILED gets replaced with -EFAULT */
+ test_binder_br_noop(fd);
+ test_binder_br_transaction_complete(fd);
+ test_binder_br_noop(fd);
+ test_binder_br_reply_status(fd, unexpected_status);
+
+ g_assert(!gbinder_ipc_sync_main.sync_reply(ipc,handle,code,req,&status));
+ g_assert_cmpint(status, == ,-EFAULT);
gbinder_local_request_unref(req);
gbinder_ipc_unref(ipc);
gbinder_ipc_exit();
+ test_binder_exit_wait(&test_opt, NULL);
}
/*==========================================================================*
@@ -316,7 +348,7 @@
test_transact_ok(
void)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
const GBinderIo* io = gbinder_driver_io(ipc->driver);
const int fd = gbinder_driver_fd(ipc->driver);
GBinderLocalRequest* req = gbinder_local_request_new(io, NULL);
@@ -348,6 +380,7 @@
gbinder_local_reply_unref(reply);
gbinder_ipc_unref(ipc);
gbinder_ipc_exit();
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_local_object/unit_local_object.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -137,7 +137,7 @@
g_assert(!gbinder_ipc_transact_custom(NULL, NULL, NULL, NULL, NULL));
gbinder_local_object_handle_increfs(NULL);
gbinder_local_object_handle_decrefs(NULL);
- gbinder_local_object_handle_acquire(NULL);
+ gbinder_local_object_handle_acquire(NULL, NULL);
gbinder_local_object_handle_release(NULL);
}
@@ -152,7 +152,7 @@
{
const char* const ifaces_foo[] = { "foo", NULL };
const char* const ifaces_bar[] = { "bar", NULL };
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
GBinderLocalObject* foo;
GBinderLocalObject* bar;
@@ -179,7 +179,7 @@
base_interface, -1) == GBINDER_LOCAL_TRANSACTION_NOT_SUPPORTED);
gbinder_local_object_handle_increfs(foo);
gbinder_local_object_handle_decrefs(foo);
- gbinder_local_object_handle_acquire(foo);
+ gbinder_local_object_handle_acquire(foo, NULL);
gbinder_local_object_handle_release(foo);
gbinder_local_object_unref(foo);
@@ -201,7 +201,7 @@
int status = INT_MAX;
const char* dev = GBINDER_DEFAULT_HWBINDER;
const GBinderRpcProtocol* prot = gbinder_rpc_protocol_for_device(dev);
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
GBinderRemoteRequest* req = gbinder_remote_request_new(reg, prot, 0, 0);
GBinderLocalObject* obj = gbinder_local_object_new(ipc, NULL, NULL, NULL);
@@ -247,7 +247,7 @@
const char* dev = GBINDER_DEFAULT_HWBINDER;
const GBinderRpcProtocol* prot = gbinder_rpc_protocol_for_device(dev);
const char* const ifaces[] = { "x", NULL };
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
GBinderRemoteRequest* req = gbinder_remote_request_new(reg, prot, 0, 0);
GBinderLocalObject* obj = gbinder_local_object_new(ipc, ifaces, NULL, NULL);
@@ -296,7 +296,7 @@
int status = INT_MAX;
const char* dev = GBINDER_DEFAULT_HWBINDER;
const GBinderRpcProtocol* prot = gbinder_rpc_protocol_for_device(dev);
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
GBinderRemoteRequest* req = gbinder_remote_request_new(reg, prot, 0, 0);
GBinderLocalObject* obj = gbinder_local_object_new(ipc, NULL, NULL, NULL);
@@ -346,7 +346,7 @@
int status = INT_MAX;
const char* dev = GBINDER_DEFAULT_HWBINDER;
const GBinderRpcProtocol* prot = gbinder_rpc_protocol_for_device(dev);
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
GBinderRemoteRequest* req = gbinder_remote_request_new(reg, prot, 0, 0);
GBinderLocalObject* obj = gbinder_local_object_new(ipc, NULL, NULL, NULL);
@@ -402,7 +402,7 @@
const char* dev = GBINDER_DEFAULT_HWBINDER;
const char* const ifaces[] = { "android.hidl.base@1.0::IBase", NULL };
const GBinderRpcProtocol* prot = gbinder_rpc_protocol_for_device(dev);
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
GBinderRemoteRequest* req = gbinder_remote_request_new(reg, prot, 0, 0);
GBinderLocalObject* obj = gbinder_local_object_new(ipc, ifaces, NULL, NULL);
@@ -476,7 +476,7 @@
int count = 0, status = INT_MAX;
const char* dev = GBINDER_DEFAULT_HWBINDER;
const GBinderRpcProtocol* prot = gbinder_rpc_protocol_for_device(dev);
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
GBinderRemoteRequest* req = gbinder_remote_request_new(reg, prot, 0, 0);
GBinderLocalObject* obj = gbinder_local_object_new(ipc, ifaces,
@@ -583,7 +583,7 @@
int count = 0, status = 0;
const char* dev = GBINDER_DEFAULT_HWBINDER;
const GBinderRpcProtocol* prot = gbinder_rpc_protocol_for_device(dev);
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
GBinderRemoteRequest* req = gbinder_remote_request_new(reg, prot, 0, 0);
GBinderLocalObject* obj = gbinder_local_object_new(ipc, ifaces,
@@ -621,10 +621,10 @@
static
void
-test_increfs(
+test_increfs_run(
void)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
GBinderLocalObject* obj = gbinder_local_object_new
(ipc, NULL, NULL, NULL);
GMainLoop* loop = g_main_loop_new(NULL, FALSE);
@@ -635,16 +635,25 @@
/* ipc is not an object, will be ignored */
test_binder_br_increfs(fd, ipc);
test_binder_br_increfs(fd, obj);
- test_binder_set_looper_enabled(fd, TRUE);
+ test_binder_set_looper_enabled(fd, TEST_LOOPER_ENABLE);
test_run(&test_opt, loop);
g_assert(obj->weak_refs == 1);
gbinder_local_object_remove_handler(obj, id);
gbinder_local_object_unref(obj);
gbinder_ipc_unref(ipc);
+ gbinder_ipc_exit();
g_main_loop_unref(loop);
}
+static
+void
+test_increfs(
+ void)
+{
+ test_run_in_context(&test_opt, test_increfs_run);
+}
+
/*==========================================================================*
* decrefs
*==========================================================================*/
@@ -663,10 +672,10 @@
static
void
-test_decrefs(
+test_decrefs_run(
void)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
GBinderLocalObject* obj = gbinder_local_object_new
(ipc, NULL, NULL, NULL);
GMainLoop* loop = g_main_loop_new(NULL, FALSE);
@@ -678,16 +687,25 @@
test_binder_br_decrefs(fd, ipc);
test_binder_br_increfs(fd, obj);
test_binder_br_decrefs(fd, obj);
- test_binder_set_looper_enabled(fd, TRUE);
+ test_binder_set_looper_enabled(fd, TEST_LOOPER_ENABLE);
test_run(&test_opt, loop);
g_assert(obj->weak_refs == 0);
gbinder_local_object_remove_handler(obj, id);
gbinder_local_object_unref(obj);
gbinder_ipc_unref(ipc);
+ gbinder_ipc_exit();
g_main_loop_unref(loop);
}
+static
+void
+test_decrefs(
+ void)
+{
+ test_run_in_context(&test_opt, test_decrefs_run);
+}
+
/*==========================================================================*
* acquire
*==========================================================================*/
@@ -705,10 +723,10 @@
static
void
-test_acquire(
+test_acquire_run(
void)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_local_reply/unit_local_reply.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -88,7 +88,8 @@
gbinder_local_reply_init_writer(NULL, NULL);
gbinder_local_reply_init_writer(NULL, &writer);
g_assert(!gbinder_local_reply_data(NULL));
- g_assert(!gbinder_local_reply_new_from_data(NULL));
+ g_assert(!gbinder_local_reply_contents(NULL));
+ g_assert(!gbinder_local_reply_set_contents(NULL, NULL, NULL));
gbinder_local_reply_cleanup(NULL, NULL, &count);
gbinder_local_reply_cleanup(NULL, test_int_inc, &count);
@@ -399,7 +400,7 @@
GBinderLocalReply* reply;
GBinderOutputData* data;
GUtilIntArray* offsets;
- GBinderIpc* ipc = gbinder_ipc_new(NULL, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(NULL);
const char* const ifaces[] = { "android.hidl.base@1.0::IBase", NULL };
GBinderLocalObject* obj = gbinder_local_object_new(ipc, ifaces, NULL, NULL);
@@ -479,7 +480,8 @@
/* Copy flat structures (no binder objects) */
buffer = test_buffer_from_bytes(driver, bytes);
- req2 = gbinder_local_reply_new_from_data(buffer);
+ req2 = gbinder_local_reply_new(io);
+ g_assert(gbinder_local_reply_set_contents(req2, buffer, NULL) == req2);
gbinder_buffer_free(buffer);
data2 = gbinder_local_reply_data(req2);
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_local_request/unit_local_request.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2020 Jolla Ltd.
- * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -94,7 +94,7 @@
g_assert(!gbinder_local_request_new(NULL, NULL));
g_assert(!gbinder_local_request_ref(NULL));
- g_assert(!gbinder_local_request_new_from_data(NULL));
+ g_assert(!gbinder_local_request_new_from_data(NULL, NULL));
gbinder_local_request_unref(NULL);
gbinder_local_request_init_writer(NULL, NULL);
gbinder_local_request_init_writer(NULL, &writer);
@@ -490,7 +490,7 @@
/* Copy flat structures (no binder objects) */
buffer = test_buffer_from_bytes(driver, bytes);
- req2 = gbinder_local_request_new_from_data(buffer);
+ req2 = gbinder_local_request_new_from_data(buffer, NULL);
gbinder_buffer_free(buffer);
data2 = gbinder_local_request_data(req2);
@@ -503,7 +503,7 @@
/* Same thing but with non-NULL (albeit empty) array of objects */
buffer = test_buffer_from_bytes_and_objects(driver, bytes, no_obj);
- req2 = gbinder_local_request_new_from_data(buffer);
+ req2 = gbinder_local_request_new_from_data(buffer, NULL);
gbinder_buffer_free(buffer);
data2 = gbinder_local_request_data(req2);
@@ -572,7 +572,7 @@
}
buffer = test_buffer_from_bytes_and_objects(driver, data->bytes, objects);
- req2 = gbinder_local_request_new_from_data(buffer);
+ req2 = gbinder_local_request_new_from_data(buffer, NULL);
gbinder_buffer_free(buffer);
test_remote_request_obj_validate_data(gbinder_local_request_data(req2));
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_protocol/unit_protocol.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018 Jolla Ltd.
- * Copyright (C) 2018 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2020 Jolla Ltd.
+ * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -33,6 +33,7 @@
#include "test_common.h"
#include "gbinder_buffer_p.h"
+#include "gbinder_config.h"
#include "gbinder_driver.h"
#include "gbinder_io.h"
#include "gbinder_local_request_p.h"
@@ -43,36 +44,118 @@
#include "gbinder_writer.h"
static TestOpt test_opt;
+static const char TMP_DIR_TEMPLATE[] = "gbinder-test-protocol-XXXXXX";
#define STRICT_MODE_PENALTY_GATHER (0x40 << 16)
#define BINDER_RPC_FLAGS (STRICT_MODE_PENALTY_GATHER)
+#define UNSET_WORK_SOURCE (-1)
+
+typedef struct test_data {
+ const char* name;
+ const char* prot;
+ const char* dev;
+} TestData;
typedef struct test_header_data {
const char* name;
+ const char* prot;
const char* dev;
const char* iface;
const guint8* header;
guint header_size;
} TestHeaderData;
-static const guint8 test_header_binder [] = {
+static const guint8 test_header_aidl [] = {
TEST_INT32_BYTES(BINDER_RPC_FLAGS),
TEST_INT32_BYTES(3),
TEST_INT16_BYTES('f'), TEST_INT16_BYTES('o'),
TEST_INT16_BYTES('o'), 0x00, 0x00
};
-static const guint8 test_header_hwbinder [] = {
+static const guint8 test_header_aidl2 [] = {
+ TEST_INT32_BYTES(BINDER_RPC_FLAGS),
+ TEST_INT32_BYTES(UNSET_WORK_SOURCE),
+ TEST_INT32_BYTES(3),
+ TEST_INT16_BYTES('f'), TEST_INT16_BYTES('o'),
+ TEST_INT16_BYTES('o'), 0x00, 0x00
+};
+
+static const guint8 test_header_hidl [] = {
'f', 'o', 'o', 0x00
};
static const TestHeaderData test_header_tests[] = {
- { "binder", GBINDER_DEFAULT_BINDER, "foo",
- TEST_ARRAY_AND_SIZE(test_header_binder) },
- { "hwbinder", GBINDER_DEFAULT_HWBINDER, "foo",
- TEST_ARRAY_AND_SIZE(test_header_hwbinder) }
+ { "aidl/ok", "aidl", GBINDER_DEFAULT_BINDER, "foo",
+ TEST_ARRAY_AND_SIZE(test_header_aidl) },
+ { "aidl/short", "aidl", GBINDER_DEFAULT_BINDER, NULL,
+ test_header_aidl, 8 }, /* Short packet */
+ { "aidl2/ok", "aidl2", GBINDER_DEFAULT_BINDER, "foo",
+ TEST_ARRAY_AND_SIZE(test_header_aidl2) },
+ { "aidl2/short/1", "aidl2", GBINDER_DEFAULT_BINDER, NULL,
+ test_header_aidl2, 1 }, /* Short packet */
+ { "aidl2/short/2", "aidl2", GBINDER_DEFAULT_BINDER, NULL,
+ test_header_aidl2, 5 }, /* Short packet */
+ { "aidl2/short/3", "adl2", GBINDER_DEFAULT_BINDER, NULL,
+ test_header_aidl2, 9 }, /* Short packet */
+ { "hidl/ok", "hidl", GBINDER_DEFAULT_HWBINDER, "foo",
+ TEST_ARRAY_AND_SIZE(test_header_hidl) },
+ { "hidl/short", "hidl", GBINDER_DEFAULT_HWBINDER, NULL,
+ test_header_hidl, 1 }
};
+typedef struct test_config {
+ char* dir;
+ char* file;
+} TestConfig;
+
+static
+void
+test_config_init(
+ TestConfig* test,
+ const char* config)
+{
+ test->dir = g_dir_make_tmp(TMP_DIR_TEMPLATE, NULL);
+ test->file = g_build_filename(test->dir, "test.conf", NULL);
+
+ /* Reset the state */
+ gbinder_rpc_protocol_exit();
+ gbinder_config_exit();
+
+ /* Write the config */
+ g_assert(g_file_set_contents(test->file, config, -1, NULL));
+ gbinder_config_file = test->file;
+}
+
+static
+void
+test_config_init2(
+ TestConfig* test,
+ const char* dev,
+ const char* prot)
+{
+ char* config = g_strconcat("[Protocol]\n", dev, " = ", prot, "\n", NULL);
+
+ test_config_init(test, config);
+ g_free(config);
+}
+
+static
+void
+test_config_cleanup(
+ TestConfig* test)
+{
+ /* Undo the damage */
+ gbinder_rpc_protocol_exit();
+ gbinder_config_exit();
+ gbinder_config_file = NULL;
+
+ remove(test->file);
+ g_free(test->file);
+
+ remove(test->dir);
+ g_free(test->dir);
+}
+
/*==========================================================================*
* device
*==========================================================================*/
@@ -82,12 +165,129 @@
test_device(
void)
{
- g_assert(gbinder_rpc_protocol_for_device(NULL) ==
- &gbinder_rpc_protocol_binder);
- g_assert(gbinder_rpc_protocol_for_device(GBINDER_DEFAULT_BINDER) ==
- &gbinder_rpc_protocol_binder);
- g_assert(gbinder_rpc_protocol_for_device(GBINDER_DEFAULT_HWBINDER) ==
- &gbinder_rpc_protocol_hwbinder);
+ const GBinderRpcProtocol* p;
+
+ p = gbinder_rpc_protocol_for_device(NULL);
+ g_assert(p);
+ g_assert_cmpstr(p->name, == ,"aidl");
+
+ p = gbinder_rpc_protocol_for_device(GBINDER_DEFAULT_BINDER);
+ g_assert(p);
+ g_assert_cmpstr(p->name, == ,"aidl");
+
+ p = gbinder_rpc_protocol_for_device(GBINDER_DEFAULT_HWBINDER);
+ g_assert(p);
+ g_assert_cmpstr(p->name, == ,"hidl");
+}
+
+/*==========================================================================*
+ * config1
+ *==========================================================================*/
+
+static
+void
+test_config1(
+ void)
+{
+ const GBinderRpcProtocol* p;
+ TestConfig config;
+
+ test_config_init(&config,
+ "[Protocol]\n"
+ "/dev/binder = hidl\n" /* Redefined name for /dev/binder */
+ "/dev/hwbinder = foo\n"); /* Invalid protocol name */
+
+ p = gbinder_rpc_protocol_for_device(NULL);
+ g_assert(p);
+ g_assert_cmpstr(p->name, == ,"aidl");
+
+ p = gbinder_rpc_protocol_for_device("/dev/hwbinder");
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_proxy_object/Makefile
^
|
@@ -0,0 +1,6 @@
+# -*- Mode: makefile-gmake -*-
+
+EXE = unit_proxy_object
+COMMON_SRC = test_binder.c test_main.c test_servicemanager_hidl.c
+
+include ../common/Makefile
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_proxy_object/unit_proxy_object.c
^
|
@@ -0,0 +1,699 @@
+/*
+ * Copyright (C) 2021 Jolla Ltd.
+ * Copyright (C) 2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "test_binder.h"
+
+#include "gbinder_ipc.h"
+#include "gbinder_client.h"
+#include "gbinder_config.h"
+#include "gbinder_driver.h"
+#include "gbinder_proxy_object.h"
+#include "gbinder_remote_object_p.h"
+#include "gbinder_remote_request.h"
+#include "gbinder_remote_reply.h"
+#include "gbinder_local_request.h"
+#include "gbinder_local_reply.h"
+
+#include <gutil_log.h>
+
+#include <errno.h>
+
+static TestOpt test_opt;
+
+#define DEV "/dev/xbinder"
+#define DEV_PRIV DEV "-private"
+#define DEV2 "/dev/ybinder"
+#define DEV2_PRIV DEV2 "-private"
+
+enum test_tx_codes {
+ TX_CODE = GBINDER_FIRST_CALL_TRANSACTION,
+ TX_CODE2,
+ TX_CODE3
+};
+#define TX_PARAM1 0x11111111
+#define TX_PARAM2 0x22222222
+#define TX_PARAM3 0x33333333
+#define TX_RESULT1 0x01010101
+#define TX_RESULT2 0x02020202
+#define TX_PARAM_REPLY 0x11110000
+#define TX_PARAM_DONT_REPLY 0x22220000
+#define TX_RESULT 0x03030303
+
+static const char TMP_DIR_TEMPLATE[] = "gbinder-test-proxy-XXXXXX";
+const char TEST_IFACE[] = "test@1.0::ITest";
+const char TEST_IFACE2[] = "test@1.0::ITest2";
+static const char* TEST_IFACES[] = { TEST_IFACE, NULL };
+static const char* TEST_IFACES2[] = { TEST_IFACE2, NULL };
+static const char DEFAULT_CONFIG_DATA[] =
+ "[Protocol]\n"
+ "Default = hidl\n"
+ "[ServiceManager]\n"
+ "Default = hidl\n";
+
+typedef struct test_config {
+ char* dir;
+ char* file;
+} TestConfig;
+
+/*==========================================================================*
+ * Common
+ *==========================================================================*/
+
+static
+void
+test_config_init(
+ TestConfig* config,
+ char* config_data)
+{
+ config->dir = g_dir_make_tmp(TMP_DIR_TEMPLATE, NULL);
+ config->file = g_build_filename(config->dir, "test.conf", NULL);
+ g_assert(g_file_set_contents(config->file, config_data ? config_data :
+ DEFAULT_CONFIG_DATA, -1, NULL));
+
+ gbinder_config_exit();
+ gbinder_config_dir = config->dir;
+ gbinder_config_file = config->file;
+ GDEBUG("Wrote config to %s", config->file);
+}
+
+static
+void
+test_config_deinit(
+ TestConfig* config)
+{
+ gbinder_config_exit();
+
+ remove(config->file);
+ g_free(config->file);
+
+ remove(config->dir);
+ g_free(config->dir);
+}
+
+/*==========================================================================*
+ * null
+ *==========================================================================*/
+
+static
+void
+test_null(
+ void)
+{
+ g_assert(!gbinder_proxy_object_new(NULL, NULL));
+}
+
+/*==========================================================================*
+ * basic
+ *==========================================================================*/
+
+static
+GBinderLocalReply*
+test_basic_cb(
+ GBinderLocalObject* obj,
+ GBinderRemoteRequest* req,
+ guint code,
+ guint flags,
+ int* status,
+ void* user_data)
+{
+ int* count = user_data;
+ GBinderReader reader;
+
+ GDEBUG("Request handled");
+ g_assert(!flags);
+ g_assert(!g_strcmp0(gbinder_remote_request_interface(req), TEST_IFACE));
+ g_assert(code == TX_CODE);
+
+ /* No parameters are expected */
+ gbinder_remote_request_init_reader(req, &reader);
+ g_assert(gbinder_reader_at_end(&reader));
+
+ *status = GBINDER_STATUS_OK;
+ (*count)++;
+ return gbinder_local_object_new_reply(obj);
+}
+
+static
+void
+test_basic_reply(
+ GBinderClient* client,
+ GBinderRemoteReply* reply,
+ int status,
+ void* loop)
+{
+ GBinderReader reader;
+
+ GDEBUG("Reply received");
+
+ /* No parameters are expected */
+ gbinder_remote_reply_init_reader(reply, &reader);
+ g_assert(gbinder_reader_at_end(&reader));
+
+ g_main_loop_quit((GMainLoop*)loop);
+}
+
+static
+void
+test_basic_run(
+ void)
+{
+ TestConfig config;
+ GBinderLocalObject* obj;
+ GBinderProxyObject* proxy;
+ GBinderRemoteObject* remote_obj;
+ GBinderRemoteObject* remote_proxy;
+ GBinderClient* proxy_client;
+ GBinderIpc* ipc_obj;
+ GBinderIpc* ipc_proxy;
+ GMainLoop* loop = g_main_loop_new(NULL, FALSE);
+ int fd_obj, fd_proxy, n = 0;
+
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_reader/unit_reader.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2020 Jolla Ltd.
+ * Copyright (C) 2018-2020 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -624,7 +624,7 @@
gconstpointer test_data)
{
const TestHidlStruct* test = test_data;
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(test->in, test->in_size), test->in_size, NULL);
GBinderReaderData data;
@@ -828,7 +828,7 @@
gconstpointer test_data)
{
const TestHidlVec* test = test_data;
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(test->in, test->in_size), test->in_size, NULL);
GBinderReaderData data;
@@ -934,7 +934,7 @@
gconstpointer test_data)
{
const TestHidlStringErr* test = test_data;
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(test->in, test->in_size), test->in_size, NULL);
GBinderReaderData data;
@@ -968,7 +968,7 @@
gconstpointer test_data)
{
const TestHidlStringErr* test = test_data;
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(test->in, test->in_size), test->in_size, NULL);
GBinderReaderData data;
@@ -1013,7 +1013,7 @@
TEST_INT32_BYTES(fd), TEST_INT32_BYTES(0),
TEST_INT64_BYTES(0)
};
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(input, sizeof(input)), sizeof(input), NULL);
GBinderReaderData data;
@@ -1053,7 +1053,7 @@
TEST_INT32_BYTES(BINDER_TYPE_FD),
TEST_INT32_BYTES(0x7f | BINDER_FLAG_ACCEPTS_FDS)
};
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(input, sizeof(input)), sizeof(input), NULL);
GBinderReaderData data;
@@ -1087,7 +1087,7 @@
TEST_INT32_BYTES(fd), TEST_INT32_BYTES(0),
TEST_INT64_BYTES(0)
};
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(input, sizeof(input)), sizeof(input), NULL);
GBinderReaderData data;
@@ -1130,7 +1130,7 @@
TEST_INT32_BYTES(fd), TEST_INT32_BYTES(0),
TEST_INT64_BYTES(0)
};
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(input, sizeof(input)), sizeof(input), NULL);
GBinderReaderData data;
@@ -1177,7 +1177,7 @@
TEST_INT32_BYTES(fd), TEST_INT32_BYTES(0),
TEST_INT64_BYTES(0)
};
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(input, sizeof(input)), sizeof(input), NULL);
GBinderReaderData data;
@@ -1220,7 +1220,7 @@
TEST_INT32_BYTES(fd), TEST_INT32_BYTES(0),
TEST_INT64_BYTES(0)
};
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(input, sizeof(input)), sizeof(input), NULL);
GBinderReaderData data;
@@ -1259,7 +1259,7 @@
guint bufcount,
const char* result)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver, g_memdup(input, size),
size, NULL);
GBinderRemoteObject* obj = NULL;
@@ -1530,7 +1530,7 @@
TEST_INT64_BYTES(0), TEST_INT64_BYTES(0),
TEST_INT64_BYTES(0), TEST_INT64_BYTES(0)
};
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(input, sizeof(input)), sizeof(input), NULL);
GBinderRemoteObject* obj = NULL;
@@ -1578,7 +1578,7 @@
TEST_INT32_BYTES(BINDER_TYPE_HANDLE), TEST_INT32_BYTES(0),
TEST_INT64_BYTES(1 /* handle*/), TEST_INT64_BYTES(0)
};
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(input, sizeof(input)), sizeof(input), NULL);
GBinderRemoteObject* obj = NULL;
@@ -1636,7 +1636,7 @@
TEST_INT32_BYTES(42 /* invalid type */), TEST_INT32_BYTES(0),
TEST_INT64_BYTES(1 /* handle*/), TEST_INT64_BYTES(0)
};
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver,
g_memdup(input, sizeof(input)), sizeof(input), NULL);
GBinderRemoteObject* obj = NULL;
@@ -1670,7 +1670,7 @@
void)
{
/* Using 64-bit I/O */
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
GBinderReaderData data;
GBinderReader reader;
BinderObject64 obj;
@@ -1723,7 +1723,7 @@
gsize size,
const char* const* result)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_HWBINDER);
GBinderBuffer* buf = gbinder_buffer_new(ipc->driver, g_memdup(input, size),
size, NULL);
GBinderRemoteObject* obj = NULL;
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_remote_object/unit_remote_object.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -68,10 +68,10 @@
test_basic(
void)
{
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
- GBinderRemoteObject* obj1 = gbinder_object_registry_get_remote(reg, 1);
- GBinderRemoteObject* obj2 = gbinder_object_registry_get_remote(reg, 2);
+ GBinderRemoteObject* obj1 = gbinder_object_registry_get_remote(reg,1,TRUE);
+ GBinderRemoteObject* obj2 = gbinder_object_registry_get_remote(reg,2,TRUE);
g_assert(obj1);
g_assert(obj2);
@@ -84,7 +84,7 @@
g_assert(gbinder_remote_object_ref(obj1) == obj1);
gbinder_remote_object_unref(obj1); /* Compensate the above reference */
g_assert(!gbinder_remote_object_add_death_handler(obj1, NULL, NULL));
- g_assert(gbinder_ipc_get_remote_object(ipc, 1, TRUE) == obj1);
+ g_assert(gbinder_object_registry_get_remote(reg, 1, FALSE) == obj1);
gbinder_remote_object_unref(obj1); /* Compensate the above reference */
gbinder_remote_object_unref(obj1);
gbinder_remote_object_unref(obj2);
@@ -107,20 +107,20 @@
static
void
-test_dead(
+test_dead_run(
void)
{
- const guint handle = 1;
+ const guint h = 1;
GMainLoop* loop = g_main_loop_new(NULL, FALSE);
- GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(GBINDER_DEFAULT_BINDER);
+ GBinderObjectRegistry* reg = gbinder_ipc_object_registry(ipc);
const int fd = gbinder_driver_fd(ipc->driver);
- GBinderRemoteObject* obj = gbinder_ipc_get_remote_object
- (ipc, handle, FALSE);
+ GBinderRemoteObject* obj = gbinder_object_registry_get_remote(reg, h, TRUE);
gulong id = gbinder_remote_object_add_death_handler
(obj, test_dead_done, loop);
- test_binder_br_dead_binder(fd, handle);
- test_binder_set_looper_enabled(fd, TRUE);
+ test_binder_br_dead_binder(fd, h);
+ test_binder_set_looper_enabled(fd, TEST_LOOPER_ENABLE);
test_run(&test_opt, loop);
g_assert(gbinder_remote_object_is_dead(obj));
@@ -128,9 +128,18 @@
gbinder_remote_object_remove_handler(obj, 0); /* has no effect */
gbinder_remote_object_unref(obj);
gbinder_ipc_unref(ipc);
+ gbinder_ipc_exit();
g_main_loop_unref(loop);
}
+static
+void
+test_dead(
+ void)
+{
+ test_run_in_context(&test_opt, test_dead_run);
+}
+
/*==========================================================================*
* Common
*==========================================================================*/
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_remote_reply/unit_remote_reply.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018 Jolla Ltd.
- * Copyright (C) 2018 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -37,6 +37,7 @@
#include "gbinder_reader.h"
#include "gbinder_local_reply_p.h"
#include "gbinder_remote_reply_p.h"
+#include "gbinder_object_registry.h"
#include "gbinder_output_data.h"
#include <gutil_intarray.h>
@@ -47,6 +48,43 @@
#define BINDER_OBJECT_SIZE_64 (GBINDER_MAX_BINDER_OBJECT_SIZE)
/*==========================================================================*
+ * Dummy GBinderObjectRegistry functions
+ *==========================================================================*/
+
+static
+void
+reg_dummy_ref_unref(
+ GBinderObjectRegistry* reg)
+{
+}
+
+static
+GBinderLocalObject*
+reg_dummy_get_local(
+ GBinderObjectRegistry* reg,
+ void* pointer)
+{
+ return NULL;
+}
+
+static
+GBinderRemoteObject*
+reg_dummy_get_remote(
+ GBinderObjectRegistry* reg,
+ guint32 handle,
+ REMOTE_REGISTRY_CREATE create)
+{
+ return NULL;
+}
+
+static GBinderObjectRegistryFunctions reg_dummy_fn = {
+ .ref = reg_dummy_ref_unref,
+ .unref = reg_dummy_ref_unref,
+ .get_local = reg_dummy_get_local,
+ .get_remote = reg_dummy_get_remote
+};
+
+/*==========================================================================*
* null
*==========================================================================*/
@@ -83,7 +121,8 @@
void)
{
GBinderDriver* driver = gbinder_driver_new(GBINDER_DEFAULT_BINDER, NULL);
- GBinderRemoteReply* reply = gbinder_remote_reply_new(NULL);
+ GBinderObjectRegistry reg = { ®_dummy_fn, gbinder_driver_io(driver) };
+ GBinderRemoteReply* reply = gbinder_remote_reply_new(®);
gbinder_remote_reply_set_data(reply,
gbinder_buffer_new(driver, NULL, 0, NULL));
@@ -103,7 +142,9 @@
void)
{
GBinderReader reader;
- GBinderRemoteReply* reply = gbinder_remote_reply_new(NULL);
+ GBinderDriver* driver = gbinder_driver_new(GBINDER_DEFAULT_BINDER, NULL);
+ GBinderObjectRegistry reg = { ®_dummy_fn, gbinder_driver_io(driver) };
+ GBinderRemoteReply* reply = gbinder_remote_reply_new(®);
gbinder_remote_reply_init_reader(reply, &reader);
g_assert(gbinder_reader_at_end(&reader));
@@ -112,6 +153,7 @@
g_assert(!gbinder_remote_reply_read_object(reply));
gbinder_remote_reply_unref(reply);
gbinder_remote_reply_unref(reply);
+ gbinder_driver_unref(driver);
}
/*==========================================================================*
@@ -129,7 +171,8 @@
guint32 out1 = 0;
gint32 out2 = 0;
GBinderDriver* driver = gbinder_driver_new(GBINDER_DEFAULT_BINDER, NULL);
- GBinderRemoteReply* reply = gbinder_remote_reply_new(NULL);
+ GBinderObjectRegistry reg = { ®_dummy_fn, gbinder_driver_io(driver) };
+ GBinderRemoteReply* reply = gbinder_remote_reply_new(®);
gbinder_remote_reply_set_data(reply, gbinder_buffer_new(driver,
g_memdup(reply_data, sizeof(reply_data)), sizeof(reply_data), NULL));
@@ -159,7 +202,8 @@
guint64 out1 = 0;
gint64 out2 = 0;
GBinderDriver* driver = gbinder_driver_new(GBINDER_DEFAULT_BINDER, NULL);
- GBinderRemoteReply* reply = gbinder_remote_reply_new(NULL);
+ GBinderObjectRegistry reg = { ®_dummy_fn, gbinder_driver_io(driver) };
+ GBinderRemoteReply* reply = gbinder_remote_reply_new(®);
gbinder_remote_reply_set_data(reply, gbinder_buffer_new(driver,
g_memdup(reply_data, sizeof(reply_data)), sizeof(reply_data), NULL));
@@ -187,7 +231,8 @@
'b', 'a', 'r', 0x00
};
GBinderDriver* driver = gbinder_driver_new(GBINDER_DEFAULT_BINDER, NULL);
- GBinderRemoteReply* reply = gbinder_remote_reply_new(NULL);
+ GBinderObjectRegistry reg = { ®_dummy_fn, gbinder_driver_io(driver) };
+ GBinderRemoteReply* reply = gbinder_remote_reply_new(®);
gbinder_remote_reply_set_data(reply, gbinder_buffer_new(driver,
g_memdup(reply_data, sizeof(reply_data)), sizeof(reply_data), NULL));
@@ -214,7 +259,8 @@
TEST_INT16_BYTES('r'), 0x00, 0x00
};
GBinderDriver* driver = gbinder_driver_new(GBINDER_DEFAULT_BINDER, NULL);
- GBinderRemoteReply* reply = gbinder_remote_reply_new(NULL);
+ GBinderObjectRegistry reg = { ®_dummy_fn, gbinder_driver_io(driver) };
+ GBinderRemoteReply* reply = gbinder_remote_reply_new(®);
char* str;
gbinder_remote_reply_set_data(reply, gbinder_buffer_new(driver,
@@ -238,7 +284,7 @@
test_to_local(
void)
{
- static const guint8 reply_data [] = {
+ static const guint8 reply_bytes [] = {
/* 32-bit integer */
TEST_INT32_BYTES(42),
/* 64-bit NULL flat_binder_object */
@@ -249,32 +295,33 @@
};
const char* dev = GBINDER_DEFAULT_BINDER;
GBinderDriver* driver = gbinder_driver_new(dev, NULL);
- GBinderRemoteReply* req = gbinder_remote_reply_new(NULL);
- GBinderLocalReply* req2;
+ GBinderObjectRegistry reg = { ®_dummy_fn, gbinder_driver_io(driver) };
+ GBinderRemoteReply* rr = gbinder_remote_reply_new(®);
+ GBinderLocalReply* lr;
GBinderOutputData* data;
const GByteArray* bytes;
GUtilIntArray* offsets;
- guint8* req_data = g_memdup(reply_data, sizeof(reply_data));
+ guint8* reply_data = g_memdup(reply_bytes, sizeof(reply_bytes));
void** objects = g_new0(void*, 2);
/* Skip the 32-bit integer */
- objects[0] = req_data + 4;
- gbinder_remote_reply_set_data(req, gbinder_buffer_new(driver, req_data,
- sizeof(reply_data), objects));
+ objects[0] = reply_data + 4;
+ gbinder_remote_reply_set_data(rr, gbinder_buffer_new(driver, reply_data,
+ sizeof(reply_bytes), objects));
/* Convert to GBinderLocalReply */
- req2 = gbinder_remote_reply_copy_to_local(req);
- data = gbinder_local_reply_data(req2);
+ lr = gbinder_remote_reply_copy_to_local(rr);
+ data = gbinder_local_reply_data(lr);
offsets = gbinder_output_data_offsets(data);
bytes = data->bytes;
g_assert(offsets);
g_assert(offsets->count == 1);
g_assert(offsets->data[0] == 4);
g_assert(!gbinder_output_data_buffers_size(data));
- g_assert(bytes->len == sizeof(reply_data));
+ g_assert(bytes->len == sizeof(reply_bytes));
- gbinder_remote_reply_unref(req);
- gbinder_local_reply_unref(req2);
+ gbinder_remote_reply_unref(rr);
+ gbinder_local_reply_unref(lr);
gbinder_driver_unref(driver);
}
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_remote_request/unit_remote_request.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018 Jolla Ltd.
- * Copyright (C) 2018 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -14,8 +14,8 @@
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the names of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -38,6 +38,7 @@
#include "gbinder_remote_request_p.h"
#include "gbinder_rpc_protocol.h"
#include "gbinder_local_request_p.h"
+#include "gbinder_object_converter.h"
#include "gbinder_output_data.h"
#include "gbinder_io.h"
@@ -54,6 +55,8 @@
TEST_INT32_BYTES(3), \
TEST_INT16_BYTES('f'), TEST_INT16_BYTES('o'), \
TEST_INT16_BYTES('o'), 0x00, 0x00
+#define HIDL_RPC_HEADER \
+ 'f', 'o', 'o', 0x00
#define BINDER_TYPE_BINDER GBINDER_FOURCC('s', 'b', '*', 0x85)
#define BINDER_OBJECT_SIZE_64 (GBINDER_MAX_BINDER_OBJECT_SIZE)
@@ -78,6 +81,7 @@
g_assert(gbinder_reader_at_end(&reader));
g_assert(!gbinder_remote_request_interface(NULL));
g_assert(!gbinder_remote_request_copy_to_local(NULL));
+ g_assert(!gbinder_remote_request_convert_to_local(NULL, NULL));
g_assert(gbinder_remote_request_sender_pid(NULL) == (pid_t)(-1));
g_assert(gbinder_remote_request_sender_euid(NULL) == (uid_t)(-1));
g_assert(!gbinder_remote_request_read_int32(NULL, NULL));
@@ -87,6 +91,7 @@
g_assert(!gbinder_remote_request_read_string8(NULL));
g_assert(!gbinder_remote_request_read_string16(NULL));
g_assert(!gbinder_remote_request_read_object(NULL));
+ g_assert(!gbinder_object_converter_handle_to_local(NULL, 0));
}
/*==========================================================================*
@@ -251,6 +256,15 @@
*==========================================================================*/
static
+GBinderLocalObject*
+test_to_local_convert_none(
+ GBinderObjectConverter* convert,
+ guint32 handle)
+{
+ return NULL;
+}
+
+static
void
test_to_local(
void)
@@ -265,10 +279,26 @@
TEST_INT64_BYTES(0), /* handle */
TEST_INT64_BYTES(0) /* cookie */
};
+ static const guint8 request_data_hidl [] = {
+ HIDL_RPC_HEADER,
+ /* 32-bit integer */
+ TEST_INT32_BYTES(42),
+ /* 64-bit NULL flat_binder_object */
+ TEST_INT32_BYTES(BINDER_TYPE_BINDER), /* hdr.type */
+ TEST_INT32_BYTES(0x17f), /* flags */
+ TEST_INT64_BYTES(0), /* handle */
+ TEST_INT64_BYTES(0) /* cookie */
+ };
+ static const GBinderObjectConverterFunctions convert_f = {
+ .handle_to_local = test_to_local_convert_none
+ };
const char* dev = GBINDER_DEFAULT_BINDER;
+ const char* dev2 = GBINDER_DEFAULT_HWBINDER;
GBinderDriver* driver = gbinder_driver_new(dev, NULL);
+ GBinderDriver* driver2 = gbinder_driver_new(dev2, NULL);
GBinderRemoteRequest* req = gbinder_remote_request_new(NULL,
gbinder_rpc_protocol_for_device(dev), 0, 0);
+ GBinderObjectConverter convert;
GBinderLocalRequest* req2;
GBinderOutputData* data;
const GByteArray* bytes;
@@ -293,10 +323,42 @@
g_assert(offsets->data[0] == 4);
g_assert(!gbinder_output_data_buffers_size(data));
g_assert(bytes->len == sizeof(request_data));
+ g_assert(!memcmp(request_data, bytes->data, bytes->len));
+ gbinder_local_request_unref(req2);
- gbinder_remote_request_unref(req);
+ /* The same with gbinder_remote_request_translate_to_local() */
+ req2 = gbinder_remote_request_convert_to_local(req, NULL);
+ data = gbinder_local_request_data(req2);
+ offsets = gbinder_output_data_offsets(data);
+ bytes = data->bytes;
+ g_assert(offsets);
+ g_assert(offsets->count == 1);
+ g_assert(offsets->data[0] == 4);
+ g_assert(!gbinder_output_data_buffers_size(data));
+ g_assert(bytes->len == sizeof(request_data));
+ g_assert(!memcmp(request_data, bytes->data, bytes->len));
gbinder_local_request_unref(req2);
+
+ /* Different driver actually requires translation */
+ memset(&convert, 0, sizeof(convert));
+ convert.f = &convert_f;
+ convert.io = gbinder_driver_io(driver2);
+ convert.protocol = gbinder_driver_protocol(driver2);
+ req2 = gbinder_remote_request_convert_to_local(req, &convert);
+ data = gbinder_local_request_data(req2);
+ offsets = gbinder_output_data_offsets(data);
+ bytes = data->bytes;
+ g_assert(offsets);
+ g_assert(offsets->count == 1);
+ g_assert(offsets->data[0] == 4);
+ g_assert(!gbinder_output_data_buffers_size(data));
+ g_assert(bytes->len == sizeof(request_data_hidl));
+ g_assert(!memcmp(request_data_hidl, bytes->data, bytes->len));
+ gbinder_local_request_unref(req2);
+
+ gbinder_remote_request_unref(req);
gbinder_driver_unref(driver);
+ gbinder_driver_unref(driver2);
}
/*==========================================================================*
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_servicemanager/unit_servicemanager.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -34,10 +34,12 @@
#include "gbinder_driver.h"
#include "gbinder_client_p.h"
+#include "gbinder_config.h"
#include "gbinder_remote_object_p.h"
#include "gbinder_ipc.h"
#include "gbinder_local_object_p.h"
#include "gbinder_servicemanager_p.h"
+#include "gbinder_object_registry.h"
#include "gbinder_rpc_protocol.h"
#include <gutil_strv.h>
@@ -47,6 +49,7 @@
#include <errno.h>
static TestOpt test_opt;
+static const char TMP_DIR_TEMPLATE[] = "gbinder-test-servicemanager-XXXXXX";
static
void
@@ -155,7 +158,8 @@
static
char**
test_servicemanager_list(
- GBinderServiceManager* sm)
+ GBinderServiceManager* sm,
+ const GBinderIpcSyncApi* api)
{
TestServiceManager* self = TEST_SERVICEMANAGER(sm);
@@ -167,14 +171,16 @@
test_servicemanager_get_service(
GBinderServiceManager* sm,
const char* name,
- int* status)
+ int* status,
+ const GBinderIpcSyncApi* api)
{
TestServiceManager* self = TEST_SERVICEMANAGER(sm);
if (gutil_strv_contains(self->services, name)) {
if (!self->remote) {
- self->remote = gbinder_ipc_get_remote_object
- (gbinder_client_ipc(sm->client), 1, TRUE);
+ self->remote = gbinder_object_registry_get_remote
+ (gbinder_ipc_object_registry(gbinder_client_ipc(sm->client)),
+ 1, TRUE);
}
*status = GBINDER_STATUS_OK;
return gbinder_remote_object_ref(self->remote);
@@ -189,7 +195,8 @@
test_servicemanager_add_service(
GBinderServiceManager* sm,
const char* name,
- GBinderLocalObject* obj)
+ GBinderLocalObject* obj,
+ const GBinderIpcSyncApi* api)
{
TestServiceManager* self = TEST_SERVICEMANAGER(sm);
@@ -224,7 +231,7 @@
{
TestHwServiceManager* self = TEST_HWSERVICEMANAGER(sm);
- return (!name || self->reject_name) ?
+ return (!name || self->reject_name) ?
GBINDER_SERVICEMANAGER_NAME_INVALID :
GBINDER_SERVICEMANAGER_NAME_NORMALIZE;
}
@@ -281,7 +288,6 @@
{
klass->iface = TEST_HWSERVICEMANAGER_IFACE;
klass->default_device = GBINDER_DEFAULT_HWBINDER;
- klass->rpc_protocol = &gbinder_rpc_protocol_hwbinder;
klass->list = test_servicemanager_list;
klass->get_service = test_servicemanager_get_service;
klass->add_service = test_servicemanager_add_service;
@@ -292,12 +298,10 @@
G_OBJECT_CLASS(klass)->finalize = test_hwservicemanager_finalize;
}
-GBinderServiceManager*
-gbinder_hwservicemanager_new(
- const char* dev)
+GType
+gbinder_servicemanager_hidl_get_type()
{
- return gbinder_servicemanager_new_with_type(TEST_TYPE_HWSERVICEMANAGER,
- dev);
+ return TEST_TYPE_HWSERVICEMANAGER;
}
/*==========================================================================*
@@ -325,7 +329,7 @@
{
TestDefServiceManager* self = TEST_DEFSERVICEMANAGER(sm);
- return (!name || self->reject_name) ?
+ return (!name || self->reject_name) ?
GBINDER_SERVICEMANAGER_NAME_INVALID :
GBINDER_SERVICEMANAGER_NAME_OK;
}
@@ -365,7 +369,6 @@
{
klass->iface = TEST_DEFSERVICEMANAGER_IFACE;
klass->default_device = GBINDER_DEFAULT_BINDER;
- klass->rpc_protocol = &gbinder_rpc_protocol_binder;
klass->list = test_servicemanager_list;
klass->get_service = test_servicemanager_get_service;
klass->add_service = test_servicemanager_add_service;
@@ -374,12 +377,17 @@
G_OBJECT_CLASS(klass)->finalize = test_defservicemanager_finalize;
}
-GBinderServiceManager*
-gbinder_defaultservicemanager_new(
- const char* dev)
+GType
+gbinder_servicemanager_aidl_get_type()
{
- return gbinder_servicemanager_new_with_type(TEST_TYPE_DEFSERVICEMANAGER,
- dev);
+ return TEST_TYPE_DEFSERVICEMANAGER;
+}
+
+GType
+gbinder_servicemanager_aidl2_get_type()
+{
+ /* Avoid pulling in gbinder_servicemanager_aidl2 object */
+ return TEST_TYPE_DEFSERVICEMANAGER;
}
/*==========================================================================*
@@ -391,6 +399,7 @@
test_null(
void)
{
+ g_assert(!gbinder_servicemanager_new(NULL));
g_assert(!gbinder_servicemanager_new_with_type(0, NULL));
g_assert(!gbinder_servicemanager_new_local_object(NULL, NULL, NULL, NULL));
g_assert(!gbinder_servicemanager_ref(NULL));
@@ -423,7 +432,7 @@
{
int status = 0;
const char* dev = GBINDER_DEFAULT_HWBINDER;
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GBinderServiceManager* sm;
gulong id = 0;
@@ -466,9 +475,9 @@
void
test_basic(
void)
-{
+{
const char* dev = GBINDER_DEFAULT_HWBINDER;
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GBinderServiceManager* sm;
GBinderLocalObject* obj;
@@ -484,6 +493,124 @@
gbinder_servicemanager_unref(sm);
gbinder_servicemanager_unref(sm);
gbinder_ipc_unref(ipc);
+ gbinder_ipc_exit();
+}
+
+/*==========================================================================*
+ * legacy
+ *==========================================================================*/
+
+static
+void
+test_legacy(
+ void)
+{
+ const char* otherdev = "/dev/otherbinder";
+ const char* dev = GBINDER_DEFAULT_HWBINDER;
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
+ GBinderServiceManager* sm;
+
+ /* Reset the state */
+ gbinder_servicemanager_exit();
+ gbinder_config_exit();
+ gbinder_config_file = NULL;
+
+ test_setup_ping(ipc);
+ sm = gbinder_hwservicemanager_new(dev);
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_servicemanager_aidl/Makefile
^
|
@@ -0,0 +1,5 @@
+# -*- Mode: makefile-gmake -*-
+
+EXE = unit_servicemanager_aidl
+
+include ../common/Makefile
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_servicemanager_aidl/unit_servicemanager_aidl.c
^
|
@@ -0,0 +1,613 @@
+/*
+ * Copyright (C) 2020-2021 Jolla Ltd.
+ * Copyright (C) 2020-2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "test_binder.h"
+
+#include "gbinder_driver.h"
+#include "gbinder_ipc.h"
+#include "gbinder_reader.h"
+#include "gbinder_servicemanager_p.h"
+#include "gbinder_rpc_protocol.h"
+#include "gbinder_local_object_p.h"
+#include "gbinder_local_reply.h"
+#include "gbinder_remote_request.h"
+#include "gbinder_remote_object.h"
+
+#include <gutil_strv.h>
+#include <gutil_log.h>
+
+static TestOpt test_opt;
+
+GType
+gbinder_servicemanager_hidl_get_type()
+{
+ /* Avoid pulling in gbinder_servicemanager_hidl object */
+ return 0;
+}
+
+GType
+gbinder_servicemanager_aidl2_get_type()
+{
+ /* Avoid pulling in gbinder_servicemanager_aidl2 object */
+ return 0;
+}
+
+/*==========================================================================*
+ * Test service manager
+ *==========================================================================*/
+
+#define SVCMGR_HANDLE (0)
+static const char SVCMGR_IFACE[] = "android.os.IServiceManager";
+enum servicemanager_aidl_tx {
+ GET_SERVICE_TRANSACTION = GBINDER_FIRST_CALL_TRANSACTION,
+ CHECK_SERVICE_TRANSACTION,
+ ADD_SERVICE_TRANSACTION,
+ LIST_SERVICES_TRANSACTION
+};
+
+const char* const servicemanager_aidl_ifaces[] = { SVCMGR_IFACE, NULL };
+
+typedef GBinderLocalObjectClass ServiceManagerAidlClass;
+typedef struct service_manager_aidl {
+ GBinderLocalObject parent;
+ GHashTable* objects;
+ gboolean handle_on_looper_thread;
+} ServiceManagerAidl;
+
+#define SERVICE_MANAGER_AIDL_TYPE (service_manager_aidl_get_type())
+#define SERVICE_MANAGER_AIDL(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), \
+ SERVICE_MANAGER_AIDL_TYPE, ServiceManagerAidl))
+G_DEFINE_TYPE(ServiceManagerAidl, service_manager_aidl, \
+ GBINDER_TYPE_LOCAL_OBJECT)
+
+static
+GBinderLocalReply*
+servicemanager_aidl_handler(
+ GBinderLocalObject* obj,
+ GBinderRemoteRequest* req,
+ guint code,
+ guint flags,
+ int* status,
+ void* user_data)
+{
+ ServiceManagerAidl* self = user_data;
+ GBinderLocalReply* reply = NULL;
+ GBinderReader reader;
+ GBinderRemoteObject* remote_obj;
+ guint32 num;
+ char* str;
+
+ g_assert(!flags);
+ g_assert_cmpstr(gbinder_remote_request_interface(req), == ,SVCMGR_IFACE);
+ *status = -1;
+ switch (code) {
+ case GET_SERVICE_TRANSACTION:
+ case CHECK_SERVICE_TRANSACTION:
+ gbinder_remote_request_init_reader(req, &reader);
+ str = gbinder_reader_read_string16(&reader);
+ if (str) {
+ reply = gbinder_local_object_new_reply(obj);
+ remote_obj = g_hash_table_lookup(self->objects, str);
+ if (remote_obj) {
+ GDEBUG("Found name '%s' => %p", str, remote_obj);
+ gbinder_local_reply_append_remote_object(reply, remote_obj);
+ } else {
+ GDEBUG("Name '%s' not found", str);
+ gbinder_local_reply_append_int32(reply, GBINDER_STATUS_OK);
+ }
+ g_free(str);
+ }
+ break;
+ case ADD_SERVICE_TRANSACTION:
+ gbinder_remote_request_init_reader(req, &reader);
+ str = gbinder_reader_read_string16(&reader);
+ remote_obj = gbinder_reader_read_object(&reader);
+ if (str && remote_obj && gbinder_reader_read_uint32(&reader, &num)) {
+ GDEBUG("Adding '%s'", str);
+ g_hash_table_replace(self->objects, str, remote_obj);
+ remote_obj = NULL;
+ str = NULL;
+ reply = gbinder_local_object_new_reply(obj);
+ *status = GBINDER_STATUS_OK;
+ }
+ g_free(str);
+ gbinder_remote_object_unref(remote_obj);
+ break;
+ case LIST_SERVICES_TRANSACTION:
+ if (gbinder_remote_request_read_uint32(req, &num)) {
+ if (num < g_hash_table_size(self->objects)) {
+ GList* keys = g_hash_table_get_keys(self->objects);
+ GList* l = g_list_nth(keys, num);
+
+ reply = gbinder_local_object_new_reply(obj);
+ gbinder_local_reply_append_string16(reply, l->data);
+ g_list_free(keys);
+ *status = GBINDER_STATUS_OK;
+ } else {
+ GDEBUG("Index %u out of bounds", num);
+ }
+ }
+ break;
+ default:
+ GDEBUG("Unhandled command %u", code);
+ break;
+ }
+ return reply;
+}
+
+static
+ServiceManagerAidl*
+servicemanager_aidl_new(
+ const char* dev,
+ gboolean handle_on_looper_thread)
+{
+ ServiceManagerAidl* self = g_object_new(SERVICE_MANAGER_AIDL_TYPE, NULL);
+ GBinderLocalObject* obj = GBINDER_LOCAL_OBJECT(self);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
+ const int fd = gbinder_driver_fd(ipc->driver);
+
+ self->handle_on_looper_thread = handle_on_looper_thread;
+ gbinder_local_object_init_base(obj, ipc, servicemanager_aidl_ifaces,
+ servicemanager_aidl_handler, self);
+ test_binder_set_looper_enabled(fd, TEST_LOOPER_ENABLE);
+ test_binder_register_object(fd, obj, SVCMGR_HANDLE);
+ gbinder_ipc_register_local_object(ipc, obj);
+ gbinder_ipc_unref(ipc);
+ return self;
+}
+
+static
+void
+servicemanager_aidl_free(
+ ServiceManagerAidl* self)
+{
+ gbinder_local_object_drop(GBINDER_LOCAL_OBJECT(self));
+}
+
+static
+GBINDER_LOCAL_TRANSACTION_SUPPORT
+service_manager_aidl_can_handle_transaction(
+ GBinderLocalObject* object,
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_servicemanager_aidl2/Makefile
^
|
@@ -0,0 +1,5 @@
+# -*- Mode: makefile-gmake -*-
+
+EXE = unit_servicemanager_aidl2
+
+include ../common/Makefile
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_servicemanager_aidl2/unit_servicemanager_aidl2.c
^
|
@@ -0,0 +1,451 @@
+/*
+ * Copyright (C) 2020-2021 Jolla Ltd.
+ * Copyright (C) 2020-2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "test_binder.h"
+
+#include "gbinder_driver.h"
+#include "gbinder_config.h"
+#include "gbinder_ipc.h"
+#include "gbinder_reader.h"
+#include "gbinder_servicemanager_p.h"
+#include "gbinder_rpc_protocol.h"
+#include "gbinder_local_object_p.h"
+#include "gbinder_local_reply.h"
+#include "gbinder_remote_request.h"
+#include "gbinder_remote_object.h"
+
+#include <gutil_strv.h>
+#include <gutil_log.h>
+
+static TestOpt test_opt;
+static const char TMP_DIR_TEMPLATE[] =
+ "gbinder-test-servicemanager_aidl2-XXXXXX";
+
+GType
+gbinder_servicemanager_hidl_get_type()
+{
+ /* Avoid pulling in gbinder_servicemanager_hidl object */
+ return 0;
+}
+
+/*==========================================================================*
+ * Test service manager
+ *==========================================================================*/
+
+#define SVCMGR_HANDLE (0)
+static const char SVCMGR_IFACE[] = "android.os.IServiceManager";
+enum servicemanager_aidl_tx {
+ GET_SERVICE_TRANSACTION = GBINDER_FIRST_CALL_TRANSACTION,
+ CHECK_SERVICE_TRANSACTION,
+ ADD_SERVICE_TRANSACTION,
+ LIST_SERVICES_TRANSACTION
+};
+
+const char* const servicemanager_aidl_ifaces[] = { SVCMGR_IFACE, NULL };
+
+typedef GBinderLocalObjectClass ServiceManagerAidl2Class;
+typedef struct service_manager_aidl2 {
+ GBinderLocalObject parent;
+ GHashTable* objects;
+ gboolean handle_on_looper_thread;
+} ServiceManagerAidl2;
+
+#define SERVICE_MANAGER_AIDL2_TYPE (service_manager_aidl2_get_type())
+#define SERVICE_MANAGER_AIDL2(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), \
+ SERVICE_MANAGER_AIDL2_TYPE, ServiceManagerAidl2))
+G_DEFINE_TYPE(ServiceManagerAidl2, service_manager_aidl2, \
+ GBINDER_TYPE_LOCAL_OBJECT)
+
+static
+GBinderLocalReply*
+servicemanager_aidl2_handler(
+ GBinderLocalObject* obj,
+ GBinderRemoteRequest* req,
+ guint code,
+ guint flags,
+ int* status,
+ void* user_data)
+{
+ ServiceManagerAidl2* self = user_data;
+ GBinderLocalReply* reply = NULL;
+ GBinderReader reader;
+ GBinderRemoteObject* remote_obj;
+ guint32 num, allow_isolated, dumpsys_priority;
+ char* str;
+
+ g_assert(!flags);
+ GDEBUG("%s %u", gbinder_remote_request_interface(req), code);
+ g_assert_cmpstr(gbinder_remote_request_interface(req), == ,SVCMGR_IFACE);
+ *status = -1;
+ switch (code) {
+ case GET_SERVICE_TRANSACTION:
+ case CHECK_SERVICE_TRANSACTION:
+ gbinder_remote_request_init_reader(req, &reader);
+ str = gbinder_reader_read_string16(&reader);
+ if (str) {
+ reply = gbinder_local_object_new_reply(obj);
+ remote_obj = g_hash_table_lookup(self->objects, str);
+ if (remote_obj) {
+ GDEBUG("Found name '%s' => %p", str, remote_obj);
+ gbinder_local_reply_append_remote_object(reply, remote_obj);
+ } else {
+ GDEBUG("Name '%s' not found", str);
+ gbinder_local_reply_append_int32(reply, GBINDER_STATUS_OK);
+ }
+ g_free(str);
+ }
+ break;
+ case ADD_SERVICE_TRANSACTION:
+ gbinder_remote_request_init_reader(req, &reader);
+ str = gbinder_reader_read_string16(&reader);
+ remote_obj = gbinder_reader_read_object(&reader);
+ if (str && remote_obj &&
+ gbinder_reader_read_uint32(&reader, &allow_isolated) &&
+ gbinder_reader_read_uint32(&reader, &dumpsys_priority)) {
+ GDEBUG("Adding '%s'", str);
+ g_hash_table_replace(self->objects, str, remote_obj);
+ remote_obj = NULL;
+ str = NULL;
+ reply = gbinder_local_object_new_reply(obj);
+ *status = GBINDER_STATUS_OK;
+ }
+ g_free(str);
+ gbinder_remote_object_unref(remote_obj);
+ break;
+ case LIST_SERVICES_TRANSACTION:
+ gbinder_remote_request_init_reader(req, &reader);
+ if (gbinder_reader_read_uint32(&reader, &num) &&
+ gbinder_reader_read_uint32(&reader, &dumpsys_priority)) {
+ if (num < g_hash_table_size(self->objects)) {
+ GList* keys = g_hash_table_get_keys(self->objects);
+ GList* l = g_list_nth(keys, num);
+
+ /* Ignore dumpsys_priority */
+ reply = gbinder_local_object_new_reply(obj);
+ gbinder_local_reply_append_string16(reply, l->data);
+ g_list_free(keys);
+ *status = GBINDER_STATUS_OK;
+ } else {
+ GDEBUG("Index %u out of bounds", num);
+ }
+ }
+ break;
+ default:
+ GDEBUG("Unhandled command %u", code);
+ break;
+ }
+ return reply;
+}
+
+static
+ServiceManagerAidl2*
+servicemanager_aidl2_new(
+ const char* dev,
+ gboolean handle_on_looper_thread)
+{
+ ServiceManagerAidl2* self = g_object_new(SERVICE_MANAGER_AIDL2_TYPE, NULL);
+ GBinderLocalObject* obj = GBINDER_LOCAL_OBJECT(self);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
+ const int fd = gbinder_driver_fd(ipc->driver);
+
+ self->handle_on_looper_thread = handle_on_looper_thread;
+ gbinder_local_object_init_base(obj, ipc, servicemanager_aidl_ifaces,
+ servicemanager_aidl2_handler, self);
+ test_binder_set_looper_enabled(fd, TEST_LOOPER_ENABLE);
+ test_binder_register_object(fd, obj, SVCMGR_HANDLE);
+ gbinder_ipc_register_local_object(ipc, obj);
+ gbinder_ipc_unref(ipc);
+ return self;
+}
+
+static
+GBINDER_LOCAL_TRANSACTION_SUPPORT
+service_manager_aidl2_can_handle_transaction(
+ GBinderLocalObject* object,
+ const char* iface,
+ guint code)
+{
+ ServiceManagerAidl2* self = SERVICE_MANAGER_AIDL2(object);
+
+ if (self->handle_on_looper_thread && !g_strcmp0(SVCMGR_IFACE, iface)) {
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_servicemanager_hidl/Makefile
^
|
@@ -0,0 +1,6 @@
+# -*- Mode: makefile-gmake -*-
+
+EXE = unit_servicemanager_hidl
+COMMON_SRC = test_binder.c test_main.c test_servicemanager_hidl.c
+
+include ../common/Makefile
|
[-]
[+]
|
Added |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_servicemanager_hidl/unit_servicemanager_hidl.c
^
|
@@ -0,0 +1,481 @@
+/*
+ * Copyright (C) 2021 Jolla Ltd.
+ * Copyright (C) 2021 Slava Monich <slava.monich@jolla.com>
+ *
+ * You may use this file under the terms of BSD license as follows:
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the names of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "test_binder.h"
+#include "test_servicemanager_hidl.h"
+
+#include "gbinder_ipc.h"
+#include "gbinder_config.h"
+#include "gbinder_driver.h"
+#include "gbinder_servicemanager_p.h"
+#include "gbinder_local_object_p.h"
+
+#include <gutil_log.h>
+#include <gutil_strv.h>
+
+static TestOpt test_opt;
+#define MAIN_DEV GBINDER_DEFAULT_HWBINDER
+#define OTHER_DEV GBINDER_DEFAULT_HWBINDER "-private"
+static const char TMP_DIR_TEMPLATE[] = "gbinder-test-svcmgr-hidl-XXXXXX";
+static const char DEFAULT_CONFIG_DATA[] =
+ "[Protocol]\n"
+ MAIN_DEV " = hidl\n"
+ OTHER_DEV " = hidl\n"
+ "[ServiceManager]\n"
+ MAIN_DEV " = hidl\n";
+
+typedef struct test_config {
+ char* dir;
+ char* file;
+} TestConfig;
+
+GType
+gbinder_servicemanager_aidl_get_type()
+{
+ /* Avoid pulling in gbinder_servicemanager_aidl object */
+ return 0;
+}
+
+GType
+gbinder_servicemanager_aidl2_get_type()
+{
+ /* Avoid pulling in gbinder_servicemanager_aidl2 object */
+ return 0;
+}
+
+/*==========================================================================*
+ * Common
+ *==========================================================================*/
+
+static
+void
+test_config_init(
+ TestConfig* config,
+ char* config_data)
+{
+ config->dir = g_dir_make_tmp(TMP_DIR_TEMPLATE, NULL);
+ config->file = g_build_filename(config->dir, "test.conf", NULL);
+ g_assert(g_file_set_contents(config->file, config_data ? config_data :
+ DEFAULT_CONFIG_DATA, -1, NULL));
+
+ gbinder_config_exit();
+ gbinder_config_dir = config->dir;
+ gbinder_config_file = config->file;
+ GDEBUG("Wrote config to %s", config->file);
+}
+
+static
+void
+test_config_deinit(
+ TestConfig* config)
+{
+ gbinder_config_exit();
+
+ remove(config->file);
+ g_free(config->file);
+
+ remove(config->dir);
+ g_free(config->dir);
+}
+
+static
+TestServiceManagerHidl*
+test_servicemanager_impl_new(
+ const char* dev)
+{
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
+ const int fd = gbinder_driver_fd(ipc->driver);
+ TestServiceManagerHidl* sm = test_servicemanager_hidl_new(ipc);
+
+ test_binder_set_looper_enabled(fd, TEST_LOOPER_ENABLE);
+ test_binder_register_object(fd, GBINDER_LOCAL_OBJECT(sm),
+ GBINDER_SERVICEMANAGER_HANDLE);
+ gbinder_ipc_unref(ipc);
+ return sm;
+}
+
+/*==========================================================================*
+ * get
+ *==========================================================================*/
+
+static
+void
+test_add_cb(
+ GBinderServiceManager* sm,
+ int status,
+ void* user_data)
+{
+ GDEBUG("Name added");
+ g_assert(status == GBINDER_STATUS_OK);
+ if (user_data) {
+ g_main_loop_quit(user_data);
+ }
+}
+
+static
+void
+test_get_none_cb(
+ GBinderServiceManager* sm,
+ GBinderRemoteObject* obj,
+ int status,
+ void* user_data)
+{
+ g_assert(!obj);
+ g_assert(status == GBINDER_STATUS_OK);
+ g_main_loop_quit(user_data);
+}
+
+static
+void
+test_get_cb(
+ GBinderServiceManager* sm,
+ GBinderRemoteObject* obj,
+ int status,
+ void* user_data)
+{
+ g_assert(obj);
+ g_assert(status == GBINDER_STATUS_OK);
+ g_main_loop_quit(user_data);
+}
+
+static
+void
+test_get_run()
+{
+ TestConfig config;
+ GBinderIpc* ipc;
+ TestServiceManagerHidl* smsvc;
+ GBinderLocalObject* obj;
+ int fd;
+ GBinderServiceManager* sm;
+ GMainLoop* loop = g_main_loop_new(NULL, FALSE);
+ const char* name = "android.hidl.base@1.0::IBase/test";
+
+ test_config_init(&config, NULL);
+ ipc = gbinder_ipc_new(MAIN_DEV);
+ smsvc = test_servicemanager_impl_new(OTHER_DEV);
+ obj = gbinder_local_object_new(ipc, NULL, NULL, NULL);
+ fd = gbinder_driver_fd(ipc->driver);
+
+ /* Set up binder simulator */
+ test_binder_register_object(fd, obj, AUTO_HANDLE);
+ test_binder_set_passthrough(fd, TRUE);
+ test_binder_set_looper_enabled(fd, TEST_LOOPER_ENABLE);
+ sm = gbinder_servicemanager_new(MAIN_DEV);
+
+ /* This one fails because of unexpected name format */
+ g_assert(!gbinder_servicemanager_get_service_sync(sm, "test", NULL));
+
+ /* Query the object (it's not there yet) and wait for completion */
+ GDEBUG("Querying '%s'", name);
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_servicename/unit_servicename.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2019 Jolla Ltd.
- * Copyright (C) 2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2019-2021 Jolla Ltd.
+ * Copyright (C) 2019-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -34,7 +34,7 @@
#include "gbinder_servicename.h"
#include "gbinder_servicemanager_p.h"
-#include "gbinder_local_object.h"
+#include "gbinder_local_object_p.h"
#include "gbinder_rpc_protocol.h"
#include "gbinder_driver.h"
#include "gbinder_ipc.h"
@@ -57,15 +57,6 @@
static
void
-test_quit_when_destroyed(
- gpointer loop,
- GObject* obj)
-{
- test_quit_later((GMainLoop*)loop);
-}
-
-static
-void
test_setup_ping(
GBinderIpc* ipc)
{
@@ -87,6 +78,7 @@
GMutex mutex;
char** services;
gboolean block_add;
+ int add_fail;
int add_result;
} TestServiceManager;
@@ -101,7 +93,8 @@
static
char**
test_servicemanager_list(
- GBinderServiceManager* manager)
+ GBinderServiceManager* manager,
+ const GBinderIpcSyncApi* api)
{
char** ret;
TestServiceManager* self = TEST_SERVICEMANAGER(manager);
@@ -118,7 +111,8 @@
test_servicemanager_get_service(
GBinderServiceManager* manager,
const char* name,
- int* status)
+ int* status,
+ const GBinderIpcSyncApi* api)
{
*status = (-ENOENT);
return NULL;
@@ -129,19 +123,34 @@
test_servicemanager_add_service(
GBinderServiceManager* manager,
const char* name,
- GBinderLocalObject* obj)
+ GBinderLocalObject* obj,
+ const GBinderIpcSyncApi* api)
{
TestServiceManager* self = TEST_SERVICEMANAGER(manager);
+ int result;
g_mutex_lock(&self->mutex);
- if (!gutil_strv_contains(self->services, name)) {
- self->services = gutil_strv_add(self->services, name);
- }
- while (self->block_add) {
- g_cond_wait(&self->cond, &self->mutex);
+ if (self->add_fail > 0) {
+ self->add_fail--;
+ result = -EFAULT;
+ } else {
+ result = self->add_result;
+ if (result == GBINDER_STATUS_OK) {
+ if (!gutil_strv_contains(self->services, name)) {
+ self->services = gutil_strv_add(self->services, name);
+ }
+ if (self->block_add) {
+ while (self->block_add) {
+ g_cond_wait(&self->cond, &self->mutex);
+ }
+ } else {
+ test_binder_br_dead_binder(gbinder_driver_fd(obj->ipc->driver),
+ GBINDER_SERVICEMANAGER_HANDLE);
+ }
+ }
}
g_mutex_unlock(&self->mutex);
- return self->add_result;
+ return result;
}
static
@@ -202,7 +211,6 @@
{
klass->iface = TEST_SERVICEMANAGER_IFACE;
klass->default_device = GBINDER_DEFAULT_HWBINDER;
- klass->rpc_protocol = &gbinder_rpc_protocol_binder;
klass->list = test_servicemanager_list;
klass->get_service = test_servicemanager_get_service;
klass->add_service = test_servicemanager_add_service;
@@ -212,18 +220,24 @@
G_OBJECT_CLASS(klass)->finalize = test_servicemanager_finalize;
}
-GBinderServiceManager*
-gbinder_defaultservicemanager_new(
- const char* dev)
+/* Avoid pulling in the actual objects */
+
+GType
+gbinder_servicemanager_aidl_get_type()
+{
+ return TEST_TYPE_SERVICEMANAGER;
+}
+
+GType
+gbinder_servicemanager_aidl2_get_type()
{
- return gbinder_servicemanager_new_with_type(TEST_TYPE_SERVICEMANAGER, dev);
+ return TEST_TYPE_SERVICEMANAGER;
}
-GBinderServiceManager*
-gbinder_hwservicemanager_new(
- const char* dev)
+GType
+gbinder_servicemanager_hidl_get_type()
{
- return gbinder_servicemanager_new(dev);
+ return TEST_TYPE_SERVICEMANAGER;
}
/*==========================================================================*
@@ -236,7 +250,7 @@
void)
{
const char* dev = GBINDER_DEFAULT_BINDER;
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GBinderServiceManager* sm;
test_setup_ping(ipc);
@@ -263,7 +277,7 @@
const char* obj_name = "test";
const char* dev = GBINDER_DEFAULT_BINDER;
const char* const ifaces[] = { "interface", NULL };
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GMainLoop* loop = g_main_loop_new(NULL, FALSE);
GBinderLocalObject* obj;
GBinderServiceManager* sm;
@@ -276,7 +290,7 @@
sn = gbinder_servicename_new(sm, obj, obj_name);
g_assert(sn);
- g_assert(!g_strcmp0(sn->name, obj_name));
+ g_assert_cmpstr(sn->name, == ,obj_name);
g_assert(gbinder_servicename_ref(sn) == sn);
gbinder_servicename_unref(sn);
@@ -284,13 +298,8 @@
gbinder_servicename_unref(sn);
gbinder_local_object_unref(obj);
gbinder_servicemanager_unref(sm);
-
- /* We need to wait until GBinderIpc is destroyed */
- GDEBUG("waiting for GBinderIpc to get destroyed");
- g_object_weak_ref(G_OBJECT(ipc), test_quit_when_destroyed, loop);
gbinder_ipc_unref(ipc);
- test_run(&test_opt, loop);
-
+ gbinder_ipc_exit();
g_main_loop_unref(loop);
}
@@ -306,7 +315,7 @@
const char* obj_name = "test";
const char* const ifaces[] = { "interface", NULL };
const char* dev = GBINDER_DEFAULT_BINDER;
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
const int fd = gbinder_driver_fd(ipc->driver);
GMainLoop* loop = g_main_loop_new(NULL, FALSE);
GBinderLocalObject* obj;
@@ -321,10 +330,10 @@
sn = gbinder_servicename_new(sm, obj, obj_name);
g_assert(sn);
|
[-]
[+]
|
Changed |
_service:tar_git:libgbinder-1.1.10.tar.bz2/unit/unit_servicepoll/unit_servicepoll.c
^
|
@@ -1,6 +1,6 @@
/*
- * Copyright (C) 2018-2019 Jolla Ltd.
- * Copyright (C) 2018-2019 Slava Monich <slava.monich@jolla.com>
+ * Copyright (C) 2018-2021 Jolla Ltd.
+ * Copyright (C) 2018-2021 Slava Monich <slava.monich@jolla.com>
*
* You may use this file under the terms of BSD license as follows:
*
@@ -79,7 +79,8 @@
static
char**
test_servicemanager_list(
- GBinderServiceManager* manager)
+ GBinderServiceManager* manager,
+ const GBinderIpcSyncApi* api)
{
char** ret;
TestServiceManager* self = TEST_SERVICEMANAGER(manager);
@@ -96,7 +97,8 @@
test_servicemanager_get_service(
GBinderServiceManager* manager,
const char* name,
- int* status)
+ int* status,
+ const GBinderIpcSyncApi* api)
{
*status = (-ENOENT);
return NULL;
@@ -107,7 +109,8 @@
test_servicemanager_add_service(
GBinderServiceManager* manager,
const char* name,
- GBinderLocalObject* obj)
+ GBinderLocalObject* obj,
+ const GBinderIpcSyncApi* api)
{
TestServiceManager* self = TEST_SERVICEMANAGER(manager);
@@ -174,7 +177,6 @@
{
klass->iface = TEST_SERVICEMANAGER_IFACE;
klass->default_device = GBINDER_DEFAULT_HWBINDER;
- klass->rpc_protocol = &gbinder_rpc_protocol_binder;
klass->list = test_servicemanager_list;
klass->get_service = test_servicemanager_get_service;
klass->add_service = test_servicemanager_add_service;
@@ -184,18 +186,24 @@
G_OBJECT_CLASS(klass)->finalize = test_servicemanager_finalize;
}
-GBinderServiceManager*
-gbinder_defaultservicemanager_new(
- const char* dev)
+/* Avoid pulling in the actual objects */
+
+GType
+gbinder_servicemanager_aidl_get_type()
+{
+ return TEST_TYPE_SERVICEMANAGER;
+}
+
+GType
+gbinder_servicemanager_aidl2_get_type()
{
- return gbinder_servicemanager_new_with_type(TEST_TYPE_SERVICEMANAGER, dev);
+ return TEST_TYPE_SERVICEMANAGER;
}
-GBinderServiceManager*
-gbinder_hwservicemanager_new(
- const char* dev)
+GType
+gbinder_servicemanager_hidl_get_type()
{
- return gbinder_servicemanager_new(dev);
+ return TEST_TYPE_SERVICEMANAGER;
}
/*==========================================================================*
@@ -225,7 +233,7 @@
void)
{
const char* dev = GBINDER_DEFAULT_BINDER;
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GBinderServicePoll* weakptr = NULL;
GBinderServiceManager* manager;
GBinderServicePoll* poll;
@@ -301,7 +309,7 @@
void)
{
const char* dev = GBINDER_DEFAULT_BINDER;
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GMainLoop* loop = g_main_loop_new(NULL, FALSE);
GBinderServicePoll* weakptr = NULL;
GBinderServiceManager* manager;
@@ -375,7 +383,7 @@
void)
{
const char* dev = GBINDER_DEFAULT_BINDER;
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GMainLoop* loop = g_main_loop_new(NULL, FALSE);
GBinderServicePoll* weakptr = NULL;
GBinderServiceManager* manager;
@@ -434,7 +442,7 @@
void)
{
const char* dev = GBINDER_DEFAULT_BINDER;
- GBinderIpc* ipc = gbinder_ipc_new(dev, NULL);
+ GBinderIpc* ipc = gbinder_ipc_new(dev);
GMainLoop* loop = g_main_loop_new(NULL, FALSE);
GBinderServicePoll* weakptr = NULL;
GBinderServiceManager* manager;
|