display: Change device_display_change_state() from async to sync
[platform/core/api/device.git] / src / display.c
1 /*
2  * Copyright (c) 2011 Samsung Electronics Co., Ltd All Rights Reserved
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17
18 #include <stdio.h>
19 #include <errno.h>
20
21 #include <vconf.h>
22 #include <libsyscommon/libgdbus.h>
23 #include <system_info.h>
24 #include <glib.h>
25
26 #include "display.h"
27 #include "display-internal.h"
28 #include "common.h"
29
30 #define DISPLAY_FEATURE     "http://tizen.org/feature/display"
31 #define DISPLAY_STATE_FEATURE     "http://tizen.org/feature/display.state"
32
33 #define METHOD_GET_DISPLAY_COUNT        "GetDisplayCount"
34 #define METHOD_GET_MAX_BRIGHTNESS       "GetMaxBrightness"
35 #define METHOD_GET_BRIGHTNESS           "GetBrightness"
36 #define METHOD_SET_BRIGHTNESS           "SetBrightness"
37 #define METHOD_CHANGE_STATE             "changestate"
38 #define METHOD_CHANGE_STATE_BY_REASON   "ChangeStateByReason"
39 #define METHOD_GET_WHITE_BALANCE        "GetWhiteBalance"
40 #define METHOD_SET_WHITE_BALANCE        "SetWhiteBalance"
41 #define METHOD_GET_ROTATION_ANGLE       "GetRotationAngle"
42 #define METHOD_SET_ROTATION_ANGLE       "SetRotationAngle"
43
44 #define STR_LCD_OFF   "lcdoff"
45 #define STR_LCD_DIM   "lcddim"
46 #define STR_LCD_ON    "lcdon"
47
48 #define DISPLAY_WHITE_BALANCE_GAIN_MAX      2047
49 #define DISPLAY_WHITE_BALANCE_GAIN_MIN      0
50 #define DISPLAY_WHITE_BALANCE_OFFSET_MAX    2047
51 #define DISPLAY_WHITE_BALANCE_OFFSET_MIN    0
52
53 #define ROTATION_ANGLE_DEGREE_MAX           360
54
55 static int display_cnt = -1;
56 struct display {
57         int normal_max;
58         int dim_max;
59 } *display_arr;
60
61 static int alloc_display(void)
62 {
63         int i;
64
65         if (display_cnt < 0)
66                 return -ENODEV;
67
68         display_arr = malloc(sizeof(struct display) * display_cnt);
69         if (!display_arr)
70                 return -ENOMEM;
71
72         for (i = 0; i < display_cnt; ++i) {
73                 display_arr[i].normal_max = -1;
74                 display_arr[i].dim_max = -1;
75         }
76
77         return 0;
78 }
79
80 int device_display_get_numbers(int *device_number)
81 {
82         int ret_val, reply;
83
84         ret_val = is_feature_display_supported();
85         if (!ret_val)
86                 return DEVICE_ERROR_NOT_SUPPORTED;
87
88         if (!device_number)
89                 return DEVICE_ERROR_INVALID_PARAMETER;
90
91         /* if it is a first request */
92         if (display_cnt < 0) {
93                 ret_val = gdbus_call_sync_with_reply_int(DEVICED_BUS_NAME,
94                                 DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
95                                 METHOD_GET_DISPLAY_COUNT, NULL, &reply);
96                 if (ret_val < 0)
97                         return errno_to_device_error(ret_val); //LCOV_EXCL_LINE System Error
98                 display_cnt = reply;
99                 alloc_display();
100         }
101
102         *device_number = display_cnt;
103         _I("device_number : %d", *device_number);
104         return DEVICE_ERROR_NONE;
105 }
106
107 int device_display_get_max_brightness(int display_index, int *max_brightness)
108 {
109         int ret_val, reply;
110
111         ret_val = is_feature_display_supported();
112         if (!ret_val)
113                 return DEVICE_ERROR_NOT_SUPPORTED;
114
115         if (!max_brightness)
116                 return DEVICE_ERROR_INVALID_PARAMETER;
117
118         if (display_cnt < 0) {
119                 ret_val = device_display_get_numbers(&display_cnt);
120                 if (ret_val != DEVICE_ERROR_NONE) //LCOV_EXCL_LINE System Error
121                         return ret_val;
122         }
123
124         if (display_index < 0 || display_index >= display_cnt)
125                 return DEVICE_ERROR_INVALID_PARAMETER;
126
127         if (!display_arr && alloc_display() < 0)
128                 return DEVICE_ERROR_OPERATION_FAILED;
129
130         if (display_arr[display_index].normal_max < 0) {
131                 ret_val = gdbus_call_sync_with_reply_int(DEVICED_BUS_NAME,
132                                 DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
133                                 METHOD_GET_MAX_BRIGHTNESS, g_variant_new("(i)", (int)DISPLAY_STATE_NORMAL),
134                                 &reply);
135                 if (ret_val < 0)
136                         return errno_to_device_error(ret_val); //LCOV_EXCL_LINE System Error
137                 display_arr[display_index].normal_max = reply;
138         }
139
140         *max_brightness = display_arr[display_index].normal_max;
141         return DEVICE_ERROR_NONE;
142 }
143
144 int device_display_get_brightness(int display_index, int *brightness)
145 {
146         int ret_val, reply;
147
148         ret_val = is_feature_display_supported();
149         if (!ret_val)
150                 return DEVICE_ERROR_NOT_SUPPORTED;
151
152         if (!brightness)
153                 return DEVICE_ERROR_INVALID_PARAMETER;
154
155         if (display_cnt < 0) {
156                 ret_val = device_display_get_numbers(&display_cnt);
157                 if (ret_val != DEVICE_ERROR_NONE) //LCOV_EXCL_LINE System Error
158                         return ret_val;
159         }
160
161         if (display_index < 0 || display_index >= display_cnt)
162                 return DEVICE_ERROR_INVALID_PARAMETER;
163
164         ret_val = gdbus_call_sync_with_reply_int(DEVICED_BUS_NAME,
165                         DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
166                         METHOD_GET_BRIGHTNESS, g_variant_new("(i)", (int)DISPLAY_STATE_NORMAL),
167                         &reply);
168         if (ret_val < 0)
169                 return errno_to_device_error(ret_val); //LCOV_EXCL_LINE System Error
170
171         *brightness = reply;
172         return DEVICE_ERROR_NONE;
173 }
174
175 int device_display_set_brightness(int display_index, int brightness)
176 {
177         int ret_val, max;
178         int ret_dbus;
179
180         ret_val = is_feature_display_supported();
181         if (!ret_val)
182                 return DEVICE_ERROR_NOT_SUPPORTED;
183
184         if (display_cnt < 0) {
185                 ret_val = device_display_get_numbers(&display_cnt);
186                 if (ret_val != DEVICE_ERROR_NONE) //LCOV_EXCL_LINE System Error
187                         return ret_val;
188         }
189
190         if (display_index < 0 || display_index >= display_cnt)
191                 return DEVICE_ERROR_INVALID_PARAMETER;
192
193         if (display_arr[display_index].normal_max < 0)
194                 device_display_get_max_brightness(display_index, &max);
195
196         if (brightness < 0 || brightness > display_arr[display_index].normal_max)
197                 return DEVICE_ERROR_INVALID_PARAMETER;
198
199         ret_dbus = gdbus_call_sync_with_reply_int(DEVICED_BUS_NAME,
200                         DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
201                         METHOD_SET_BRIGHTNESS, g_variant_new("(ii)", (int)DISPLAY_STATE_NORMAL, brightness),
202                         &ret_val);
203
204         if (ret_dbus < 0)
205                 return DEVICE_ERROR_OPERATION_FAILED;
206
207         if (ret_val < 0)
208                 return errno_to_device_error(ret_val); //LCOV_EXCL_LINE System Error
209
210         return DEVICE_ERROR_NONE;
211 }
212
213 int device_display_get_state(display_state_e *state)
214 {
215         int ret_val, val;
216
217         ret_val = is_feature_display_supported();
218         if (!ret_val)
219                 return DEVICE_ERROR_NOT_SUPPORTED;
220
221         if (!state)
222                 return DEVICE_ERROR_INVALID_PARAMETER;
223
224         ret_val = vconf_get_int(VCONFKEY_PM_STATE, &val);
225         if (ret_val < 0)
226                 return DEVICE_ERROR_OPERATION_FAILED;
227
228         if (val == VCONFKEY_PM_STATE_NORMAL)
229                 *state = DISPLAY_STATE_NORMAL;
230         else if (val == VCONFKEY_PM_STATE_LCDDIM)
231                 *state = DISPLAY_STATE_SCREEN_DIM;
232         else if (val == VCONFKEY_PM_STATE_LCDOFF || val == VCONFKEY_PM_STATE_SLEEP)
233                 *state = DISPLAY_STATE_SCREEN_OFF;
234         else
235                 return DEVICE_ERROR_OPERATION_FAILED;
236
237         return DEVICE_ERROR_NONE;
238 }
239
240 static char *get_state_str(display_state_e state)
241 {
242         switch (state) {
243         case DISPLAY_STATE_NORMAL:
244                 return STR_LCD_ON;
245         case DISPLAY_STATE_SCREEN_DIM:
246                 return STR_LCD_DIM;
247         case DISPLAY_STATE_SCREEN_OFF:
248                 return STR_LCD_OFF;
249         default:
250                 break;
251         }
252         return NULL;
253 }
254
255 int device_display_change_state(display_state_e state)
256 {
257         char *str;
258         int ret;
259         int val;
260         static int privilege = -1;
261         static long num_calls = 0;
262         GVariant *reply = NULL;
263
264         ret = is_feature_display_state_supported();
265         if (!ret)
266                 return DEVICE_ERROR_NOT_SUPPORTED;
267
268         if (check_async_call_rate(&num_calls) < 0) {
269 //LCOV_EXCL_START System Error
270                 _E("Rejected by too frequent calls; %d (calls per sec.) limit is violated."
271                                 , CHECK_RATE_THRESHOLD);
272                 return DEVICE_ERROR_OPERATION_FAILED;
273 //LCOV_EXCL_STOP
274         }
275
276         if (state < DISPLAY_STATE_NORMAL || state > DISPLAY_STATE_SCREEN_OFF)
277                 return DEVICE_ERROR_INVALID_PARAMETER;
278
279         if (privilege < 0) {
280                 ret = gdbus_call_sync_with_reply_int(DEVICED_BUS_NAME,
281                                 DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
282                                 METHOD_CHANGE_STATE, g_variant_new("(s)", "privilege check"),
283                                 NULL);
284 //LCOV_EXCL_START System Error
285                 if (ret < 0)
286                         return errno_to_device_error(ret); //LCOV_EXCL_LINE System Error
287 //LCOV_EXCL_STOP
288                 else
289                         privilege = 1;
290         }
291
292         str = get_state_str(state);
293         if (!str)
294                 return DEVICE_ERROR_INVALID_PARAMETER;
295
296         ret = gdbus_call_sync_with_reply(DEVICED_BUS_NAME,
297                         DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
298                         METHOD_CHANGE_STATE, g_variant_new("(s)", str), &reply);
299
300         if (ret < 0)
301                 ret = errno_to_device_error(ret); //LCOV_EXCL_LINE System Error
302
303         if (reply) {
304                 g_variant_get(reply, "(i)", &val);
305                 _D("%s-%s : %d", DEVICED_INTERFACE_DISPLAY, METHOD_CHANGE_STATE, val);
306
307                 if (val < 0)
308                         return errno_to_device_error(val);
309         }
310
311         return ret;
312 }
313
314 //LCOV_EXCL_START Not tested API
315 int device_display_get_max_brightness_state(int display_index, display_state_e state, int *brightness)
316 {
317         int ret_val, reply;
318
319         ret_val = is_feature_display_supported();
320         if (!ret_val)
321                 return DEVICE_ERROR_NOT_SUPPORTED;
322
323         if (!brightness)
324                 return DEVICE_ERROR_INVALID_PARAMETER;
325
326         if (state > DISPLAY_STATE_SCREEN_DIM)
327                 return DEVICE_ERROR_INVALID_PARAMETER;
328
329         if (display_cnt < 0) {
330                 ret_val = device_display_get_numbers(&display_cnt);
331                 if (ret_val != DEVICE_ERROR_NONE) //LCOV_EXCL_LINE System Error
332                         return ret_val;
333         }
334
335         if (display_index < 0 || display_index >= display_cnt)
336                 return DEVICE_ERROR_INVALID_PARAMETER;
337
338         if (!display_arr && alloc_display() < 0)
339                 return DEVICE_ERROR_OPERATION_FAILED;
340
341         ret_val = gdbus_call_sync_with_reply_int(DEVICED_BUS_NAME,
342                                 DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
343                                 METHOD_GET_MAX_BRIGHTNESS, g_variant_new("(i)", (int)state),
344                                 &reply);
345         if (ret_val < 0)
346                 return errno_to_device_error(ret_val); //LCOV_EXCL_LINE System Error
347
348         if (state == DISPLAY_STATE_NORMAL) {
349                 display_arr[display_index].normal_max = reply;
350                 *brightness = display_arr[display_index].normal_max;
351         } else {
352                 display_arr[display_index].dim_max = reply;
353                 *brightness = display_arr[display_index].dim_max;
354         }
355
356         return DEVICE_ERROR_NONE;
357 }
358 //LCOV_EXCL_STOP
359
360 //LCOV_EXCL_START Not tested API
361 int device_display_get_brightness_state(int display_index, display_state_e state, int *brightness)
362 {
363         int ret_val, reply;
364
365         ret_val = is_feature_display_supported();
366         if (!ret_val)
367                 return DEVICE_ERROR_NOT_SUPPORTED;
368
369         if (!brightness)
370                 return DEVICE_ERROR_INVALID_PARAMETER;
371
372         if (state > DISPLAY_STATE_SCREEN_DIM)
373                 return DEVICE_ERROR_INVALID_PARAMETER;
374
375         if (display_cnt < 0) {
376                 ret_val = device_display_get_numbers(&display_cnt);
377                 if (ret_val != DEVICE_ERROR_NONE) //LCOV_EXCL_LINE System Error
378                         return ret_val;
379         }
380
381         if (display_index < 0 || display_index >= display_cnt)
382                 return DEVICE_ERROR_INVALID_PARAMETER;
383
384         ret_val = gdbus_call_sync_with_reply_int(DEVICED_BUS_NAME,
385                         DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
386                         METHOD_GET_BRIGHTNESS, g_variant_new("(i)", (int)state),
387                         &reply);
388         if (ret_val < 0)
389                 return errno_to_device_error(ret_val); //LCOV_EXCL_LINE System Error
390
391         *brightness = reply;
392
393         return DEVICE_ERROR_NONE;
394 }
395 //LCOV_EXCL_STOP
396
397 //LCOV_EXCL_START Not tested API
398 int device_display_set_brightness_state(int display_index, display_state_e state, int brightness)
399 {
400         int ret_val, max;
401
402         ret_val = is_feature_display_supported();
403         if (!ret_val)
404                 return DEVICE_ERROR_NOT_SUPPORTED;
405
406         if (display_cnt < 0) {
407                 ret_val = device_display_get_numbers(&display_cnt);
408                 if (ret_val != DEVICE_ERROR_NONE) //LCOV_EXCL_LINE System Error
409                         return ret_val;
410         }
411
412         if (state > DISPLAY_STATE_SCREEN_DIM)
413                 return DEVICE_ERROR_INVALID_PARAMETER;
414
415         if (display_index < 0 || display_index >= display_cnt)
416                 return DEVICE_ERROR_INVALID_PARAMETER;
417
418         switch (state) {
419         case DISPLAY_STATE_NORMAL:
420                 if (display_arr[display_index].normal_max < 0)
421                         device_display_get_max_brightness_state(display_index, DISPLAY_STATE_NORMAL, &max);
422                 if (brightness < 0 || brightness > display_arr[display_index].normal_max)
423                         return DEVICE_ERROR_INVALID_PARAMETER;
424                 break;
425         case DISPLAY_STATE_SCREEN_DIM:
426                 if (display_arr[display_index].dim_max < 0)
427                         device_display_get_max_brightness_state(display_index, DISPLAY_STATE_SCREEN_DIM, &max);
428                 if (brightness < 0 || brightness > display_arr[display_index].dim_max)
429                         return DEVICE_ERROR_INVALID_PARAMETER;
430                 break;
431         default:
432                 break;
433         }
434
435         ret_val = gdbus_call_sync_with_reply_int(DEVICED_BUS_NAME,
436                         DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
437                         METHOD_SET_BRIGHTNESS, g_variant_new("(ii)", (int)state, brightness),
438                         NULL);
439         if (ret_val < 0)
440                 return errno_to_device_error(ret_val); //LCOV_EXCL_LINE System Error
441
442         return DEVICE_ERROR_NONE;
443 }
444 //LCOV_EXCL_STOP
445
446 //LCOV_EXCL_START Not tested API
447 int device_display_change_state_by_reason(display_state_e type, const char *reason, int timeout, dbus_pending_cb cb)
448 {
449         int ret;
450
451         ret = gdbus_call_async_with_reply(DEVICED_BUS_NAME,
452                         DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
453                         METHOD_CHANGE_STATE_BY_REASON, g_variant_new("(isi)", (int)type, reason, timeout), cb, -1, NULL);
454
455         return errno_to_device_error(ret);
456 }
457 //LCOV_EXCL_STOP
458
459 int is_feature_display_supported(void)
460 {
461         int ret_val;
462         bool display_avail;
463
464         ret_val = system_info_get_platform_bool(DISPLAY_FEATURE, &display_avail);
465         if (ret_val < 0) {
466 //LCOV_EXCL_START System Error
467                 _E("Failed to get value of display feature");
468                 return false;
469 //LCOV_EXCL_STOP
470         } else if (ret_val == 0 && !display_avail) {
471 //LCOV_EXCL_START System Error
472                 _D("Display feature is not supported");
473                 return false;
474 //LCOV_EXCL_STOP
475         } else
476                 return true;
477 }
478
479 //LCOV_EXCL_START Internal function
480 int device_display_get_rotation_angle(int display_index,
481                                 device_display_rotation_angle_e *angle,
482                                 device_display_init_direction_e *init_direction)
483 {
484         int ret = 0, reply_angle, reply_init_direction;
485         GVariant *reply;
486
487         ret = is_feature_display_supported();
488         if (!ret)
489                 return DEVICE_ERROR_NOT_SUPPORTED;
490
491         if (display_cnt < 0) {
492                 ret = device_display_get_numbers(&display_cnt);
493                 if (ret < 0)
494                         return ret;
495         }
496
497         if (display_index < 0 || display_index >= display_cnt || !angle || !init_direction)
498                 return DEVICE_ERROR_INVALID_PARAMETER;
499
500         /* Get the display rotation angle from deviced */
501         ret = gdbus_call_sync_with_reply(DEVICED_BUS_NAME,
502                                         DEVICED_PATH_DISPLAY,
503                                         DEVICED_INTERFACE_DISPLAY,
504                                         METHOD_GET_ROTATION_ANGLE,
505                                         g_variant_new("(i)", display_index),
506                                         &reply);
507
508         if (ret < 0) {
509                 _E("Failed to call dbus method to get the rotation angle");
510                 return ret;
511         }
512
513         g_variant_get(reply, "(iii)", &ret, &reply_angle, &reply_init_direction);
514         g_variant_unref(reply);
515
516         if (ret == -ENODEV) {
517                 _E("Get display rotation is not supported");
518                 return DEVICE_ERROR_OPERATION_FAILED;
519         } else if (ret < 0) {
520                 _E("Failed to get display rotation angle");
521                 return DEVICE_ERROR_OPERATION_FAILED;
522         }
523
524         *angle = reply_angle;
525         *init_direction = reply_init_direction;
526
527         return DEVICE_ERROR_NONE;
528 }
529 //LCOV_EXCL_STOP
530
531 //LCOV_EXCL_START Internal function
532 int device_display_set_rotation_angle(int display_index,
533                                 device_display_rotation_angle_e angle,
534                                 device_display_rotation_direction_e rotation_direction)
535 {
536         int ret, reply;
537
538         ret = is_feature_display_supported();
539         if (!ret)
540                 return DEVICE_ERROR_NOT_SUPPORTED;
541
542         if (display_cnt < 0) {
543                 ret = device_display_get_numbers(&display_cnt);
544                 if (ret < 0)
545                         return ret;
546         }
547
548         if (display_index < 0 || display_index >= display_cnt)
549                 return DEVICE_ERROR_INVALID_PARAMETER;
550
551         if (angle < DEVICE_DISPLAY_ROTATION_ANGLE_DEGREE_0
552                 || angle > ROTATION_ANGLE_DEGREE_MAX)
553                 return DEVICE_ERROR_INVALID_PARAMETER;
554
555         switch (rotation_direction) {
556         case DEVICE_DISPLAY_ROTATION_DIRECTION_CLOCKWISE:
557         case DEVICE_DISPLAY_ROTATION_DIRECTION_COUNTER_CLOCKWISE:
558                 break;
559         default:
560                 return DEVICE_ERROR_INVALID_PARAMETER;
561         }
562
563         ret = gdbus_call_sync_with_reply_int(DEVICED_BUS_NAME,
564                                         DEVICED_PATH_DISPLAY,
565                                         DEVICED_INTERFACE_DISPLAY,
566                                         METHOD_SET_ROTATION_ANGLE,
567                                         g_variant_new("(iii)", display_index, angle, rotation_direction),
568                                         &reply);
569
570         if (ret < 0) {
571                 _E("Failed to call dbus method to set the rotation angle");
572                 return ret;
573         }
574
575         if (reply == -ENODEV) {
576                 _E("Set display rotation is not supported");
577                 return DEVICE_ERROR_OPERATION_FAILED;
578         } else if (reply < 0) {
579                 _E("Failed to set display rotation angle");
580                 return DEVICE_ERROR_OPERATION_FAILED;
581         }
582
583         return DEVICE_ERROR_NONE;
584 }
585 //LCOV_EXCL_STOP
586
587 int is_feature_display_state_supported(void)
588 {
589         int ret_val;
590         bool display_state_avail;
591
592         ret_val = system_info_get_platform_bool(DISPLAY_STATE_FEATURE, &display_state_avail);
593         if (ret_val < 0) {
594 //LCOV_EXCL_START System Error
595                 _E("Failed to get value of display state feature");
596                 return false;
597 //LCOV_EXCL_STOP
598         } else if (ret_val == 0 && !display_state_avail) {
599 //LCOV_EXCL_START System Error
600                 _D("Display state feature is not supported");
601                 return false;
602 //LCOV_EXCL_STOP
603         } else
604                 return true;
605 }
606
607 //LCOV_EXCL_START Internal function
608 int device_display_set_white_balance(int display_index, display_white_balance_e white_balance_type, int value)
609 {
610         int ret;
611
612         if (!is_feature_display_supported())
613                 return DEVICE_ERROR_NOT_SUPPORTED;
614
615         if (display_cnt < 0) {
616                 ret = device_display_get_numbers(&display_cnt);
617                 if (ret != DEVICE_ERROR_NONE)
618                         return ret;
619         }
620
621         if (display_index < 0 || display_index >= display_cnt)
622                 return DEVICE_ERROR_INVALID_PARAMETER;
623
624         switch (white_balance_type) {
625         case DISPLAY_WHITE_BALANCE_R_GAIN:
626         case DISPLAY_WHITE_BALANCE_G_GAIN:
627         case DISPLAY_WHITE_BALANCE_B_GAIN:
628                 if (value < DISPLAY_WHITE_BALANCE_GAIN_MIN || value > DISPLAY_WHITE_BALANCE_GAIN_MAX) {
629                         _E("Invalid value of white balance gain (%d)", white_balance_type);
630                         return DEVICE_ERROR_INVALID_PARAMETER;
631                 }
632                 break;
633         case DISPLAY_WHITE_BALANCE_R_OFFSET:
634         case DISPLAY_WHITE_BALANCE_G_OFFSET:
635         case DISPLAY_WHITE_BALANCE_B_OFFSET:
636                 if (value < DISPLAY_WHITE_BALANCE_OFFSET_MIN || value > DISPLAY_WHITE_BALANCE_OFFSET_MAX) {
637                         _E("Invalid value of white balance offset (%d)", white_balance_type);
638                         return DEVICE_ERROR_INVALID_PARAMETER;
639                 }
640                 break;
641         default:
642                 _E("Unknown white balance type");
643                 return DEVICE_ERROR_INVALID_PARAMETER;
644         }
645
646         ret = gdbus_call_sync_with_reply_int(DEVICED_BUS_NAME,
647                                 DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
648                                 METHOD_SET_WHITE_BALANCE, g_variant_new("(ii)",
649                                 (int)white_balance_type, value),
650                                 NULL);
651
652         if (ret < 0)
653                 return errno_to_device_error(ret);
654
655         return DEVICE_ERROR_NONE;
656 }
657 //LCOV_EXCL_STOP
658
659 //LCOV_EXCL_START Internal function
660 int device_display_get_white_balance(int display_index, display_white_balance_e white_balance_type, int *value)
661 {
662         int ret, reply;
663
664         if (!is_feature_display_supported())
665                 return DEVICE_ERROR_NOT_SUPPORTED;
666
667         if (display_cnt < 0) {
668                 ret = device_display_get_numbers(&display_cnt);
669                 if (ret != DEVICE_ERROR_NONE)
670                         return ret;
671         }
672
673         if (display_index < 0 || display_index >= display_cnt)
674                 return DEVICE_ERROR_INVALID_PARAMETER;
675
676         switch (white_balance_type) {
677         case DISPLAY_WHITE_BALANCE_R_GAIN:
678         case DISPLAY_WHITE_BALANCE_G_GAIN:
679         case DISPLAY_WHITE_BALANCE_B_GAIN:
680         case DISPLAY_WHITE_BALANCE_R_OFFSET:
681         case DISPLAY_WHITE_BALANCE_G_OFFSET:
682         case DISPLAY_WHITE_BALANCE_B_OFFSET:
683                 break;
684         default:
685                 _E("Unknown white balance type");
686                 return DEVICE_ERROR_INVALID_PARAMETER;
687         }
688
689         ret = gdbus_call_sync_with_reply_int(DEVICED_BUS_NAME,
690                                 DEVICED_PATH_DISPLAY, DEVICED_INTERFACE_DISPLAY,
691                                 METHOD_GET_WHITE_BALANCE, g_variant_new("(i)",
692                                 (int)white_balance_type),
693                                 &reply);
694
695         if (ret < 0)
696                 return errno_to_device_error(ret);
697
698         if (reply < 0)
699                 return DEVICE_ERROR_OPERATION_FAILED;
700
701         *value = reply;
702
703         return DEVICE_ERROR_NONE;
704 }
705 //LCOV_EXCL_STOP