OmniSciDB  2e3a973ef4
GDAL.cpp
Go to the documentation of this file.
1 /*
2  * Copyright 2020 OmniSci, Inc.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #include <ImportExport/GDAL.h>
18 
19 #include <array>
20 #include <string>
21 
22 #include <gdal.h>
23 #include <gdal_priv.h>
24 
25 #include <Logger/Logger.h>
27 
28 namespace import_export {
29 
30 namespace {
31 
32 void gdal_error_handler(CPLErr err_class, int err_no, const char* err_msg) {
33  CHECK(err_class >= CE_None && err_class <= CE_Fatal);
34  static constexpr std::array<const char*, 5> err_class_strings{
35  "Info",
36  "Debug",
37  "Warning",
38  "Failure",
39  "Fatal",
40  };
41  std::string log_msg = std::string("GDAL ") + err_class_strings[err_class] + ": " +
42  err_msg + " (" + std::to_string(err_no) + ")";
43  if (err_class >= CE_Failure) {
44  throw std::runtime_error(log_msg);
45  } else {
46  LOG(INFO) << log_msg;
47  }
48 }
49 
50 } // namespace
51 
52 bool GDAL::initialized_ = false;
53 
54 std::mutex GDAL::init_mutex_;
55 
56 void GDAL::init() {
57  // this should not be called from multiple threads, but...
58  std::lock_guard<std::mutex> guard(init_mutex_);
59 
60  // init under mutex
61  if (!initialized_) {
62  // FIXME(andrewseidl): investigate if CPLPushFinderLocation can be public
63  setenv("GDAL_DATA",
64  std::string(omnisci::get_root_abs_path() + "/ThirdParty/gdal-data").c_str(),
65  true);
66 
67  // configure SSL certificate path (per S3Archive::init_for_read)
68  // in a production build, GDAL and Curl will have been built on
69  // CentOS, so the baked-in system path will be wrong for Ubuntu
70  // and other Linux distros. Unless the user is deliberately
71  // overriding it by setting SSL_CERT_FILE explicitly in the server
72  // environment, we set it to whichever CA bundle directory exists
73  // on the machine we're running on
74  static constexpr std::array<const char*, 6> known_ca_paths{
75  "/etc/ssl/certs/ca-certificates.crt",
76  "/etc/pki/tls/certs/ca-bundle.crt",
77  "/usr/share/ssl/certs/ca-bundle.crt",
78  "/usr/local/share/certs/ca-root.crt",
79  "/etc/ssl/cert.pem",
80  "/etc/ssl/ca-bundle.pem"};
81  for (const auto& known_ca_path : known_ca_paths) {
82  if (boost::filesystem::exists(known_ca_path)) {
83  LOG(INFO) << "GDAL SSL Certificate path: " << known_ca_path;
84  setenv("SSL_CERT_FILE", known_ca_path, false); // no overwrite
85  break;
86  }
87  }
88 
89  GDALAllRegister();
90  OGRRegisterAll();
91  CPLSetErrorHandler(*gdal_error_handler);
92  LOG(INFO) << "GDAL Initialized: " << GDALVersionInfo("--version");
93  initialized_ = true;
94  }
95 }
96 
98 #if (GDAL_VERSION_MAJOR > 2) || (GDAL_VERSION_MAJOR == 2 && GDAL_VERSION_MINOR >= 2)
99  return true;
100 #else
101  return false;
102 #endif
103 }
104 
105 bool GDAL::supportsDriver(const char* driver_name) {
106  init();
107  return GetGDALDriverManager()->GetDriverByName(driver_name) != nullptr;
108 }
109 
110 } // namespace import_export
#define LOG(tag)
Definition: Logger.h:188
static std::mutex init_mutex_
Definition: GDAL.h:31
static void init()
Definition: GDAL.cpp:56
void gdal_error_handler(CPLErr err_class, int err_no, const char *err_msg)
Definition: GDAL.cpp:32
std::string to_string(char const *&&v)
static bool supportsDriver(const char *driver_name)
Definition: GDAL.cpp:105
static bool initialized_
Definition: GDAL.h:30
static bool supportsNetworkFileAccess()
Definition: GDAL.cpp:97
#define CHECK(condition)
Definition: Logger.h:197
std::string get_root_abs_path()