| // Copyright 2018 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/async-loop/default.h> |
| #include <lib/async-loop/loop.h> |
| #include <lib/fidl-async/bind.h> |
| #include <string.h> |
| #include <zircon/fidl.h> |
| #include <zircon/syscalls.h> |
| |
| #include <fidl/test/spaceship/c/fidl.h> |
| #include <zxtest/zxtest.h> |
| |
| static zx_status_t SpaceShip_AdjustHeading(void* ctx, const uint32_t* stars_data, |
| size_t stars_count, fidl_txn_t* txn) { |
| EXPECT_EQ(3u, stars_count, ""); |
| EXPECT_EQ(11u, stars_data[0], ""); |
| EXPECT_EQ(0u, stars_data[1], ""); |
| EXPECT_EQ(UINT32_MAX, stars_data[2], ""); |
| return fidl_test_spaceship_SpaceShipAdjustHeading_reply(txn, -12); |
| } |
| |
| static zx_status_t SpaceShip_ScanForLifeforms(void* ctx, fidl_txn_t* txn) { |
| const uint32_t lifesigns[5] = {42u, 43u, UINT32_MAX, 0u, 9u}; |
| return fidl_test_spaceship_SpaceShipScanForLifeforms_reply(txn, lifesigns, 5); |
| } |
| |
| static zx_status_t SpaceShip_ScanForTensorLifeforms(void* ctx, fidl_txn_t* txn) { |
| uint32_t lifesigns[8][5][3] = {}; |
| // fill the array with increasing counter |
| uint32_t counter = 0; |
| for (size_t i = 0; i < 8; i++) { |
| for (size_t j = 0; j < 5; j++) { |
| for (size_t k = 0; k < 3; k++) { |
| lifesigns[i][j][k] = counter; |
| counter += 1; |
| } |
| } |
| } |
| return fidl_test_spaceship_SpaceShipScanForTensorLifeforms_reply(txn, lifesigns); |
| } |
| |
| static zx_status_t SpaceShip_SetAstrometricsListener(void* ctx, zx_handle_t listener) { |
| EXPECT_EQ(ZX_OK, fidl_test_spaceship_AstrometricsListenerOnNova(listener), ""); |
| EXPECT_EQ(ZX_OK, zx_handle_close(listener), ""); |
| return ZX_OK; |
| } |
| |
| static zx_status_t SpaceShip_SetDefenseCondition(void* ctx, fidl_test_spaceship_Alert alert) { |
| EXPECT_EQ(fidl_test_spaceship_Alert_RED, alert, ""); |
| return ZX_OK; |
| } |
| |
| static zx_status_t SpaceShip_GetFuelRemaining(void* ctx, zx_handle_t cancel, fidl_txn_t* txn) { |
| EXPECT_EQ(ZX_HANDLE_INVALID, cancel, ""); |
| const fidl_test_spaceship_FuelLevel level = { |
| .reaction_mass = 1641u, |
| }; |
| return fidl_test_spaceship_SpaceShipGetFuelRemaining_reply(txn, ZX_OK, &level); |
| } |
| |
| static zx_status_t SpaceShip_AddFuelTank(void* ctx, const fidl_test_spaceship_FuelLevel* level, |
| fidl_txn_t* txn) { |
| return fidl_test_spaceship_SpaceShipAddFuelTank_reply(txn, level->reaction_mass / 2); |
| } |
| |
| static const fidl_test_spaceship_SpaceShip_ops_t kOps = { |
| .AdjustHeading = SpaceShip_AdjustHeading, |
| .ScanForLifeforms = SpaceShip_ScanForLifeforms, |
| .SetAstrometricsListener = SpaceShip_SetAstrometricsListener, |
| .SetDefenseCondition = SpaceShip_SetDefenseCondition, |
| .GetFuelRemaining = SpaceShip_GetFuelRemaining, |
| .AddFuelTank = SpaceShip_AddFuelTank, |
| .ScanForTensorLifeforms = SpaceShip_ScanForTensorLifeforms, |
| }; |
| |
| TEST(SpaceshipTests, spaceship_test) { |
| zx_handle_t client, server; |
| zx_status_t status = zx_channel_create(0, &client, &server); |
| ASSERT_EQ(ZX_OK, status, ""); |
| |
| async_loop_t* loop = NULL; |
| ASSERT_EQ(ZX_OK, async_loop_create(&kAsyncLoopConfigNoAttachToCurrentThread, &loop), ""); |
| ASSERT_EQ(ZX_OK, async_loop_start_thread(loop, "spaceship-dispatcher", NULL), ""); |
| |
| async_dispatcher_t* dispatcher = async_loop_get_dispatcher(loop); |
| fidl_bind(dispatcher, server, (fidl_dispatch_t*)fidl_test_spaceship_SpaceShip_dispatch, NULL, |
| &kOps); |
| |
| { |
| const uint32_t stars[3] = {11u, 0u, UINT32_MAX}; |
| int8_t result = 0; |
| ASSERT_EQ(ZX_OK, fidl_test_spaceship_SpaceShipAdjustHeading(client, stars, 3, &result), ""); |
| ASSERT_EQ(-12, result, ""); |
| } |
| |
| { |
| const uint32_t num_stars_overflow = fidl_test_spaceship_MaxStarsAdjustHeading * 2; |
| const uint32_t stars[num_stars_overflow]; |
| int8_t result = 0; |
| ASSERT_EQ( |
| ZX_ERR_INVALID_ARGS, |
| fidl_test_spaceship_SpaceShipAdjustHeading(client, stars, num_stars_overflow, &result), ""); |
| } |
| |
| { |
| int8_t result = 0; |
| ASSERT_EQ(ZX_ERR_INVALID_ARGS, |
| fidl_test_spaceship_SpaceShipAdjustHeading(client, NULL, 1u << 31, &result), ""); |
| } |
| |
| { |
| uint32_t lifesigns[64]; |
| size_t actual = 0; |
| ASSERT_EQ(ZX_OK, fidl_test_spaceship_SpaceShipScanForLifeforms(client, lifesigns, 64, &actual), |
| ""); |
| ASSERT_EQ(5u, actual, ""); |
| ASSERT_EQ(42u, lifesigns[0], ""); |
| ASSERT_EQ(43u, lifesigns[1], ""); |
| ASSERT_EQ(UINT32_MAX, lifesigns[2], ""); |
| ASSERT_EQ(0u, lifesigns[3], ""); |
| ASSERT_EQ(9u, lifesigns[4], ""); |
| } |
| |
| { |
| uint32_t lifesigns[8][5][3]; |
| ASSERT_EQ(ZX_OK, fidl_test_spaceship_SpaceShipScanForTensorLifeforms(client, lifesigns), ""); |
| uint32_t counter = 0; |
| for (size_t i = 0; i < 8; i++) { |
| for (size_t j = 0; j < 5; j++) { |
| for (size_t k = 0; k < 3; k++) { |
| ASSERT_EQ(counter, lifesigns[i][j][k], ""); |
| counter += 1; |
| } |
| } |
| } |
| } |
| |
| { |
| zx_handle_t listener_client, listener_server; |
| status = zx_channel_create(0, &listener_client, &listener_server); |
| ASSERT_EQ(ZX_OK, status, ""); |
| ASSERT_EQ(ZX_OK, fidl_test_spaceship_SpaceShipSetAstrometricsListener(client, listener_client), |
| ""); |
| ASSERT_EQ(ZX_OK, |
| zx_object_wait_one(listener_server, ZX_CHANNEL_READABLE, ZX_TIME_INFINITE, NULL), ""); |
| ASSERT_EQ(ZX_OK, zx_handle_close(listener_server), ""); |
| } |
| |
| { |
| ASSERT_EQ( |
| ZX_OK, |
| fidl_test_spaceship_SpaceShipSetDefenseCondition(client, fidl_test_spaceship_Alert_RED), |
| ""); |
| } |
| |
| { |
| fidl_test_spaceship_FuelLevel level; |
| ASSERT_EQ( |
| ZX_OK, |
| fidl_test_spaceship_SpaceShipGetFuelRemaining(client, ZX_HANDLE_INVALID, &status, &level), |
| ""); |
| ASSERT_EQ(ZX_OK, status, ""); |
| ASSERT_EQ(1641u, level.reaction_mass, ""); |
| } |
| |
| { |
| fidl_test_spaceship_FuelLevel level = { |
| .reaction_mass = 9482, |
| }; |
| uint32_t out_consumed = 0u; |
| ASSERT_EQ(ZX_OK, fidl_test_spaceship_SpaceShipAddFuelTank(client, &level, &out_consumed), ""); |
| ASSERT_EQ(4741u, out_consumed, ""); |
| } |
| |
| ASSERT_EQ(ZX_OK, zx_handle_close(client), ""); |
| |
| async_loop_destroy(loop); |
| } |