view src/thread/riscos/SDL_syscond.c @ 1662:782fd950bd46 SDL-1.3

Revamp of the video system in progress - adding support for multiple displays, multiple windows, and a full video mode selection API. WARNING: None of the video drivers have been updated for the new API yet! The API is still under design and very fluid. The code is now run through a consistent indent format: indent -i4 -nut -nsc -br -ce The headers are being converted to automatically generate doxygen documentation.
author Sam Lantinga <slouken@libsdl.org>
date Sun, 28 May 2006 13:04:16 +0000
parents d910939febfa
children 4da1ee79c9af
line wrap: on
line source

/*
    SDL - Simple DirectMedia Layer
    Copyright (C) 1997-2006 Sam Lantinga

    This library is free software; you can redistribute it and/or
    modify it under the terms of the GNU Lesser General Public
    License as published by the Free Software Foundation; either
    version 2.1 of the License, or (at your option) any later version.

    This library is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
    Lesser General Public License for more details.

    You should have received a copy of the GNU Lesser General Public
    License along with this library; if not, write to the Free Software
    Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA

    Sam Lantinga
    slouken@libsdl.org
*/
#include "SDL_config.h"

/* RISC OS implementations uses pthreads based on linux code */

#if SDL_THREADS_DISABLED
#include "../generic/SDL_syscond.c"
#else
#include <sys/time.h>
#include <unistd.h>
#include <pthread.h>

#include "SDL_thread.h"
#include "SDL_sysmutex_c.h"

struct SDL_cond
{
    pthread_cond_t cond;
};

/* Create a condition variable */
SDL_cond *
SDL_CreateCond (void)
{
    SDL_cond *cond;

    cond = (SDL_cond *) SDL_malloc (sizeof (SDL_cond));
    if (cond) {
        if (pthread_cond_init (&cond->cond, NULL) < 0) {
            SDL_SetError ("pthread_cond_init() failed");
            SDL_free (cond);
            cond = NULL;
        }
    }
    return (cond);
}

/* Destroy a condition variable */
void
SDL_DestroyCond (SDL_cond * cond)
{
    if (cond) {
        pthread_cond_destroy (&cond->cond);
        SDL_free (cond);
    }
}

/* Restart one of the threads that are waiting on the condition variable */
int
SDL_CondSignal (SDL_cond * cond)
{
    int retval;

    if (!cond) {
        SDL_SetError ("Passed a NULL condition variable");
        return -1;
    }

    retval = 0;
    if (pthread_cond_signal (&cond->cond) != 0) {
        SDL_SetError ("pthread_cond_signal() failed");
        retval = -1;
    }
    return retval;
}

/* Restart all threads that are waiting on the condition variable */
int
SDL_CondBroadcast (SDL_cond * cond)
{
    int retval;

    if (!cond) {
        SDL_SetError ("Passed a NULL condition variable");
        return -1;
    }

    retval = 0;
    if (pthread_cond_broadcast (&cond->cond) != 0) {
        SDL_SetError ("pthread_cond_broadcast() failed");
        retval = -1;
    }
    return retval;
}

int
SDL_CondWaitTimeout (SDL_cond * cond, SDL_mutex * mutex, Uint32 ms)
{
    int retval;
    struct timeval delta;
    struct timespec abstime;

    if (!cond) {
        SDL_SetError ("Passed a NULL condition variable");
        return -1;
    }

    gettimeofday (&delta, NULL);

    abstime.tv_sec = delta.tv_sec + (ms / 1000);
    abstime.tv_nsec = (delta.tv_usec + (ms % 1000) * 1000) * 1000;
    if (abstime.tv_nsec > 1000000000) {
        abstime.tv_sec += 1;
        abstime.tv_nsec -= 1000000000;
    }

  tryagain:
    retval = pthread_cond_timedwait (&cond->cond, &mutex->id, &abstime);
    switch (retval) {
    case EINTR:
        goto tryagain;
        break;
    case ETIMEDOUT:
        retval = SDL_MUTEX_TIMEDOUT;
        break;
    case 0:
        break;
    default:
        SDL_SetError ("pthread_cond_timedwait() failed");
        retval = -1;
        break;
    }
    return retval;
}

/* Wait on the condition variable, unlocking the provided mutex.
   The mutex must be locked before entering this function!
 */
int
SDL_CondWait (SDL_cond * cond, SDL_mutex * mutex)
{
    int retval;

    if (!cond) {
        SDL_SetError ("Passed a NULL condition variable");
        return -1;
    }

    retval = 0;
    if (pthread_cond_wait (&cond->cond, &mutex->id) != 0) {
        SDL_SetError ("pthread_cond_wait() failed");
        retval = -1;
    }
    return retval;
}
#endif
/* vi: set ts=4 sw=4 expandtab: */