/*
 * Copyright © 2015 Red Hat, Inc.
 *
 * Permission is hereby granted, free of charge, to any person obtaining
 * a copy of this software and associated documentation files (the
 * "Software"), to deal in the Software without restriction, including
 * without limitation the rights to use, copy, modify, merge, publish,
 * distribute, sublicense, and/or sell copies of the Software, and to
 * permit persons to whom the Software is furnished to do so, subject to
 * the following conditions:
 *
 * The above copyright notice and this permission notice (including the
 * next paragraph) shall be included in all copies or substantial
 * portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
 * NONINFRINGEMENT.  IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
 * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
 * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
 * SOFTWARE.
 */

#include "config.h"

#include <string.h>
#include "weston-test-client-helper.h"

/**
 * Test (un)plugging devices
 *
 * At the end of each test we must return Weston to the previous state
 * (add all removed devices and remove extra devices), so that
 * the environment is prepared for the other tests too
 */

#define WL_SEAT_CAPABILITY_ALL (WL_SEAT_CAPABILITY_KEYBOARD |\
				WL_SEAT_CAPABILITY_POINTER  |\
				WL_SEAT_CAPABILITY_TOUCH)

char *server_parameters = "--shell=weston-test-desktop-shell.so";

/* simply test if weston sends the right capabilities when
 * some devices are removed */
TEST(seat_capabilities_test)
{
	struct client *cl = create_client_and_test_surface(100, 100, 100, 100);
	assert(cl->input->caps == WL_SEAT_CAPABILITY_ALL);

	assert(cl->input->pointer);
	weston_test_device_release(cl->test->weston_test, "pointer");
	client_roundtrip(cl);
	assert(!cl->input->pointer);
	assert(!(cl->input->caps & WL_SEAT_CAPABILITY_POINTER));

	assert(cl->input->keyboard);
	weston_test_device_release(cl->test->weston_test, "keyboard");
	client_roundtrip(cl);
	assert(!cl->input->keyboard);
	assert(!(cl->input->caps & WL_SEAT_CAPABILITY_KEYBOARD));

	assert(cl->input->touch);
	weston_test_device_release(cl->test->weston_test, "touch");
	client_roundtrip(cl);
	assert(!cl->input->touch);
	assert(!(cl->input->caps & WL_SEAT_CAPABILITY_TOUCH));

	/* restore previous state */
	weston_test_device_add(cl->test->weston_test, "keyboard");
	weston_test_device_add(cl->test->weston_test, "pointer");
	weston_test_device_add(cl->test->weston_test, "touch");
	client_roundtrip(cl);

	assert(cl->input->pointer);
	assert(cl->input->keyboard);
	assert(cl->input->touch);

	/* add extra devices */
	weston_test_device_add(cl->test->weston_test, "keyboard");
	weston_test_device_add(cl->test->weston_test, "pointer");
	weston_test_device_add(cl->test->weston_test, "touch");
	client_roundtrip(cl);

	/* remove extra devices */
	weston_test_device_release(cl->test->weston_test, "keyboard");
	weston_test_device_release(cl->test->weston_test, "pointer");
	weston_test_device_release(cl->test->weston_test, "touch");
	client_roundtrip(cl);

	/* we still should have all the capabilities, since the devices
	 * were doubled */
	assert(cl->input->caps == WL_SEAT_CAPABILITY_ALL);

	assert(cl->input->pointer);
	assert(cl->input->keyboard);
	assert(cl->input->touch);
}

#define COUNT 15
TEST(multiple_device_add_and_remove)
{
	int i;
	struct client *cl = create_client_and_test_surface(100, 100, 100, 100);

	/* add device a lot of times */
	for (i = 0; i < COUNT; ++i) {
		weston_test_device_add(cl->test->weston_test, "keyboard");
		weston_test_device_add(cl->test->weston_test, "pointer");
		weston_test_device_add(cl->test->weston_test, "touch");
	}

	client_roundtrip(cl);

	assert(cl->input->pointer);
	assert(cl->input->keyboard);
	assert(cl->input->touch);

	assert(cl->input->caps == WL_SEAT_CAPABILITY_ALL);

	/* release all new devices */
	for (i = 0; i < COUNT; ++i) {
		weston_test_device_release(cl->test->weston_test, "keyboard");
		weston_test_device_release(cl->test->weston_test, "pointer");
		weston_test_device_release(cl->test->weston_test, "touch");
	}

	client_roundtrip(cl);

	/* there is still one from each device left */
	assert(cl->input->caps == WL_SEAT_CAPABILITY_ALL);

	assert(cl->input->pointer);
	assert(cl->input->keyboard);
	assert(cl->input->touch);
}

TEST(device_release_before_destroy)
{
	struct client *cl = create_client_and_test_surface(100, 100, 100, 100);

	/* we can release pointer when we won't be using it anymore.
	 * Do it and see what happens if the device is destroyed
	 * right after that */
	wl_pointer_release(cl->input->pointer->wl_pointer);
	/* we must free and set to NULL the structures, otherwise
	 * seat capabilities will double-free them */
	free(cl->input->pointer);
	cl->input->pointer = NULL;

	wl_keyboard_release(cl->input->keyboard->wl_keyboard);
	free(cl->input->keyboard);
	cl->input->keyboard = NULL;

	wl_touch_release(cl->input->touch->wl_touch);
	free(cl->input->touch);
	cl->input->touch = NULL;

	weston_test_device_release(cl->test->weston_test, "pointer");
	weston_test_device_release(cl->test->weston_test, "keyboard");
	weston_test_device_release(cl->test->weston_test, "touch");
	client_roundtrip(cl);

	assert(cl->input->caps == 0);

	/* restore previous state */
	weston_test_device_add(cl->test->weston_test, "pointer");
	weston_test_device_add(cl->test->weston_test, "keyboard");
	weston_test_device_add(cl->test->weston_test, "touch");
	client_roundtrip(cl);

	assert(cl->input->caps == WL_SEAT_CAPABILITY_ALL);
}

TEST(device_release_before_destroy_multiple)
{
	int i;

	/* if weston crashed during this test, then there is
	 * some inconsistency */
	for (i = 0; i < 30; ++i) {
		/* Fifty times run the previous test. This will create
		 * fifty clients, because we don't have any
		 * way how to destroy them (worth of adding!). Only one
		 * client will run at a time though and so should have no
		 * effect on the result of the test (after the client
		 * finishes its body, it just 'is' and does nothing). */
		device_release_before_destroy();
	}
}

/* normal work-flow test */
TEST(device_release_after_destroy)
{
	struct client *cl = create_client_and_test_surface(100, 100, 100, 100);

	weston_test_device_release(cl->test->weston_test, "pointer");
	wl_pointer_release(cl->input->pointer->wl_pointer);
	/* we must free the memory manually, otherwise seat.capabilities
	 * will try to free it and will use invalid proxy */
	free(cl->input->pointer);
	cl->input->pointer = NULL;

	client_roundtrip(cl);

	weston_test_device_release(cl->test->weston_test, "keyboard");
	wl_keyboard_release(cl->input->keyboard->wl_keyboard);
	free(cl->input->keyboard);
	cl->input->keyboard = NULL;

	client_roundtrip(cl);

	weston_test_device_release(cl->test->weston_test, "touch");
	wl_touch_release(cl->input->touch->wl_touch);
	free(cl->input->touch);
	cl->input->touch = NULL;

	client_roundtrip(cl);

	assert(cl->input->caps == 0);

	/* restore previous state */
	weston_test_device_add(cl->test->weston_test, "pointer");
	weston_test_device_add(cl->test->weston_test, "keyboard");
	weston_test_device_add(cl->test->weston_test, "touch");
	client_roundtrip(cl);

	assert(cl->input->caps == WL_SEAT_CAPABILITY_ALL);
}

TEST(device_release_after_destroy_multiple)
{
	int i;

	/* if weston crashed during this test, then there is
	 * some inconsistency */
	for (i = 0; i < 30; ++i) {
		device_release_after_destroy();
	}
}

/* see https://bugzilla.gnome.org/show_bug.cgi?id=745008
 * It is a mutter bug, but highly relevant. Weston does not
 * suffer from this bug atm, but it is worth of testing. */
TEST(get_device_after_destroy)
{
	struct client *cl = create_client_and_test_surface(100, 100, 100, 100);
	struct wl_pointer *wl_pointer;
	struct wl_keyboard *wl_keyboard;
	struct wl_touch *wl_touch;

	/* There's a race:
	 *  1) compositor destroys device
	 *  2) client asks for the device, because it has not received
	 *     the new capabilities yet
	 *  3) compositor gets the request with a new_id for the
	 *     destroyed device
	 *  4) client uses the new_id
	 *  5) client gets new capabilities, destroying the objects
	 *
	 * If the compositor just bails out in step 3) and does not
	 * create the resource, then the client gets an error in step 4)
	 * - even though it followed the protocol (it just didn't know
	 * about new capabilities).
	 *
	 * This test simulates this situation
	 */

	/* connection is buffered, so after calling client_roundtrip(),
	 * this whole batch will be delivered to compositor and will
	 * exactly simulate our situation */
	weston_test_device_release(cl->test->weston_test, "pointer");
	wl_pointer = wl_seat_get_pointer(cl->input->wl_seat);
	assert(wl_pointer);

	/* this should be ignored */
	wl_pointer_set_cursor(wl_pointer, 0, NULL, 0, 0);

	/* this should not be ignored */
	wl_pointer_release(wl_pointer);
	client_roundtrip(cl);

	weston_test_device_release(cl->test->weston_test, "keyboard");
	wl_keyboard = wl_seat_get_keyboard(cl->input->wl_seat);
	assert(wl_keyboard);
	wl_keyboard_release(wl_keyboard);
	client_roundtrip(cl);

	weston_test_device_release(cl->test->weston_test, "touch");
	wl_touch = wl_seat_get_touch(cl->input->wl_seat);
	assert(wl_touch);
	wl_touch_release(wl_touch);
	client_roundtrip(cl);

	/* get weston to the previous state */
	weston_test_device_add(cl->test->weston_test, "pointer");
	weston_test_device_add(cl->test->weston_test, "keyboard");
	weston_test_device_add(cl->test->weston_test, "touch");
	client_roundtrip(cl);

	assert(cl->input->caps == WL_SEAT_CAPABILITY_ALL);
}

TEST(get_device_after_destroy_multiple)
{
	int i;

	/* if weston crashed during this test, then there is
	 * some inconsistency */
	for (i = 0; i < 30; ++i) {
		get_device_after_destroy();
	}
}

TEST(seats_have_names)
{
	struct client *cl = create_client_and_test_surface(100, 100, 100, 100);
	struct input *input;

	wl_list_for_each(input, &cl->inputs, link) {
		assert(input->seat_name);
	}
}

TEST(seat_destroy_and_recreate)
{
	struct client *cl = create_client_and_test_surface(100, 100, 100, 100);

	weston_test_device_release(cl->test->weston_test, "seat");
	/* Roundtrip to receive and handle the seat global removal event */
	client_roundtrip(cl);

	assert(!cl->input);

	weston_test_device_add(cl->test->weston_test, "seat");
	/* First roundtrip to send request and receive new seat global */
	client_roundtrip(cl);
	/* Second roundtrip to handle seat events and set up input devices */
	client_roundtrip(cl);

	assert(cl->input);
	assert(cl->input->pointer);
	assert(cl->input->keyboard);
	assert(cl->input->touch);
}
