1 /* 2 * Copyright (c) Huawei Technologies Co., Ltd. 2023. All rights reserved. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 #ifndef UNIQUE_FD_H 17 #define UNIQUE_FD_H 18 19 #include <unistd.h> 20 21 namespace OHOS { 22 class DefaultDeleter { 23 public: Close(int fd)24 static void Close(int fd) 25 { 26 if (fd >= 0) { 27 close(fd); 28 } 29 } 30 }; 31 32 template <typename Deleter> 33 class UniqueFdAddDeletor; 34 template <typename Deleter> 35 bool operator==(const int &lhs, const UniqueFdAddDeletor<Deleter> &rhs); 36 template <typename Deleter> 37 bool operator!=(const int &lhs, const UniqueFdAddDeletor<Deleter> &rhs); 38 template <typename Deleter> 39 bool operator>=(const int &lhs, const UniqueFdAddDeletor<Deleter> &rhs); 40 template <typename Deleter> 41 bool operator>(const int &lhs, const UniqueFdAddDeletor<Deleter> &rhs); 42 template <typename Deleter> 43 bool operator<=(const int &lhs, const UniqueFdAddDeletor<Deleter> &rhs); 44 template <typename Deleter> 45 bool operator<(const int &lhs, const UniqueFdAddDeletor<Deleter> &rhs); 46 47 template <typename Deleter = DefaultDeleter> 48 class UniqueFdAddDeletor final { 49 friend bool operator==<Deleter>(const int &lhs, const UniqueFdAddDeletor<Deleter> &rhs); 50 51 friend bool operator!=<Deleter>(const int &lhs, const UniqueFdAddDeletor<Deleter> &rhs); 52 53 friend bool operator>=<Deleter>(const int &lhs, const UniqueFdAddDeletor<Deleter> &rhs); 54 55 friend bool operator><Deleter>(const int &lhs, const UniqueFdAddDeletor<Deleter> &rhs); 56 57 friend bool operator<=<Deleter>(const int &lhs, const UniqueFdAddDeletor<Deleter> &rhs); 58 // clang-format off 59 friend bool operator< <Deleter>(const int& lhs, const UniqueFdAddDeletor<Deleter>& rhs); 60 // clang-format on 61 public: UniqueFdAddDeletor(const int & value)62 explicit UniqueFdAddDeletor(const int &value) : fd_(value) {} UniqueFdAddDeletor()63 UniqueFdAddDeletor() : fd_(-1) {} ~UniqueFdAddDeletor()64 ~UniqueFdAddDeletor() 65 { 66 Reset(-1); 67 } 68 69 // get fd out Release()70 int Release() 71 { 72 int tmp = fd_; 73 fd_ = -1; 74 return tmp; 75 } 76 77 // this is dangerous, when you use it , you should know it, donot operator on the ret 78 operator int() const 79 { 80 return Get(); 81 } // NOLINT 82 // this is dangerous, when you use it , you should know it, donot operator on the ret Get()83 int Get() const 84 { 85 return fd_; 86 } 87 88 // we need move fd from one to another UniqueFdAddDeletor(UniqueFdAddDeletor && rhs)89 UniqueFdAddDeletor(UniqueFdAddDeletor &&rhs) 90 { 91 int rhsfd = rhs.Release(); 92 fd_ = rhsfd; 93 } 94 95 UniqueFdAddDeletor &operator=(UniqueFdAddDeletor &&rhs) 96 { 97 int rhsfd = rhs.Release(); 98 Reset(rhsfd); 99 return *this; 100 } 101 102 bool operator==(const int &rhs) const 103 { 104 return fd_ == rhs; 105 } 106 107 bool operator!=(const int &rhs) const 108 { 109 return !(fd_ == rhs); 110 } 111 bool operator>=(const int &rhs) const 112 { 113 return fd_ >= rhs; 114 } 115 116 bool operator>(const int &rhs) const 117 { 118 return fd_ > rhs; 119 } 120 121 bool operator<=(const int &rhs) const 122 { 123 return fd_ <= rhs; 124 } 125 126 bool operator<(const int &rhs) const 127 { 128 return fd_ < rhs; 129 } 130 131 private: 132 int fd_ = -1; 133 Reset(int newValue)134 void Reset(int newValue) 135 { 136 if (fd_ >= 0) { 137 Deleter::Close(fd_); 138 } 139 fd_ = newValue; 140 } 141 142 // disallow copy ctor and copy assign 143 UniqueFdAddDeletor(const UniqueFdAddDeletor &rhs) = delete; 144 UniqueFdAddDeletor &operator=(const UniqueFdAddDeletor &rhs) = delete; 145 }; 146 147 template <typename Deleter = DefaultDeleter> 148 bool operator==(const int &lhs, const UniqueFdAddDeletor<Deleter> &uniqueFd) 149 { 150 return lhs == uniqueFd.fd_; 151 } 152 153 template <typename Deleter = DefaultDeleter> 154 bool operator!=(const int &lhs, const UniqueFdAddDeletor<Deleter> &uniqueFd) 155 { 156 return !(lhs == uniqueFd.fd_); 157 } 158 159 template <typename Deleter = DefaultDeleter> 160 bool operator>=(const int &lhs, const UniqueFdAddDeletor<Deleter> &uniqueFd) 161 { 162 return lhs >= uniqueFd.fd_; 163 } 164 165 template <typename Deleter = DefaultDeleter> 166 bool operator>(const int &lhs, const UniqueFdAddDeletor<Deleter> &uniqueFd) 167 { 168 return lhs > uniqueFd.fd_; 169 } 170 171 template <typename Deleter = DefaultDeleter> 172 bool operator<=(const int &lhs, const UniqueFdAddDeletor<Deleter> &uniqueFd) 173 { 174 return lhs <= uniqueFd.fd_; 175 } 176 177 template <typename Deleter = DefaultDeleter> 178 bool operator<(const int &lhs, const UniqueFdAddDeletor<Deleter> &uniqueFd) 179 { 180 return lhs < uniqueFd.fd_; 181 } 182 183 using UniqueFd = UniqueFdAddDeletor<DefaultDeleter>; 184 } // namespace OHOS 185 #endif 186