1 /*
2 * Copyright (c) 2022 Huawei Device Co., Ltd.
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
17 #define USE_OPENSSL
18
19 #include <curl/curl.h>
20 #include <thread>
21 #include <pthread.h>
22 #include "upload_hilog_wrapper.h"
23 static pthread_mutex_t *lockarray;
24
25 #ifdef USE_OPENSSL
26 #include <openssl/crypto.h>
27
28 using namespace OHOS::Request::Upload;
LockCallback(int mode,int type,char * file,int line)29 static void LockCallback(int mode, int type, char *file, int line)
30 {
31 (void)file;
32 (void)line;
33 if (mode & CRYPTO_LOCK) {
34 pthread_mutex_lock(&(lockarray[type]));
35 } else {
36 pthread_mutex_unlock(&(lockarray[type]));
37 }
38 }
39
ThreadIdCallback(void)40 static unsigned long ThreadIdCallback(void)
41 {
42 unsigned long ret = static_cast<unsigned long>(pthread_self());
43 return ret;
44 }
45
46 using THREAD_ID_CALLBACK = unsigned long (*)(void);
47 using LOCK_CALLBACK = void (*)(int mode, int type, char *file, int line);
InitLocks(void)48 static void InitLocks(void)
49 {
50 int i;
51 THREAD_ID_CALLBACK threadIdCallback;
52 LOCK_CALLBACK lockCallback;
53 threadIdCallback = ThreadIdCallback;
54 lockCallback = LockCallback;
55 lockarray = (pthread_mutex_t *)OPENSSL_malloc(CRYPTO_num_locks() *
56 sizeof(pthread_mutex_t));
57 for (i = 0; i<CRYPTO_num_locks(); i++) {
58 pthread_mutex_init(&(lockarray[i]), NULL);
59 }
60 CRYPTO_set_id_callback(threadIdCallback);
61 CRYPTO_set_locking_callback(lockCallback);
62 }
63
KillLocks(void)64 static void KillLocks(void)
65 {
66 int i;
67 CRYPTO_set_locking_callback(NULL);
68 for (i = 0; i<CRYPTO_num_locks(); i++) {
69 pthread_mutex_destroy(&(lockarray[i]));
70 }
71 OPENSSL_free(lockarray);
72 }
73 #endif
74
75 class ModuleInit {
76 public:
77 ModuleInit() noexcept;
78 virtual ~ModuleInit();
79 };
80
ModuleInit()81 ModuleInit::ModuleInit() noexcept
82 {
83 curl_global_init(CURL_GLOBAL_ALL);
84 #if defined(USE_OPENSSL)
85 InitLocks();
86 #endif
87 }
88
~ModuleInit()89 ModuleInit::~ModuleInit()
90 {
91 #if defined(USE_OPENSSL)
92 KillLocks();
93 #endif
94 curl_global_cleanup();
95 }
96
97 static ModuleInit mi;
98