blob: 1a31765b5b440c0aa54e377f8e94994bccc0b7bd [file] [log] [blame]
// Copyright 2021 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include <lib/zx/channel.h>
#include <lib/zx/stream.h>
#include <lib/zx/vmo.h>
#include <lib/zxio/cpp/inception.h>
#include <zircon/syscalls.h>
#include <zircon/types.h>
#include "private.h"
namespace fio = fuchsia_io;
namespace funknown = fuchsia_unknown;
zx_status_t zxio_create_with_allocator(zx::handle handle, zxio_storage_alloc allocator,
void** out_context) {
zx_info_handle_basic_t handle_info = {};
if (const zx_status_t status = handle.get_info(ZX_INFO_HANDLE_BASIC, &handle_info,
sizeof(handle_info), nullptr, nullptr);
status != ZX_OK) {
return status;
}
zxio_storage_t* storage = nullptr;
zxio_object_type_t type = ZXIO_OBJECT_TYPE_NONE;
switch (handle_info.type) {
case ZX_OBJ_TYPE_CHANNEL: {
fidl::ClientEnd<funknown::Queryable> queryable(zx::channel(std::move(handle)));
zx::result type = zxio_get_object_type(queryable);
if (type.is_error()) {
return type.error_value();
}
zx_status_t status = allocator(type.value(), &storage, out_context);
if (status != ZX_OK || storage == nullptr) {
return ZX_ERR_NO_MEMORY;
}
return zxio_create_with_info(queryable.TakeChannel().release(), &handle_info, storage);
}
case ZX_OBJ_TYPE_LOG: {
type = ZXIO_OBJECT_TYPE_DEBUGLOG;
break;
}
case ZX_OBJ_TYPE_SOCKET: {
type = ZXIO_OBJECT_TYPE_PIPE;
break;
}
case ZX_OBJ_TYPE_VMO: {
type = ZXIO_OBJECT_TYPE_VMO;
break;
}
}
if (const zx_status_t status = allocator(type, &storage, out_context);
status != ZX_OK || storage == nullptr) {
return ZX_ERR_NO_MEMORY;
}
return zxio_create_with_info(handle.release(), &handle_info, storage);
}
zx_status_t zxio_create_with_allocator(fidl::ClientEnd<fuchsia_io::Node> node,
fuchsia_io::wire::NodeInfoDeprecated& info,
zxio_storage_alloc allocator, void** out_context) {
zxio_storage_t* storage = nullptr;
zxio_object_type_t type = ZXIO_OBJECT_TYPE_NONE;
switch (info.Which()) {
case fio::wire::NodeInfoDeprecated::Tag::kDirectory:
type = ZXIO_OBJECT_TYPE_DIR;
break;
case fio::wire::NodeInfoDeprecated::Tag::kFile:
type = ZXIO_OBJECT_TYPE_FILE;
break;
case fio::wire::NodeInfoDeprecated::Tag::kService:
type = ZXIO_OBJECT_TYPE_SERVICE;
break;
#if __Fuchsia_API_level__ >= 18
case fio::wire::NodeInfoDeprecated::Tag::kSymlink:
type = ZXIO_OBJECT_TYPE_SYMLINK;
break;
#endif
}
zx_status_t status = allocator(type, &storage, out_context);
if (status != ZX_OK || storage == nullptr) {
return ZX_ERR_NO_MEMORY;
}
return zxio_create_with_nodeinfo(std::move(node), info, storage);
}