1e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project/******************************************************************************
2e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *
3e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *  Copyright (C) 2012 Broadcom Corporation
4e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *
5e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *  Licensed under the Apache License, Version 2.0 (the "License");
6e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *  you may not use this file except in compliance with the License.
7e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *  You may obtain a copy of the License at:
8e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *
9e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *  http://www.apache.org/licenses/LICENSE-2.0
10e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *
11e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *  Unless required by applicable law or agreed to in writing, software
12e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *  distributed under the License is distributed on an "AS IS" BASIS,
13e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *  See the License for the specific language governing permissions and
15e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *  limitations under the License.
16e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *
17e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project ******************************************************************************/
18e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
19e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project/******************************************************************************
20e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *
21e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *  Encapsulate a condition variable for thread synchronization.
22e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project *
23e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project ******************************************************************************/
24e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project#define LOG_TAG "NfcNciHal"
25e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project#include "OverrideLog.h"
26e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project#include "CondVar.h"
27e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project#include <errno.h>
28be6e6864e012010919062e94a71989efc77592fbElliott Hughes#include <string.h>
29e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
30e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
31e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project/*******************************************************************************
32e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
33e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Function:        CondVar
34e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
35e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Description:     Initialize member variables.
36e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
37e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Returns:         None.
38e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
39e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project*******************************************************************************/
40e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source ProjectCondVar::CondVar ()
41e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project{
428d3c6b9faddfe63303c72dd050e25b9673a6e7d8Colin Cross    pthread_condattr_t attr;
438d3c6b9faddfe63303c72dd050e25b9673a6e7d8Colin Cross    pthread_condattr_init(&attr);
448d3c6b9faddfe63303c72dd050e25b9673a6e7d8Colin Cross    pthread_condattr_setclock(&attr, CLOCK_MONOTONIC);
45e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    memset (&mCondition, 0, sizeof(mCondition));
468d3c6b9faddfe63303c72dd050e25b9673a6e7d8Colin Cross    int const res = pthread_cond_init (&mCondition, &attr);
47e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    if (res)
48e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    {
49e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project        ALOGE ("CondVar::CondVar: fail init; error=0x%X", res);
50e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    }
51e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project}
52e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
53e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
54e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project/*******************************************************************************
55e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
56e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Function:        ~CondVar
57e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
58e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Description:     Cleanup all resources.
59e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
60e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Returns:         None.
61e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
62e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project*******************************************************************************/
63e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source ProjectCondVar::~CondVar ()
64e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project{
65e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    int const res = pthread_cond_destroy (&mCondition);
66e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    if (res)
67e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    {
68e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project        ALOGE ("CondVar::~CondVar: fail destroy; error=0x%X", res);
69e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    }
70e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project}
71e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
72e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
73e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project/*******************************************************************************
74e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
75e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Function:        wait
76e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
77e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Description:     Block the caller and wait for a condition.
78e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
79e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Returns:         None.
80e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
81e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project*******************************************************************************/
82e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Projectvoid CondVar::wait (Mutex& mutex)
83e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project{
84e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    int const res = pthread_cond_wait (&mCondition, mutex.nativeHandle());
85e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    if (res)
86e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    {
87e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project        ALOGE ("CondVar::wait: fail wait; error=0x%X", res);
88e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    }
89e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project}
90e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
91e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
92e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project/*******************************************************************************
93e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
94e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Function:        wait
95e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
96e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Description:     Block the caller and wait for a condition.
97e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**                  millisec: Timeout in milliseconds.
98e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
99e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Returns:         True if wait is successful; false if timeout occurs.
100e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
101e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project*******************************************************************************/
102e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Projectbool CondVar::wait (Mutex& mutex, long millisec)
103e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project{
104e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    bool retVal = false;
105e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    struct timespec absoluteTime;
106e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
107e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    if (clock_gettime (CLOCK_MONOTONIC, &absoluteTime) == -1)
108e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    {
109e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project        ALOGE ("CondVar::wait: fail get time; errno=0x%X", errno);
110e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    }
111e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    else
112e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    {
113e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project        absoluteTime.tv_sec += millisec / 1000;
114e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project        long ns = absoluteTime.tv_nsec + ((millisec % 1000) * 1000000);
115e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project        if (ns > 1000000000)
116e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project        {
117e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project            absoluteTime.tv_sec++;
118e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project            absoluteTime.tv_nsec = ns - 1000000000;
119e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project        }
120e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project        else
121e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project            absoluteTime.tv_nsec = ns;
122e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    }
123e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
1240a85f658ebd49b72be39fe0fb61fcca4ee0fbc82Martijn Coenen    int waitResult = pthread_cond_timedwait (&mCondition, mutex.nativeHandle(), &absoluteTime);
125e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    if ((waitResult != 0) && (waitResult != ETIMEDOUT))
126e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project        ALOGE ("CondVar::wait: fail timed wait; error=0x%X", waitResult);
127e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    retVal = (waitResult == 0); //waited successfully
128e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    return retVal;
129e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project}
130e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
131e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
132e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project/*******************************************************************************
133e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
134e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Function:        notifyOne
135e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
136e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Description:     Unblock the waiting thread.
137e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
138e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project** Returns:         None.
139e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project**
140e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project*******************************************************************************/
141e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Projectvoid CondVar::notifyOne ()
142e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project{
143e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    int const res = pthread_cond_signal (&mCondition);
144e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    if (res)
145e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    {
146e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project        ALOGE ("CondVar::notifyOne: fail signal; error=0x%X", res);
147e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project    }
148e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project}
149e9df6ba5a8fcccf306a80b1670b423be8fe7746The Android Open Source Project
150