1ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen/* 2ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * Copyright (C) 2011 The Android Open Source Project 3ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * 4ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * Licensed under the Apache License, Version 2.0 (the "License"); 5ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * you may not use this file except in compliance with the License. 6ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * You may obtain a copy of the License at 7ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * 8ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * http://www.apache.org/licenses/LICENSE-2.0 9ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * 10ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * Unless required by applicable law or agreed to in writing, software 11ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * distributed under the License is distributed on an "AS IS" BASIS, 12ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * See the License for the specific language governing permissions and 14ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen * limitations under the License. 15ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen */ 16ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 17ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen#define LOG_TAG "local_time_hw_default" 18ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen//#define LOG_NDEBUG 0 19ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 20ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen#include <errno.h> 2107c085565a3b24bb658d05b8aa08fb7420725602Elliott Hughes#include <malloc.h> 22ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen#include <stdint.h> 2307c085565a3b24bb658d05b8aa08fb7420725602Elliott Hughes#include <string.h> 2432dde03332e9822d751ab71fc38c7bda48ec811cJiyong Park#include <time.h> 25ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 26d88dfe8607af019186a309674d9081a056ed3daaMark Salyzyn#include <log/log.h> 27ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 28ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen#include <hardware/hardware.h> 29ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen#include <hardware/local_time_hal.h> 30ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 31e8343251f54f54e46c927da852dca9b63a2a016bGreg Kaiser// We only support gcc and clang, both of which support this attribute. 32e8343251f54f54e46c927da852dca9b63a2a016bGreg Kaiser#define UNUSED_ARGUMENT __attribute((unused)) 33e8343251f54f54e46c927da852dca9b63a2a016bGreg Kaiser 34ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chenstruct stub_local_time_device { 35ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen struct local_time_hw_device device; 36ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen}; 37ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 38ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chenstatic int64_t ltdev_get_local_time(struct local_time_hw_device* dev) 39ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen{ 40ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen struct timespec ts; 41ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen uint64_t now; 42ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen int ret; 43ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 44ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen ret = clock_gettime(CLOCK_MONOTONIC, &ts); 45ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen if (ret < 0) { 465ad38a901dcca2961f3ed35ae0b206c13bc515cdMike J. Chen ALOGW("%s failed to fetch CLOCK_MONOTONIC value! (res = %d)", 47ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen dev->common.module->name, ret); 48ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen return 0; 49ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen } 50ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 51ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen now = (((uint64_t)ts.tv_sec) * 1000000000ull) + 52ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen ((uint64_t)ts.tv_nsec); 53ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 54ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen return (int64_t)now; 55ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen} 56ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 57e8343251f54f54e46c927da852dca9b63a2a016bGreg Kaiserstatic uint64_t ltdev_get_local_freq( 58e8343251f54f54e46c927da852dca9b63a2a016bGreg Kaiser struct local_time_hw_device* dev UNUSED_ARGUMENT) 59ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen{ 60ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen // For better or worse, linux clock_gettime routines normalize all clock 61ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen // frequencies to 1GHz 62ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen return 1000000000ull; 63ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen} 64ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 65ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chenstatic int ltdev_close(hw_device_t *device) 66ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen{ 67ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen free(device); 68ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen return 0; 69ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen} 70ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 71ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chenstatic int ltdev_open(const hw_module_t* module, const char* name, 72ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen hw_device_t** device) 73ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen{ 74ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen struct stub_local_time_device *ltdev; 75ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 76ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen if (strcmp(name, LOCAL_TIME_HARDWARE_INTERFACE) != 0) 77ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen return -EINVAL; 78ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 79ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen ltdev = calloc(1, sizeof(struct stub_local_time_device)); 80ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen if (!ltdev) 81ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen return -ENOMEM; 82ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 83ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen ltdev->device.common.tag = HARDWARE_DEVICE_TAG; 84ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen ltdev->device.common.version = 0; 85ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen ltdev->device.common.module = (struct hw_module_t *) module; 86ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen ltdev->device.common.close = ltdev_close; 87ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 88ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen ltdev->device.get_local_time = ltdev_get_local_time; 89ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen ltdev->device.get_local_freq = ltdev_get_local_freq; 90ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen ltdev->device.set_local_slew = NULL; 91ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen ltdev->device.get_debug_log = NULL; 92ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 93ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen *device = <dev->device.common; 94ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 95ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen return 0; 96ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen} 97ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 98ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chenstatic struct hw_module_methods_t hal_module_methods = { 99ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen .open = ltdev_open, 100ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen}; 101ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen 102ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chenstruct local_time_module HAL_MODULE_INFO_SYM = { 103ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen .common = { 104ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen .tag = HARDWARE_MODULE_TAG, 105ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen .version_major = 1, 106ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen .version_minor = 0, 107ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen .id = LOCAL_TIME_HARDWARE_MODULE_ID, 108ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen .name = "Default local_time HW HAL", 109ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen .author = "The Android Open Source Project", 110ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen .methods = &hal_module_methods, 111ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen }, 112ad255ee424e36f1fbf5e92e320328ceae1aecd49Mike J. Chen}; 113