Logo Search packages:      
Sourcecode: wine-unstable version File versions  Download package

alsa.h

/* Definition for ALSA drivers : wine multimedia system
 *
 * Copyright (C) 2002 Erich Pouech
 * Copyright (C) 2002 Marco Pietrobono
 * Copyright (C) 2003 Christian Costa
 * Copyright (C) 2007 Maarten Lankhorst
 *
 * 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
 */

#ifndef __WINE_CONFIG_H
# error You must include config.h to use this header
#endif

#if defined(HAVE_ALSA) && !defined(__ALSA_H)
#define __ALSA_H

#ifdef interface
#undef interface
#endif

#define ALSA_PCM_NEW_HW_PARAMS_API
#define ALSA_PCM_NEW_SW_PARAMS_API

#ifdef HAVE_ALSA_ASOUNDLIB_H
#include <alsa/asoundlib.h>
#elif defined(HAVE_SYS_ASOUNDLIB_H)
#include <sys/asoundlib.h>
#endif
#ifdef HAVE_SYS_ERRNO_H
#include <sys/errno.h>
#endif

#include "mmreg.h"
#include "dsound.h"
#include "dsdriver.h"

#include "ks.h"
#include "ksmedia.h"
#include "ksguid.h"

/* state diagram for waveOut writing:
 *
 * +---------+-------------+---------------+---------------------------------+
 * |  state  |  function   |     event     |            new state      |
 * +---------+-------------+---------------+---------------------------------+
 * |       | open()        |           | STOPPED                             |
 * | PAUSED  | write()     |           | PAUSED                        |
 * | STOPPED | write()     | <thrd create> | PLAYING                   |
 * | PLAYING | write()     | HEADER        | PLAYING                   |
 * | (other) | write()     | <error>       |                                 |
 * | (any)   | pause()     | PAUSING         | PAUSED                        |
 * | PAUSED  | restart()   | RESTARTING    | PLAYING (if no thrd => STOPPED) |
 * | (any)   | reset()     | RESETTING     | STOPPED                         |
 * | (any)   | close()     | CLOSING         | CLOSED                        |
 * +---------+-------------+---------------+---------------------------------+
 */

/* states of the playing device */
#define     WINE_WS_PLAYING         0
#define     WINE_WS_PAUSED          1
#define     WINE_WS_STOPPED         2
#define WINE_WS_CLOSED        3

/* events to be send to device */
enum win_wm_message {
    WINE_WM_PAUSING = WM_USER + 1, WINE_WM_RESTARTING, WINE_WM_RESETTING, WINE_WM_HEADER,
    WINE_WM_UPDATE, WINE_WM_BREAKLOOP, WINE_WM_CLOSING, WINE_WM_STARTING, WINE_WM_STOPPING
};

typedef struct {
    enum win_wm_message msg; /* message identifier */
    DWORD_PTR param;         /* parameter for this message */
    HANDLE hEvent;           /* if message is synchronous, handle of event for synchro */
} ALSA_MSG;

/* implement an in-process message ring for better performance
 * (compared to passing thru the server)
 * this ring will be used by the input (resp output) record (resp playback) routine
 */
typedef struct {
    ALSA_MSG                  * messages;
    int                         ring_buffer_size;
    int                       msg_tosave;
    int                       msg_toget;
/* Either pipe or event is used, but that is defined in alsa.c,
 * since this is a global header we define both here */
    int                         msg_pipe[2];
    HANDLE                      msg_event;
    CRITICAL_SECTION          msg_crst;
} ALSA_MSG_RING;

typedef struct {
    volatile int        state;                  /* one of the WINE_WS_ manifest constants */
    WAVEOPENDESC        waveDesc;
    WORD                wFlags;
    WAVEFORMATPCMEX           format;

    char*                       pcmname;                /* string name of alsa PCM device */
    char*                       ctlname;                /* string name of alsa control device */
    char                        interface_name[MAXPNAMELEN * 2];

    snd_pcm_t*                  pcm;                    /* handle to ALSA playback device */

    snd_pcm_hw_params_t *       hw_params;

    DWORD                       dwBufferSize;           /* size of whole ALSA buffer in bytes */
    LPWAVEHDR                 lpQueuePtr;       /* start of queued WAVEHDRs (waiting to be notified) */
    LPWAVEHDR                 lpPlayPtr;        /* start of not yet fully played buffers */

    LPWAVEHDR                 lpLoopPtr;              /* pointer of first buffer in loop, if any */
    DWORD               dwLoops;          /* private copy of loop counter */

    DWORD               dwPlayedTotal;          /* number of bytes actually played since opening */
    DWORD               dwWrittenTotal;         /* number of bytes written to ALSA buffer since opening */

    /* synchronization stuff */
    HANDLE              hStartUpEvent;
    HANDLE              hThread;
    DWORD               dwThreadID;
    ALSA_MSG_RING       msgRing;

    /* DirectSound stuff */
    DSDRIVERDESC                ds_desc;
    DSDRIVERCAPS                ds_caps;

    /* Waveout only fields */
    WAVEOUTCAPSW        outcaps;

    snd_hctl_t *                hctl;                    /* control handle for the playback volume */

    snd_pcm_sframes_t           (*write)(snd_pcm_t *, const void *, snd_pcm_uframes_t );

    DWORD               dwPartialOffset;  /* Offset of not yet written bytes in lpPlayPtr */

    /* Wavein only fields */

    WAVEINCAPSW                 incaps;
    DWORD                       dwSupport;

    snd_pcm_sframes_t           (*read)(snd_pcm_t *, void *, snd_pcm_uframes_t );

    DWORD               dwPeriodSize;           /* size of OSS buffer period */
    DWORD               dwTotalRecorded;

}   WINE_WAVEDEV;

/*----------------------------------------------------------------------------
**  Global array of output and input devices, initialized via ALSA_WaveInit
*/
#define WAVEDEV_ALLOC_EXTENT_SIZE       10

/* wavein.c */
extern WINE_WAVEDEV     *WInDev;
extern DWORD            ALSA_WidNumMallocedDevs;
extern DWORD            ALSA_WidNumDevs;

/* waveout.c */
extern WINE_WAVEDEV     *WOutDev;
extern DWORD            ALSA_WodNumMallocedDevs;
extern DWORD            ALSA_WodNumDevs;

/* alsa.c */
int   ALSA_InitRingMessage(ALSA_MSG_RING* omr);
int   ALSA_DestroyRingMessage(ALSA_MSG_RING* omr);
void  ALSA_ResetRingMessage(ALSA_MSG_RING* omr);
void  ALSA_WaitRingMessage(ALSA_MSG_RING* omr, DWORD sleep);
int   ALSA_AddRingMessage(ALSA_MSG_RING* omr, enum win_wm_message msg, DWORD_PTR param, BOOL wait);
int   ALSA_RetrieveRingMessage(ALSA_MSG_RING* omr, enum win_wm_message *msg, DWORD_PTR *param, HANDLE *hEvent);
int   ALSA_CheckSetVolume(snd_hctl_t *hctl, int *out_left, int *out_right, int *out_min, int *out_max, int *out_step, int *new_left, int *new_right);

const char * ALSA_getCmdString(enum win_wm_message msg);
const char * ALSA_getMessage(UINT msg);
const char * ALSA_getFormat(WORD wFormatTag);
BOOL  ALSA_NearMatch(int rate1, int rate2);
DWORD ALSA_bytes_to_mmtime(LPMMTIME lpTime, DWORD position, WAVEFORMATPCMEX* format);
void  ALSA_TraceParameters(snd_pcm_hw_params_t * hw_params, snd_pcm_sw_params_t * sw, int full);
int   ALSA_XRUNRecovery(WINE_WAVEDEV * wwo, int err);
void  ALSA_copyFormat(LPWAVEFORMATEX wf1, LPWAVEFORMATPCMEX wf2);
BOOL  ALSA_supportedFormat(LPWAVEFORMATEX wf);

/* dscapture.c */
DWORD widDsCreate(UINT wDevID, PIDSCDRIVER* drv);
DWORD widDsDesc(UINT wDevID, PDSDRIVERDESC desc);

/* dsoutput.c */
DWORD wodDsCreate(UINT wDevID, PIDSDRIVER* drv);
DWORD wodDsDesc(UINT wDevID, PDSDRIVERDESC desc);

/* midi.c */
extern LONG ALSA_MidiInit(void);

/* waveinit.c */
extern LONG ALSA_WaveInit(void);

#endif /* __ALSA_H */

Generated by  Doxygen 1.6.0   Back to index