blob: df8aacc42888f9ddf484d6b46d4136c0594741e1 [file] [log] [blame]
// Licensed to the Apache Software Foundation (ASF) under one
// or more contributor license agreements. See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership. The ASF licenses this file
// to you under the Apache License, Version 2.0 (the
// "License"); you may not use this file except in compliance
// with the License. You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing,
// software distributed under the License is distributed on an
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
// KIND, either express or implied. See the License for the
// specific language governing permissions and limitations
// under the License.
use std::ffi::c_char;
use std::ffi::CString;
use std::ptr;
use ::opendal as od;
#[repr(C)]
#[derive(Debug)]
pub struct FFIResult<T> {
code: FFIErrorCode,
data_ptr: *mut T,
error_message: *mut c_char,
}
#[repr(C)]
#[derive(Debug)]
pub enum FFIErrorCode {
Ok,
FFIError,
Unexpected,
Unsupported,
ConfigInvalid,
NotFound,
PermissionDenied,
IsADirectory,
NotADirectory,
AlreadyExists,
RateLimited,
IsSameFile,
}
impl<T> FFIResult<T> {
pub fn ok(data: T) -> Self {
FFIResult {
code: FFIErrorCode::Ok,
data_ptr: Box::into_raw(Box::new(data)),
error_message: ptr::null_mut(),
}
}
pub fn err(error_message: &str) -> Self {
let c_string = CString::new(error_message).unwrap();
FFIResult {
code: FFIErrorCode::FFIError,
data_ptr: ptr::null_mut(),
error_message: c_string.into_raw(),
}
}
pub fn err_with_source(error_message: &str, source: od::Error) -> Self {
let msg = format!("{error_message}, source error: {source}");
let c_string = CString::new(msg).unwrap();
FFIResult {
code: source.kind().into(),
data_ptr: ptr::null_mut(),
error_message: c_string.into_raw(),
}
}
}
impl From<od::ErrorKind> for FFIErrorCode {
fn from(kind: od::ErrorKind) -> Self {
match kind {
od::ErrorKind::Unexpected => FFIErrorCode::Unexpected,
od::ErrorKind::Unsupported => FFIErrorCode::Unsupported,
od::ErrorKind::ConfigInvalid => FFIErrorCode::ConfigInvalid,
od::ErrorKind::NotFound => FFIErrorCode::NotFound,
od::ErrorKind::PermissionDenied => FFIErrorCode::PermissionDenied,
od::ErrorKind::IsADirectory => FFIErrorCode::IsADirectory,
od::ErrorKind::NotADirectory => FFIErrorCode::NotADirectory,
od::ErrorKind::AlreadyExists => FFIErrorCode::AlreadyExists,
od::ErrorKind::RateLimited => FFIErrorCode::RateLimited,
od::ErrorKind::IsSameFile => FFIErrorCode::IsSameFile,
_ => FFIErrorCode::Unexpected,
}
}
}