Annotation of qemu/audio/mixeng.c, revision 1.1

1.1     ! root        1: /*
        !             2:  * QEMU Mixing engine
        !             3:  *
        !             4:  * Copyright (c) 2004 Vassili Karpov (malc)
        !             5:  * Copyright (c) 1998 Fabrice Bellard
        !             6:  *
        !             7:  * Permission is hereby granted, free of charge, to any person obtaining a copy
        !             8:  * of this software and associated documentation files (the "Software"), to deal
        !             9:  * in the Software without restriction, including without limitation the rights
        !            10:  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
        !            11:  * copies of the Software, and to permit persons to whom the Software is
        !            12:  * furnished to do so, subject to the following conditions:
        !            13:  *
        !            14:  * The above copyright notice and this permission notice shall be included in
        !            15:  * all copies or substantial portions of the Software.
        !            16:  *
        !            17:  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
        !            18:  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
        !            19:  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
        !            20:  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
        !            21:  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
        !            22:  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
        !            23:  * THE SOFTWARE.
        !            24:  */
        !            25: #include "vl.h"
        !            26: //#define DEBUG_FP
        !            27: #include "audio/mixeng.h"
        !            28: 
        !            29: #define IN_T int8_t
        !            30: #define IN_MIN CHAR_MIN
        !            31: #define IN_MAX CHAR_MAX
        !            32: #define SIGNED
        !            33: #include "mixeng_template.h"
        !            34: #undef SIGNED
        !            35: #undef IN_MAX
        !            36: #undef IN_MIN
        !            37: #undef IN_T
        !            38: 
        !            39: #define IN_T uint8_t
        !            40: #define IN_MIN 0
        !            41: #define IN_MAX UCHAR_MAX
        !            42: #include "mixeng_template.h"
        !            43: #undef IN_MAX
        !            44: #undef IN_MIN
        !            45: #undef IN_T
        !            46: 
        !            47: #define IN_T int16_t
        !            48: #define IN_MIN SHRT_MIN
        !            49: #define IN_MAX SHRT_MAX
        !            50: #define SIGNED
        !            51: #include "mixeng_template.h"
        !            52: #undef SIGNED
        !            53: #undef IN_MAX
        !            54: #undef IN_MIN
        !            55: #undef IN_T
        !            56: 
        !            57: #define IN_T uint16_t
        !            58: #define IN_MIN 0
        !            59: #define IN_MAX USHRT_MAX
        !            60: #include "mixeng_template.h"
        !            61: #undef IN_MAX
        !            62: #undef IN_MIN
        !            63: #undef IN_T
        !            64: 
        !            65: t_sample *mixeng_conv[2][2][2] = {
        !            66:     {
        !            67:         {
        !            68:             conv_uint8_t_to_mono,
        !            69:             conv_uint16_t_to_mono
        !            70:         },
        !            71:         {
        !            72:             conv_int8_t_to_mono,
        !            73:             conv_int16_t_to_mono
        !            74:         }
        !            75:     },
        !            76:     {
        !            77:         {
        !            78:             conv_uint8_t_to_stereo,
        !            79:             conv_uint16_t_to_stereo
        !            80:         },
        !            81:         {
        !            82:             conv_int8_t_to_stereo,
        !            83:             conv_int16_t_to_stereo
        !            84:         }
        !            85:     }
        !            86: };
        !            87: 
        !            88: f_sample *mixeng_clip[2][2][2] = {
        !            89:     {
        !            90:         {
        !            91:             clip_uint8_t_from_mono,
        !            92:             clip_uint16_t_from_mono
        !            93:         },
        !            94:         {
        !            95:             clip_int8_t_from_mono,
        !            96:             clip_int16_t_from_mono
        !            97:         }
        !            98:     },
        !            99:     {
        !           100:         {
        !           101:             clip_uint8_t_from_stereo,
        !           102:             clip_uint16_t_from_stereo
        !           103:         },
        !           104:         {
        !           105:             clip_int8_t_from_stereo,
        !           106:             clip_int16_t_from_stereo
        !           107:         }
        !           108:     }
        !           109: };
        !           110: 
        !           111: /*
        !           112:  * August 21, 1998
        !           113:  * Copyright 1998 Fabrice Bellard.
        !           114:  *
        !           115:  * [Rewrote completly the code of Lance Norskog And Sundry
        !           116:  * Contributors with a more efficient algorithm.]
        !           117:  *
        !           118:  * This source code is freely redistributable and may be used for
        !           119:  * any purpose.  This copyright notice must be maintained. 
        !           120:  * Lance Norskog And Sundry Contributors are not responsible for 
        !           121:  * the consequences of using this software.  
        !           122:  */
        !           123: 
        !           124: /*
        !           125:  * Sound Tools rate change effect file.
        !           126:  */
        !           127: /*
        !           128:  * Linear Interpolation.
        !           129:  *
        !           130:  * The use of fractional increment allows us to use no buffer. It
        !           131:  * avoid the problems at the end of the buffer we had with the old
        !           132:  * method which stored a possibly big buffer of size
        !           133:  * lcm(in_rate,out_rate).
        !           134:  *
        !           135:  * Limited to 16 bit samples and sampling frequency <= 65535 Hz. If
        !           136:  * the input & output frequencies are equal, a delay of one sample is
        !           137:  * introduced.  Limited to processing 32-bit count worth of samples.
        !           138:  *
        !           139:  * 1 << FRAC_BITS evaluating to zero in several places.  Changed with
        !           140:  * an (unsigned long) cast to make it safe.  MarkMLl 2/1/99
        !           141:  */
        !           142: 
        !           143: /* Private data */
        !           144: typedef struct ratestuff {
        !           145:     uint64_t opos;
        !           146:     uint64_t opos_inc;
        !           147:     uint32_t ipos;              /* position in the input stream (integer) */
        !           148:     st_sample_t ilast;          /* last sample in the input stream */
        !           149: } *rate_t;
        !           150: 
        !           151: /*
        !           152:  * Prepare processing.
        !           153:  */
        !           154: void *st_rate_start (int inrate, int outrate)
        !           155: {
        !           156:     rate_t rate = (rate_t) qemu_mallocz (sizeof (struct ratestuff));
        !           157: 
        !           158:     if (!rate) {
        !           159:         exit (EXIT_FAILURE);
        !           160:     }
        !           161: 
        !           162:     if (inrate == outrate) {
        !           163:         // exit (EXIT_FAILURE);
        !           164:     }
        !           165: 
        !           166:     if (inrate >= 65535 || outrate >= 65535) {
        !           167:         // exit (EXIT_FAILURE);
        !           168:     }
        !           169: 
        !           170:     rate->opos = 0;
        !           171: 
        !           172:     /* increment */
        !           173:     rate->opos_inc = (inrate * ((int64_t) UINT_MAX)) / outrate;
        !           174: 
        !           175:     rate->ipos = 0;
        !           176:     rate->ilast.l = 0;
        !           177:     rate->ilast.r = 0;
        !           178:     return rate;
        !           179: }
        !           180: 
        !           181: /*
        !           182:  * Processed signed long samples from ibuf to obuf.
        !           183:  * Return number of samples processed.
        !           184:  */
        !           185: void st_rate_flow (void *opaque, st_sample_t *ibuf, st_sample_t *obuf,
        !           186:                    int *isamp, int *osamp)
        !           187: {
        !           188:     rate_t rate = (rate_t) opaque;
        !           189:     st_sample_t *istart, *iend;
        !           190:     st_sample_t *ostart, *oend;
        !           191:     st_sample_t ilast, icur, out;
        !           192:     int64_t t;
        !           193: 
        !           194:     ilast = rate->ilast;
        !           195: 
        !           196:     istart = ibuf;
        !           197:     iend = ibuf + *isamp;
        !           198: 
        !           199:     ostart = obuf;
        !           200:     oend = obuf + *osamp;
        !           201: 
        !           202:     if (rate->opos_inc == 1ULL << 32) {
        !           203:         int i, n = *isamp > *osamp ? *osamp : *isamp;
        !           204:         for (i = 0; i < n; i++) {
        !           205:             obuf[i].l += ibuf[i].r;
        !           206:             obuf[i].r += ibuf[i].r;
        !           207:         }
        !           208:         *isamp = n;
        !           209:         *osamp = n;
        !           210:         return;
        !           211:     }
        !           212: 
        !           213:     while (obuf < oend) {
        !           214: 
        !           215:         /* Safety catch to make sure we have input samples.  */
        !           216:         if (ibuf >= iend)
        !           217:             break;
        !           218: 
        !           219:         /* read as many input samples so that ipos > opos */
        !           220: 
        !           221:         while (rate->ipos <= (rate->opos >> 32)) {
        !           222:             ilast = *ibuf++;
        !           223:             rate->ipos++;
        !           224:             /* See if we finished the input buffer yet */
        !           225:             if (ibuf >= iend) goto the_end;
        !           226:         }
        !           227: 
        !           228:         icur = *ibuf;
        !           229: 
        !           230:         /* interpolate */
        !           231:         t = rate->opos & 0xffffffff;
        !           232:         out.l = (ilast.l * (INT_MAX - t) + icur.l * t) / INT_MAX;
        !           233:         out.r = (ilast.r * (INT_MAX - t) + icur.r * t) / INT_MAX;
        !           234: 
        !           235:         /* output sample & increment position */
        !           236: #if 0
        !           237:         *obuf++ = out;
        !           238: #else
        !           239:         obuf->l += out.l;
        !           240:         obuf->r += out.r;
        !           241:         obuf += 1;
        !           242: #endif
        !           243:         rate->opos += rate->opos_inc;
        !           244:     }
        !           245: 
        !           246: the_end:
        !           247:     *isamp = ibuf - istart;
        !           248:     *osamp = obuf - ostart;
        !           249:     rate->ilast = ilast;
        !           250: }
        !           251: 
        !           252: void st_rate_stop (void *opaque)
        !           253: {
        !           254:     qemu_free (opaque);
        !           255: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.