@Override
    public int freeSlot(AllocationID allocationId, Throwable cause) throws SlotNotFoundException {
        checkStarted();

        TaskSlot<T> taskSlot = getTaskSlot(allocationId);

        if (taskSlot != null) {
            return freeSlotInternal(taskSlot, cause).isDone() ? taskSlot.getIndex() : -1;
        } else {
            throw new SlotNotFoundException(allocationId);
        }
    }
@Test
    void testFreeSlot() throws Exception {
        try (final TaskSlotTable<TaskSlotPayload> taskSlotTable = createTaskSlotTableAndStart(2)) {
            final JobID jobId = new JobID();
            final AllocationID allocationId1 = new AllocationID();
            final AllocationID allocationId2 = new AllocationID();

            assertThat(taskSlotTable.allocateSlot(0, jobId, allocationId1, SLOT_TIMEOUT)).isTrue();
            assertThat(taskSlotTable.allocateSlot(1, jobId, allocationId2, SLOT_TIMEOUT)).isTrue();

            assertThat(taskSlotTable.freeSlot(allocationId2)).isOne();

            Iterator<TaskSlot<TaskSlotPayload>> allocatedSlots =
                    taskSlotTable.getAllocatedSlots(jobId);
            assertThat(allocatedSlots.next().getIndex()).isZero();
            assertThat(allocatedSlots.hasNext()).isFalse();
            assertThat(taskSlotTable.isAllocated(1, jobId, allocationId1)).isFalse();
            assertThat(taskSlotTable.isAllocated(1, jobId, allocationId2)).isFalse();
            assertThat(taskSlotTable.isSlotFree(1)).isTrue();
        }
    }