blob: bb0d541a002f730aed9ab4e8fdb2f3b9c3d1a047 [file] [log] [blame]
Ramakant Singha1547ee2019-11-20 15:44:42 +05301/*
Dileep Marchyadc8f45d2020-01-13 16:33:50 +05302* Copyright (c) 2019-2020, The Linux Foundation. All rights reserved.
Ramakant Singha1547ee2019-11-20 15:44:42 +05303*
4* Redistribution and use in source and binary forms, with or without
5* modification, are permitted provided that the following conditions are
6* met:
7* * Redistributions of source code must retain the above copyright
8* notice, this list of conditions and the following disclaimer.
9* * Redistributions in binary form must reproduce the above
10* copyright notice, this list of conditions and the following
11* disclaimer in the documentation and/or other materials provided
12* with the distribution.
13* * Neither the name of The Linux Foundation nor the names of its
14* contributors may be used to endorse or promote products derived
15* from this software without specific prior written permission.
16*
17* THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED
18* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
19* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT
20* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
21* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
22* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
24* BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
25* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
26* OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
27* IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28*/
29
30#include <utils/fence.h>
Dileep Marchyadc8f45d2020-01-13 16:33:50 +053031#include <assert.h>
Ramakant Singha1547ee2019-11-20 15:44:42 +053032#include <string>
33
34#define __CLASS__ "Fence"
35
36namespace sdm {
37
Dileep Marchyadc8f45d2020-01-13 16:33:50 +053038#define ASSERT_IF_NO_BUFFER_SYNC(x) if (!x) { assert(false); }
39
Ramakant Singha1547ee2019-11-20 15:44:42 +053040BufferSyncHandler* Fence::buffer_sync_handler_ = nullptr;
41
42Fence::Fence(int fd) : fd_(fd) {
43}
44
45Fence::~Fence() {
46 close(fd_);
47}
48
49void Fence::Set(BufferSyncHandler *buffer_sync_handler) {
50 buffer_sync_handler_ = buffer_sync_handler;
51}
52
53shared_ptr<Fence> Fence::Create(int fd) {
54 // Do not create Fence object for invalid fd, so that nullptr can be used for invalid fences.
55 if (fd < 0) {
56 return nullptr;
57 }
58
59 shared_ptr<Fence> fence(new Fence(fd));
60 if (!fence) {
61 close(fd);
62 }
63
64 return fence;
65}
66
67int Fence::Dup(const shared_ptr<Fence> &fence) {
Dileep Marchyadc8f45d2020-01-13 16:33:50 +053068 return (fence ? dup(fence->fd_) : -1);
69}
Ramakant Singha1547ee2019-11-20 15:44:42 +053070
Dileep Marchyadc8f45d2020-01-13 16:33:50 +053071int Fence::Get(const shared_ptr<Fence> &fence) {
72 return (fence ? fence->fd_ : -1);
Ramakant Singha1547ee2019-11-20 15:44:42 +053073}
74
75shared_ptr<Fence> Fence::Merge(const shared_ptr<Fence> &fence1, const shared_ptr<Fence> &fence2) {
Dileep Marchyadc8f45d2020-01-13 16:33:50 +053076 ASSERT_IF_NO_BUFFER_SYNC(buffer_sync_handler_);
Ramakant Singha1547ee2019-11-20 15:44:42 +053077
Dileep Marchyadc8f45d2020-01-13 16:33:50 +053078 // Sync merge will return a new unique fd if source fds are same.
Ramakant Singha1547ee2019-11-20 15:44:42 +053079 int fd1 = fence1 ? fence1->fd_ : -1;
80 int fd2 = fence2 ? fence2->fd_ : -1;
81 int merged = -1;
82
83 buffer_sync_handler_->SyncMerge(fd1, fd2, &merged);
84
85 return Create(merged);
86}
87
88DisplayError Fence::Wait(const shared_ptr<Fence> &fence) {
Dileep Marchyadc8f45d2020-01-13 16:33:50 +053089 ASSERT_IF_NO_BUFFER_SYNC(buffer_sync_handler_);
Ramakant Singha1547ee2019-11-20 15:44:42 +053090
Dileep Marchyadc8f45d2020-01-13 16:33:50 +053091 return buffer_sync_handler_->SyncWait(Fence::Get(fence), 1000);
Ramakant Singha1547ee2019-11-20 15:44:42 +053092}
93
94DisplayError Fence::Wait(const shared_ptr<Fence> &fence, int timeout) {
Dileep Marchyadc8f45d2020-01-13 16:33:50 +053095 ASSERT_IF_NO_BUFFER_SYNC(buffer_sync_handler_);
Ramakant Singha1547ee2019-11-20 15:44:42 +053096
97 return buffer_sync_handler_->SyncWait(Fence::Get(fence), timeout);
98}
99
Dileep Marchyadc8f45d2020-01-13 16:33:50 +0530100Fence::Status Fence::GetStatus(const shared_ptr<Fence> &fence) {
101 ASSERT_IF_NO_BUFFER_SYNC(buffer_sync_handler_);
102
103 if (!fence) {
104 return Fence::Status::kSignaled;
105 }
106
107 // Treat only timeout error as pending, assume other errors as signaled.
108 return (buffer_sync_handler_->SyncWait(Fence::Get(fence), 0) == kErrorTimeOut ?
109 Fence::Status::kPending : Fence::Status::kSignaled);
110}
111
Ramakant Singha1547ee2019-11-20 15:44:42 +0530112string Fence::GetStr(const shared_ptr<Fence> &fence) {
113 return std::to_string(Fence::Get(fence));
114}
115
Dileep Marchyadc8f45d2020-01-13 16:33:50 +0530116Fence::ScopedRef::~ScopedRef() {
117 for (int dup_fd : dup_fds_) {
118 close(dup_fd);
119 }
120}
121
122int Fence::ScopedRef::Get(const shared_ptr<Fence> &fence) {
123 int dup_fd = Fence::Dup(fence);
124 if (dup_fd >= 0) {
125 dup_fds_.push_back(dup_fd);
126 }
127
128 return dup_fd;
Ramakant Singha1547ee2019-11-20 15:44:42 +0530129}
130
131} // namespace sdm