/*
 * Copyright (C) 2017 Apple Inc. All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in the
 *    documentation and/or other materials provided with the distribution.
 *
 * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE INC. OR
 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 
 */

#include "config.h"
#include "SynchronousStopTheWorldMutatorScheduler.h"

namespace JSC {

SynchronousStopTheWorldMutatorScheduler::SynchronousStopTheWorldMutatorScheduler()
{
}

SynchronousStopTheWorldMutatorScheduler::~SynchronousStopTheWorldMutatorScheduler()
{
}

MutatorScheduler::State SynchronousStopTheWorldMutatorScheduler::state() const
{
    return m_state;
}

void SynchronousStopTheWorldMutatorScheduler::beginCollection()
{
    RELEASE_ASSERT(m_state == Normal);
    m_state = Stopped;
}

MonotonicTime SynchronousStopTheWorldMutatorScheduler::timeToStop()
{
    return m_state == Normal ? MonotonicTime::infinity() : MonotonicTime::now();
}

MonotonicTime SynchronousStopTheWorldMutatorScheduler::timeToResume()
{
    return m_state == Normal ? MonotonicTime::now() : MonotonicTime::infinity();
}

void SynchronousStopTheWorldMutatorScheduler::endCollection()
{
    RELEASE_ASSERT(m_state == Stopped);
    m_state = Normal;
}

} // namespace JSC

