virtual: add get_available_modes and set_mode protocol. 53/187453/2
authorJunkyeong Kim <jk0430.kim@samsung.com>
Thu, 23 Aug 2018 09:02:10 +0000 (18:02 +0900)
committerJunkyeong Kim <jk0430.kim@samsung.com>
Fri, 24 Aug 2018 09:10:21 +0000 (18:10 +0900)
add tc for tdm_client_output_get_available_modes.

Change-Id: Id5a4616b89ecf0c4b8a3f853f6a37fd27049f3e1
Signed-off-by: Junkyeong Kim <jk0430.kim@samsung.com>
client/tdm_client.c
client/tdm_client.h
haltests/src/tc_tdm_client.cpp
protocol/tdm.xml
src/tdm_server.c

index a187cb6..f5c69db 100644 (file)
@@ -95,6 +95,11 @@ typedef struct _tdm_private_client_output {
        unsigned int req_id;
        unsigned int watch_output_changes;
 
+       struct {
+               int count;
+               tdm_client_output_mode *modes;
+       } available_modes;
+
        tdm_private_client_voutput *voutput;
 } tdm_private_client_output;
 
@@ -436,10 +441,41 @@ _tdm_client_output_cb_dpms(void *data, struct wl_tdm_output *wl_tdm_output, uint
        pthread_mutex_lock(&private_client->lock);
 }
 
+static void
+_tdm_client_output_cb_availablie_modes(void *data, struct wl_tdm_output *wl_tdm_output, struct wl_array *modes, uint32_t error)
+{
+       tdm_private_client_output *private_output = (tdm_private_client_output*)data;
+       tdm_output_mode *mode;
+       int size, count = 0, i = 0;
+
+       if (error != TDM_ERROR_NONE)
+               TDM_INFO("get availablie_modes event error: %d", error);
+
+       private_output->available_modes.count = 0;
+       if (private_output->available_modes.modes)
+               free(private_output->available_modes.modes);
+
+       wl_array_for_each(mode, modes)
+               count++;
+       if (count == 0) {
+               TDM_INFO("no output mode");
+               return;
+       }
+
+       size = sizeof(tdm_output_mode);
+
+       private_output->available_modes.modes = malloc(count * size);
+       private_output->available_modes.count = count;
+
+       wl_array_for_each(mode, modes)
+               memcpy(&private_output->available_modes.modes[i++], mode, size);
+}
+
 static const struct wl_tdm_output_listener tdm_client_output_listener = {
        _tdm_client_output_cb_mode,
        _tdm_client_output_cb_connection,
        _tdm_client_output_cb_dpms,
+       _tdm_client_output_cb_availablie_modes,
 };
 
 static void
@@ -1144,6 +1180,72 @@ tdm_client_output_get_dpms(tdm_client_output *output, tdm_output_dpms *dpms)
        return TDM_ERROR_NONE;
 }
 
+tdm_error
+tdm_client_output_get_available_modes(tdm_client_output *output, tdm_client_output_mode **modes, int *count)
+{
+       tdm_private_client_output *private_output;
+       tdm_private_client *private_client;
+
+       TDM_RETURN_VAL_IF_FAIL(output != NULL, TDM_ERROR_INVALID_PARAMETER);
+       TDM_RETURN_VAL_IF_FAIL(modes != NULL, TDM_ERROR_INVALID_PARAMETER);
+       TDM_RETURN_VAL_IF_FAIL(count != NULL, TDM_ERROR_INVALID_PARAMETER);
+
+
+       private_output = (tdm_private_client_output *)output;
+       private_client = private_output->private_client;
+       if (private_output->connection == TDM_OUTPUT_CONN_STATUS_DISCONNECTED) {
+               *modes = NULL;
+               *count = 0;
+               return TDM_ERROR_NONE;
+       }
+
+       pthread_mutex_lock(&private_client->lock);
+
+       if (CHECK_WL_PROTOCOL_ERROR(private_client)) {
+               pthread_mutex_unlock(&private_client->lock);
+               return TDM_ERROR_PROTOCOL_ERROR;
+       }
+
+       wl_proxy_set_queue((struct wl_proxy *)private_output->output, private_client->queue);
+       wl_tdm_output_get_available_modes(private_output->output);
+       wl_display_roundtrip_queue(private_client->display, private_client->queue);
+       wl_proxy_set_queue((struct wl_proxy *)private_output->output, NULL);
+
+       if (CHECK_WL_PROTOCOL_ERROR(private_client)) {
+               pthread_mutex_unlock(&private_client->lock);
+               return TDM_ERROR_PROTOCOL_ERROR;
+       }
+
+       *modes = (tdm_client_output_mode *)private_output->available_modes.modes;
+       *count = private_output->available_modes.count;
+
+       pthread_mutex_unlock(&private_client->lock);
+
+       return TDM_ERROR_NONE;
+}
+
+tdm_error
+tdm_client_output_set_mode(tdm_client_output *output, int index)
+{
+       tdm_private_client_output *private_output;
+
+       TDM_RETURN_VAL_IF_FAIL(output != NULL, TDM_ERROR_INVALID_PARAMETER);
+       TDM_RETURN_VAL_IF_FAIL(index < 0, TDM_ERROR_INVALID_PARAMETER);
+
+       private_output = (tdm_private_client_output*)output;
+
+       if (private_output->available_modes.count - 1 < index)
+               return TDM_ERROR_INVALID_PARAMETER;
+
+       if ((private_output->connection == TDM_OUTPUT_CONN_STATUS_DISCONNECTED) ||
+               (private_output->available_modes.count == 0))
+               return TDM_ERROR_BAD_REQUEST;
+
+       wl_tdm_output_set_mode(private_output->output, index);
+
+       return TDM_ERROR_NONE;
+}
+
 tdm_client_vblank*
 tdm_client_output_create_vblank(tdm_client_output *output, tdm_error *error)
 {
@@ -2311,25 +2413,6 @@ tdm_client_voutput_get_client_output(tdm_client_voutput *voutput, tdm_error *err
        return private_output;
 }
 
-tdm_error
-tdm_client_output_get_available_modes(tdm_client_output *output, tdm_client_output_mode **modes, int *count)
-{
-       TDM_RETURN_VAL_IF_FAIL(output != NULL, TDM_ERROR_INVALID_PARAMETER);
-       TDM_RETURN_VAL_IF_FAIL(modes != NULL, TDM_ERROR_INVALID_PARAMETER);
-       TDM_RETURN_VAL_IF_FAIL(count != NULL, TDM_ERROR_INVALID_PARAMETER);
-
-       return TDM_ERROR_NONE;
-}
-
-tdm_error
-tdm_client_output_set_mode(tdm_client_output *output, const tdm_client_output_mode *mode)
-{
-       TDM_RETURN_VAL_IF_FAIL(output != NULL, TDM_ERROR_INVALID_PARAMETER);
-       TDM_RETURN_VAL_IF_FAIL(mode != NULL, TDM_ERROR_INVALID_PARAMETER);
-
-       return TDM_ERROR_NONE;
-}
-
 void
 _tdm_client_voutput_send_available_modes(tdm_private_client_voutput *private_voutput)
 {
index 8c10ebe..b52785a 100644 (file)
@@ -462,7 +462,7 @@ tdm_error
 tdm_client_output_get_available_modes(tdm_client_output *output, tdm_client_output_mode **modes, int *count);
 
 tdm_error
-tdm_client_output_set_mode(tdm_client_output *output, const tdm_client_output_mode *mode);
+tdm_client_output_set_mode(tdm_client_output *output, int index);
 
 tdm_error
 tdm_client_output_connect(tdm_client_output *output);
index 01668cb..883ac5c 100644 (file)
@@ -802,6 +802,45 @@ TEST_P(TDMClient, ClientOutputGetDpmsNullOther)
        ASSERT_EQ(tdm_client_output_get_dpms(output, NULL), TDM_ERROR_INVALID_PARAMETER);
 }
 
+TEST_P(TDMClient, ClientOutputGetAvailableModes)
+{
+       tdm_client_output_mode *modes;
+       int i, count = 0;
+
+       ASSERT_EQ(PrepareClient(), true);
+       ASSERT_EQ(PrepareOutput(), true);
+
+       ASSERT_EQ(tdm_client_output_get_available_modes(output, &modes, &count), TDM_ERROR_NONE);
+       ASSERT_GT(count, 0);
+
+       for (i = 0; i < count; i++) {
+               tdm_client_output_mode *mode = (tdm_client_output_mode *)&modes[i];
+               ASSERT_GT(mode->hdisplay, 0);
+               ASSERT_GT(mode->vdisplay, 0);
+               ASSERT_GT(mode->vrefresh, 0);
+       }
+}
+
+TEST_P(TDMClient, ClientOutputGetAvailableModesNullObject)
+{
+       tdm_client_output_mode *modes;
+       int count = TDM_UT_INVALID_VALUE;
+
+       ASSERT_EQ(PrepareClient(), true);
+       ASSERT_EQ(PrepareOutput(), true);
+
+       ASSERT_EQ(tdm_client_output_get_available_modes(NULL, &modes, &count), TDM_ERROR_INVALID_PARAMETER);
+       ASSERT_EQ(count, TDM_UT_INVALID_VALUE);
+}
+
+TEST_P(TDMClient, ClientOutputGetAvailableModesNullOther)
+{
+       ASSERT_EQ(PrepareClient(), true);
+       ASSERT_EQ(PrepareOutput(), true);
+
+       ASSERT_EQ(tdm_client_output_get_available_modes(output, NULL, NULL), TDM_ERROR_INVALID_PARAMETER);
+}
+
 /* tdm_client_output_create_vblank */
 TEST_P(TDMClient, ClientOutputCreateVblank)
 {
index a152c95..8272eec 100644 (file)
             <arg name="error" type="uint" summary="error status enumeration"/>
         </event>
 
+        <event name="available_modes">
+            <arg name="modes" type="array"/>
+            <arg name="error" type="uint" summary="error status enumeration"/>
+        </event>
+
         <request name="destroy" type="destructor"/>
 
         <request name="create_vblank">
 
         <request name="get_dpms"/>
 
+        <request name="get_available_modes"/>
+
+        <request name="set_mode">
+            <arg name="index" type="uint"/>
+        </request>
+
     </interface>
 
     <interface name="wl_tdm_voutput" version="1">
index e51d868..a71eb0e 100644 (file)
@@ -596,6 +596,53 @@ failed:
        wl_tdm_output_send_dpms(output_info->resource, TDM_OUTPUT_DPMS_OFF, ret);
 }
 
+static void
+_tdm_server_output_cb_get_available_modes(struct wl_client *client, struct wl_resource *resource)
+{
+       tdm_server_output_info *output_info = wl_resource_get_user_data(resource);
+       const tdm_output_mode *modes;
+       tdm_output_mode *mode;
+       struct wl_array array;
+       int i, size, count = 0;
+       tdm_error ret;
+
+       ret = tdm_output_get_available_modes(output_info->output, &modes, &count);
+
+       if ((ret != TDM_ERROR_NONE) || (count == 0)) {
+               wl_tdm_output_send_available_modes(output_info->resource, NULL, ret);
+               return;
+       }
+
+       size = sizeof(tdm_output_mode);
+       wl_array_init(&array);
+       for (i = 0; i < count; i++) {
+               mode = wl_array_add(&array, size);
+               memcpy(mode, &modes[i], size);
+       }
+
+       wl_tdm_output_send_available_modes(output_info->resource, &array, ret);
+
+       wl_array_release(&array);
+}
+
+static void
+_tdm_server_output_cb_set_mode(struct wl_client *client, struct wl_resource *resource, unsigned int index)
+{
+       tdm_server_output_info *output_info = wl_resource_get_user_data(resource);
+       tdm_output_conn_status status = TDM_OUTPUT_CONN_STATUS_DISCONNECTED;
+       tdm_error ret;
+
+       TDM_RETURN_IF_FAIL(output_info != NULL);
+
+       ret = tdm_output_get_conn_status(output_info->output, &status);
+       TDM_RETURN_IF_FAIL(ret == TDM_ERROR_NONE);
+       TDM_RETURN_IF_FAIL(status != TDM_OUTPUT_CONN_STATUS_DISCONNECTED);
+
+       //To do
+
+       return;
+}
+
 static const struct wl_tdm_output_interface tdm_output_implementation = {
        _tdm_server_output_cb_destroy,
        _tdm_server_output_cb_create_vblank,
@@ -603,6 +650,8 @@ static const struct wl_tdm_output_interface tdm_output_implementation = {
        _tdm_server_output_cb_get_connection,
        _tdm_server_output_cb_get_mode,
        _tdm_server_output_cb_get_dpms,
+       _tdm_server_output_cb_get_available_modes,
+       _tdm_server_output_cb_set_mode,
 };
 
 static void