1ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson/* 2ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * Copyright (C) 2008 The Android Open Source Project 3a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson * Copyright (C) 2014 The Linux Foundation. All rights reserved. 4ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * 5ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * Licensed under the Apache License, Version 2.0 (the "License"); 6ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * you may not use this file except in compliance with the License. 7ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * You may obtain a copy of the License at 8ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * 9ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * http://www.apache.org/licenses/LICENSE-2.0 10ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * 11ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * Unless required by applicable law or agreed to in writing, software 12ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * distributed under the License is distributed on an "AS IS" BASIS, 13ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * See the License for the specific language governing permissions and 15ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * limitations under the License. 16ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson */ 17ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 18ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 19ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson// #define LOG_NDEBUG 0 20ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 21ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson#include <cutils/log.h> 22ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 23ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson#include <stdint.h> 24ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson#include <string.h> 25ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson#include <unistd.h> 26ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson#include <errno.h> 27ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson#include <fcntl.h> 28ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson#include <pthread.h> 29ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 30ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson#include <sys/ioctl.h> 31ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson#include <sys/types.h> 32ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 33ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson#include <hardware/lights.h> 34ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 35ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson/******************************************************************************/ 36ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 37ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic pthread_once_t g_init = PTHREAD_ONCE_INIT; 38ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic pthread_mutex_t g_lock = PTHREAD_MUTEX_INITIALIZER; 39ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic struct light_state_t g_notification; 40ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic struct light_state_t g_battery; 41ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic int g_attention = 0; 42ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 43ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonchar const*const RED_LED_FILE 44ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson = "/sys/class/leds/red/brightness"; 45ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 46ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonchar const*const GREEN_LED_FILE 47ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson = "/sys/class/leds/green/brightness"; 48ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 49ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonchar const*const BLUE_LED_FILE 50ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson = "/sys/class/leds/blue/brightness"; 51ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 52ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonchar const*const LCD_FILE 53ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson = "/sys/class/leds/lcd-backlight/brightness"; 54ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 55a653efede03423aa840da24634f1ec6f20796f1eSimon Wilsonchar const*const BUTTON_FILE 56a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson = "/sys/class/leds/button-backlight/brightness"; 57ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 58a653efede03423aa840da24634f1ec6f20796f1eSimon Wilsonchar const*const RED_BLINK_FILE 59a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson = "/sys/class/leds/red/blink"; 60ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 61a653efede03423aa840da24634f1ec6f20796f1eSimon Wilsonchar const*const GREEN_BLINK_FILE 62a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson = "/sys/class/leds/green/blink"; 63ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 64a653efede03423aa840da24634f1ec6f20796f1eSimon Wilsonchar const*const BLUE_BLINK_FILE 65a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson = "/sys/class/leds/blue/blink"; 66ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 67ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson/** 68ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * device methods 69ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson */ 70ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 71ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonvoid init_globals(void) 72ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson{ 73ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson // init the mutex 74ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson pthread_mutex_init(&g_lock, NULL); 75ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson} 76ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 77ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic int 78ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonwrite_int(char const* path, int value) 79ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson{ 80ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson int fd; 81ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson static int already_warned = 0; 82ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 83ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson fd = open(path, O_RDWR); 84ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson if (fd >= 0) { 85ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson char buffer[20]; 869caaa41be6c1f3ceb52a2748c8f13c48b8aee848Manoj Kumar AVM int bytes = snprintf(buffer, sizeof(buffer), "%d\n", value); 87a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson ssize_t amt = write(fd, buffer, (size_t)bytes); 88ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson close(fd); 89ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson return amt == -1 ? -errno : 0; 90ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson } else { 91ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson if (already_warned == 0) { 92ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson ALOGE("write_int failed to open %s\n", path); 93ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson already_warned = 1; 94ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson } 95ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson return -errno; 96ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson } 97ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson} 98ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 99ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic int 100ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonis_lit(struct light_state_t const* state) 101ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson{ 102ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson return state->color & 0x00ffffff; 103ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson} 104ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 105ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic int 106ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonrgb_to_brightness(struct light_state_t const* state) 107ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson{ 108ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson int color = state->color & 0x00ffffff; 109ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson return ((77*((color>>16)&0x00ff)) 110ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson + (150*((color>>8)&0x00ff)) + (29*(color&0x00ff))) >> 8; 111ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson} 112ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 113ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic int 114ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonset_light_backlight(struct light_device_t* dev, 115ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson struct light_state_t const* state) 116ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson{ 117ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson int err = 0; 118ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson int brightness = rgb_to_brightness(state); 119a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson if(!dev) { 120a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson return -1; 121a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson } 122ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson pthread_mutex_lock(&g_lock); 123ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson err = write_int(LCD_FILE, brightness); 124ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson pthread_mutex_unlock(&g_lock); 125ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson return err; 126ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson} 127ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 128ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic int 129ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonset_speaker_light_locked(struct light_device_t* dev, 130ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson struct light_state_t const* state) 131ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson{ 132a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson int red, green, blue; 133a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson int blink; 134ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson int onMS, offMS; 135ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson unsigned int colorRGB; 136ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 137a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson if(!dev) { 138a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson return -1; 139a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson } 140a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson 141ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson switch (state->flashMode) { 142ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson case LIGHT_FLASH_TIMED: 143ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson onMS = state->flashOnMS; 144ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson offMS = state->flashOffMS; 145ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson break; 146ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson case LIGHT_FLASH_NONE: 147ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson default: 148ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson onMS = 0; 149ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson offMS = 0; 150ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson break; 151ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson } 152ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 153ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson colorRGB = state->color; 154ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 155ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson#if 0 156ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson ALOGD("set_speaker_light_locked mode %d, colorRGB=%08X, onMS=%d, offMS=%d\n", 157ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson state->flashMode, colorRGB, onMS, offMS); 158ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson#endif 159ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 160a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson red = (colorRGB >> 16) & 0xFF; 161a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson green = (colorRGB >> 8) & 0xFF; 162a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson blue = colorRGB & 0xFF; 163ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 164a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson if (onMS > 0 && offMS > 0) { 165ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson blink = 1; 166ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson } else { 167ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson blink = 0; 168ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson } 169ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 170ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson if (blink) { 171cbf0d5f822b638271c897338a3d29c43ce0d4e37Mao Li if (red) { 172cbf0d5f822b638271c897338a3d29c43ce0d4e37Mao Li if (write_int(RED_BLINK_FILE, blink)) 173cbf0d5f822b638271c897338a3d29c43ce0d4e37Mao Li write_int(RED_LED_FILE, 0); 174cbf0d5f822b638271c897338a3d29c43ce0d4e37Mao Li } 175cbf0d5f822b638271c897338a3d29c43ce0d4e37Mao Li if (green) { 176cbf0d5f822b638271c897338a3d29c43ce0d4e37Mao Li if (write_int(GREEN_BLINK_FILE, blink)) 177cbf0d5f822b638271c897338a3d29c43ce0d4e37Mao Li write_int(GREEN_LED_FILE, 0); 178cbf0d5f822b638271c897338a3d29c43ce0d4e37Mao Li } 179cbf0d5f822b638271c897338a3d29c43ce0d4e37Mao Li if (blue) { 180cbf0d5f822b638271c897338a3d29c43ce0d4e37Mao Li if (write_int(BLUE_BLINK_FILE, blink)) 181cbf0d5f822b638271c897338a3d29c43ce0d4e37Mao Li write_int(BLUE_LED_FILE, 0); 182cbf0d5f822b638271c897338a3d29c43ce0d4e37Mao Li } 183a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson } else { 184a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson write_int(RED_LED_FILE, red); 185a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson write_int(GREEN_LED_FILE, green); 186a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson write_int(BLUE_LED_FILE, blue); 187ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson } 188ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 189ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson return 0; 190ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson} 191ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 192ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic void 193ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonhandle_speaker_battery_locked(struct light_device_t* dev) 194ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson{ 195ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson if (is_lit(&g_battery)) { 196ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson set_speaker_light_locked(dev, &g_battery); 197ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson } else { 198ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson set_speaker_light_locked(dev, &g_notification); 199ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson } 200ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson} 201ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 202ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic int 203db007e94420fc2efb423fa037355ea7269a982edMao Liset_light_battery(struct light_device_t* dev, 204db007e94420fc2efb423fa037355ea7269a982edMao Li struct light_state_t const* state) 205db007e94420fc2efb423fa037355ea7269a982edMao Li{ 206db007e94420fc2efb423fa037355ea7269a982edMao Li pthread_mutex_lock(&g_lock); 207db007e94420fc2efb423fa037355ea7269a982edMao Li g_battery = *state; 208db007e94420fc2efb423fa037355ea7269a982edMao Li handle_speaker_battery_locked(dev); 209db007e94420fc2efb423fa037355ea7269a982edMao Li pthread_mutex_unlock(&g_lock); 210db007e94420fc2efb423fa037355ea7269a982edMao Li return 0; 211db007e94420fc2efb423fa037355ea7269a982edMao Li} 212db007e94420fc2efb423fa037355ea7269a982edMao Li 213db007e94420fc2efb423fa037355ea7269a982edMao Listatic int 214ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonset_light_notifications(struct light_device_t* dev, 215ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson struct light_state_t const* state) 216ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson{ 217ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson pthread_mutex_lock(&g_lock); 218ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson g_notification = *state; 219ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson handle_speaker_battery_locked(dev); 220ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson pthread_mutex_unlock(&g_lock); 221ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson return 0; 222ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson} 223ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 224ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic int 225ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonset_light_attention(struct light_device_t* dev, 226ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson struct light_state_t const* state) 227ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson{ 228ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson pthread_mutex_lock(&g_lock); 229ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson if (state->flashMode == LIGHT_FLASH_HARDWARE) { 230ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson g_attention = state->flashOnMS; 231ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson } else if (state->flashMode == LIGHT_FLASH_NONE) { 232ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson g_attention = 0; 233ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson } 234ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson handle_speaker_battery_locked(dev); 235ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson pthread_mutex_unlock(&g_lock); 236ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson return 0; 237ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson} 238ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 239a653efede03423aa840da24634f1ec6f20796f1eSimon Wilsonstatic int 240a653efede03423aa840da24634f1ec6f20796f1eSimon Wilsonset_light_buttons(struct light_device_t* dev, 241a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson struct light_state_t const* state) 242a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson{ 243a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson int err = 0; 244a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson if(!dev) { 245a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson return -1; 246a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson } 247a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson pthread_mutex_lock(&g_lock); 248a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson err = write_int(BUTTON_FILE, state->color & 0xFF); 249a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson pthread_mutex_unlock(&g_lock); 250a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson return err; 251a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson} 252ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 253ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson/** Close the lights device */ 254ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic int 255ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonclose_lights(struct light_device_t *dev) 256ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson{ 257ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson if (dev) { 258ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson free(dev); 259ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson } 260ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson return 0; 261ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson} 262ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 263ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 264ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson/******************************************************************************/ 265ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 266ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson/** 267ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * module methods 268ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson */ 269ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 270ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson/** Open a new instance of a lights device using name */ 271ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic int open_lights(const struct hw_module_t* module, char const* name, 272ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson struct hw_device_t** device) 273ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson{ 274ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson int (*set_light)(struct light_device_t* dev, 275ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson struct light_state_t const* state); 276ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 277ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson if (0 == strcmp(LIGHT_ID_BACKLIGHT, name)) 278ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson set_light = set_light_backlight; 279db007e94420fc2efb423fa037355ea7269a982edMao Li else if (0 == strcmp(LIGHT_ID_BATTERY, name)) 280db007e94420fc2efb423fa037355ea7269a982edMao Li set_light = set_light_battery; 281ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson else if (0 == strcmp(LIGHT_ID_NOTIFICATIONS, name)) 282ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson set_light = set_light_notifications; 283a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson else if (0 == strcmp(LIGHT_ID_BUTTONS, name)) 284a653efede03423aa840da24634f1ec6f20796f1eSimon Wilson set_light = set_light_buttons; 285ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson else if (0 == strcmp(LIGHT_ID_ATTENTION, name)) 286ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson set_light = set_light_attention; 287ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson else 288ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson return -EINVAL; 289ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 290ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson pthread_once(&g_init, init_globals); 291ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 292ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson struct light_device_t *dev = malloc(sizeof(struct light_device_t)); 2939caaa41be6c1f3ceb52a2748c8f13c48b8aee848Manoj Kumar AVM 2949caaa41be6c1f3ceb52a2748c8f13c48b8aee848Manoj Kumar AVM if(!dev) 2959caaa41be6c1f3ceb52a2748c8f13c48b8aee848Manoj Kumar AVM return -ENOMEM; 2969caaa41be6c1f3ceb52a2748c8f13c48b8aee848Manoj Kumar AVM 297ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson memset(dev, 0, sizeof(*dev)); 298ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 299ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson dev->common.tag = HARDWARE_DEVICE_TAG; 300ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson dev->common.version = 0; 301ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson dev->common.module = (struct hw_module_t*)module; 302ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson dev->common.close = (int (*)(struct hw_device_t*))close_lights; 303ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson dev->set_light = set_light; 304ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 305ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson *device = (struct hw_device_t*)dev; 306ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson return 0; 307ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson} 308ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 309ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstatic struct hw_module_methods_t lights_module_methods = { 310ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson .open = open_lights, 311ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson}; 312ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson 313ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson/* 314ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson * The lights Module 315ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson */ 316ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilsonstruct hw_module_t HAL_MODULE_INFO_SYM = { 317ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson .tag = HARDWARE_MODULE_TAG, 318ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson .version_major = 1, 319ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson .version_minor = 0, 320ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson .id = LIGHTS_HARDWARE_MODULE_ID, 321ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson .name = "lights Module", 322ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson .author = "Google, Inc.", 323ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson .methods = &lights_module_methods, 324ef53c1c84ec55ed50f607d52b7abfbb86239408eSimon Wilson}; 325