15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync/* $Id$ */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync/** @file
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * Intermediate audio driver header.
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync/*
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * Copyright (C) 2006-2014 Oracle Corporation
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync *
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * This file is part of VirtualBox Open Source Edition (OSE), as
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * available from http://www.virtualbox.org. This file is free software;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * you can redistribute it and/or modify it under the terms of the GNU
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * General Public License (GPL) as published by the Free Software
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * Foundation, in version 2 as it comes in the "COPYING" file of the
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * --------------------------------------------------------------------
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync *
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * This code is based on: audio.h
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync *
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * QEMU Audio subsystem header
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync *
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * Copyright (c) 2003-2005 Vassili Karpov (malc)
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync *
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * Permission is hereby granted, free of charge, to any person obtaining a copy
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * of this software and associated documentation files (the "Software"), to deal
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * in the Software without restriction, including without limitation the rights
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * copies of the Software, and to permit persons to whom the Software is
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * furnished to do so, subject to the following conditions:
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync *
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * The above copyright notice and this permission notice shall be included in
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * all copies or substantial portions of the Software.
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync *
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * THE SOFTWARE.
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync#ifndef DRV_AUDIO_H
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync#define DRV_AUDIO_H
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync#include <limits.h>
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync#include <iprt/circbuf.h>
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync#include <VBox/vmm/pdmdev.h>
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync#include <VBox/vmm/pdm.h>
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync#include <VBox/vmm/pdmaudioifs.h>
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsynctypedef enum
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync{
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync AUD_OPT_INT,
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync AUD_OPT_FMT,
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync AUD_OPT_STR,
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync AUD_OPT_BOOL
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync} audio_option_tag_e;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsynctypedef struct audio_option
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync{
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync const char *name;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync audio_option_tag_e tag;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync void *valp;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync const char *descr;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync int *overridenp;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync int overriden;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync} audio_option;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync/**
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * Audio driver instance data.
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync *
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * @implements PDMIAUDIOCONNECTOR
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsynctypedef struct DRVAUDIO
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync{
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync /** Input/output processing thread. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync RTTHREAD hThread;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync /** Event for input/ouput processing. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync RTSEMEVENT hEvent;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync /** Shutdown indicator. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync bool fTerminate;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync /** The audio interface presented to the device/driver above us. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync PDMIAUDIOCONNECTOR IAudioConnector;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync /** Pointer to the driver instance. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync PPDMDRVINS pDrvIns;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync /** Pointer to audio driver below us. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync PPDMIHOSTAUDIO pHostDrvAudio;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync RTLISTANCHOR lstHstStrmIn;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync RTLISTANCHOR lstHstStrmOut;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync /** Max. number of free input streams. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync uint8_t cFreeInputStreams;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync /** Max. number of free output streams. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync uint8_t cFreeOutputStreams;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync /** Audio configuration settings retrieved
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync * from the backend. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync PDMAUDIOBACKENDCFG BackendCfg;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync} DRVAUDIO, *PDRVAUDIO;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync/** Makes a PDRVBLOCK out of a PPDMIBLOCK. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync#define PDMIAUDIOCONNECTOR_2_DRVAUDIO(pInterface) \
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync ( (PDRVAUDIO)((uintptr_t)pInterface - RT_OFFSETOF(DRVAUDIO, IAudioConnector)) )
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync//const char *drvAudioHlpFormatToString(PDMAUDIOFMT fmt);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncconst char *drvAudioRecSourceToString(PDMAUDIORECSOURCE enmRecSource);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncPDMAUDIOFMT drvAudioHlpStringToFormat(const char *pszFormat);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncbool drvAudioPCMPropsAreEqual(PPDMPCMPROPS info, PPDMAUDIOSTREAMCFG pCfg);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncint drvAudioStreamCfgToProps(PPDMAUDIOSTREAMCFG pCfg, PPDMPCMPROPS pProps);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncvoid drvAudioStreamCfgPrint(PPDMAUDIOSTREAMCFG pCfg);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync/* AUDIO IN function declarations. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncvoid drvAudioHlpPcmSwFreeResourcesIn(PPDMAUDIOGSTSTRMIN pGstStrmIn);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncvoid drvAudioGstInFreeRes(PPDMAUDIOGSTSTRMIN pGstStrmIn);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncvoid drvAudioGstInRemove(PPDMAUDIOGSTSTRMIN pGstStrmIn);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncuint32_t drvAudioHstInFindMinCaptured(PPDMAUDIOHSTSTRMIN pHstStrmIn);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncvoid drvAudioHstInFreeRes(PPDMAUDIOHSTSTRMIN pHstStrmIn);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncuint32_t drvAudioHstInGetFree(PPDMAUDIOHSTSTRMIN pHstStrmIn);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncuint32_t drvAudioHstInGetLive(PPDMAUDIOHSTSTRMIN pHstStrmIn);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncvoid drvAudioGstInRemove(PPDMAUDIOGSTSTRMIN pGstStrmIn);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncint drvAudioGstInInit(PPDMAUDIOGSTSTRMIN pGstStrmIn, PPDMAUDIOHSTSTRMIN pHstStrmIn, const char *pszName, PPDMAUDIOSTREAMCFG pCfg);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncPPDMAUDIOHSTSTRMIN drvAudioFindNextHstIn(PDRVAUDIO pDrvAudio, PPDMAUDIOHSTSTRMIN pHstStrmIn);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncPPDMAUDIOHSTSTRMIN drvAudioFindNextEnabledHstIn(PDRVAUDIO pDrvAudio, PPDMAUDIOHSTSTRMIN pHstStrmIn);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncPPDMAUDIOHSTSTRMIN drvAudioFindNextEqHstIn(PDRVAUDIO pDrvAudio, PPDMAUDIOHSTSTRMIN pHstStrmIn, PPDMAUDIOSTREAMCFG pCfg);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync/* AUDIO OUT function declarations. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncint drvAudioGstOutAlloc(PPDMAUDIOGSTSTRMOUT pGstStrmOut);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncvoid drvAudioGstOutFreeRes(PPDMAUDIOGSTSTRMOUT pGstStrmOut);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncvoid drvAudioHstOutFreeRes(PPDMAUDIOHSTSTRMOUT pHstStrmOut);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncint drvAudioDestroyGstOut(PDRVAUDIO pDrvAudio, PPDMAUDIOGSTSTRMOUT pGstStrmOut);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncvoid drvAudioDestroyHstOut(PDRVAUDIO pDrvAudio, PDMAUDIOHSTSTRMOUT pHstStrmOut);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncint drvAudioGstOutInit(PPDMAUDIOGSTSTRMOUT pGstStrmOut, PPDMAUDIOHSTSTRMOUT pHstStrmOut, const char *pszName, PPDMAUDIOSTREAMCFG pCfg);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncPPDMAUDIOHSTSTRMOUT drvAudioFindAnyHstOut(PDRVAUDIO pDrvAudio, PPDMAUDIOHSTSTRMOUT pHstStrmOut);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncPPDMAUDIOHSTSTRMOUT drvAudioHstFindAnyEnabledOut(PDRVAUDIO pDrvAudio, PPDMAUDIOHSTSTRMOUT pHstStrmOut);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncPPDMAUDIOHSTSTRMOUT drvAudioFindSpecificOut(PDRVAUDIO pDrvAudio, PPDMAUDIOHSTSTRMOUT pHstStrmOut, PPDMAUDIOSTREAMCFG pCfg);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncint drvAudioAllocHstOut(PDRVAUDIO pDrvAudio, const char *pszName, PPDMAUDIOSTREAMCFG pCfg, PPDMAUDIOHSTSTRMOUT *ppHstStrmOut);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncint drvAudioHlpPcmHwAddOut(PDRVAUDIO pDrvAudio, PPDMAUDIOSTREAMCFG pCfg, PPDMAUDIOHSTSTRMOUT *ppHstStrmOut);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncint drvAudioHlpPcmCreateVoicePairOut(PDRVAUDIO pDrvAudio, const char *pszName, PPDMAUDIOSTREAMCFG pCfg, PPDMAUDIOGSTSTRMOUT *ppGstStrmOut);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync/* Common functions between DrvAudio and backends (host audio drivers). */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncint drvAudioAttachCapture(PDRVAUDIO pDrvAudio, PPDMAUDIOHSTSTRMOUT pHstStrmOut);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncvoid drvAudioDetachCapture(PPDMAUDIOHSTSTRMOUT pHstStrmOut);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncuint32_t drvAudioHstOutSamplesLive(PPDMAUDIOHSTSTRMOUT pHstStrmOut, uint32_t *pcStreamsLive);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncvoid audio_pcm_info_clear_buf(PPDMPCMPROPS pPCMInfo, void *pvBuf, int len);
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsynctypedef struct fixed_settings
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync{
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync int enabled;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync int cStreams;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync int greedy;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync PDMAUDIOSTREAMCFG settings;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync} fixed_settings;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsyncstatic struct {
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync struct fixed_settings fixed_out;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync struct fixed_settings fixed_in;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync union {
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync int hz;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync int64_t ticks;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync } period;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync int plive;
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync} conf = {
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync /* Fixed output settings. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync { /* DAC fixed settings */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync 1, /* enabled */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync 1, /* cStreams */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync 1, /* greedy */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync {
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync 44100, /* freq */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync 2, /* nchannels */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync AUD_FMT_S16, /* fmt */
10258d88c40d8254a2a0d89e9b6c1f3b487f5c2dvboxsync PDMAUDIOHOSTENDIANNESS
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync }
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync },
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync /* Fixed input settings. */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync { /* ADC fixed settings */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync 1, /* enabled */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync 2, /* cStreams */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync 1, /* greedy */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync {
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync 44100, /* freq */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync 2, /* nchannels */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync AUD_FMT_S16, /* fmt */
10258d88c40d8254a2a0d89e9b6c1f3b487f5c2dvboxsync PDMAUDIOHOSTENDIANNESS
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync }
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync },
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync { 200 }, /* frequency (in Hz) */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync 0, /* plive */ /** @todo Disable pending live? */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync};
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync#endif /* DRV_AUDIO_H */
15fd6c193acece312cad1846b7c6e1e677b4557fvboxsync