mix.c 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146
  1. /*
  2. * some code for sample mixing
  3. * (C) notaz, 2006,2007
  4. * (C) kub, 2019,2020 added filtering
  5. *
  6. * This work is licensed under the terms of MAME license.
  7. * See COPYING file in the top-level directory.
  8. */
  9. #include <string.h>
  10. #define MAXOUT (+32767)
  11. #define MINOUT (-32768)
  12. /* limitter */
  13. #define Limit16(val) \
  14. val -= val >> 3; /* reduce level to avoid clipping */ \
  15. if ((short)val != val) val = (val < 0 ? MINOUT : MAXOUT)
  16. int mix_32_to_16l_level;
  17. static struct iir {
  18. int alpha; // alpha for EMA low pass
  19. int y[2]; // filter intermediates
  20. } lfi2, rfi2;
  21. // NB ">>" rounds to -infinity, "/" to 0. To compensate the effect possibly use
  22. // "-(-y>>n)" (round to +infinity) instead of "y>>n" in places.
  23. // NB uses fixpoint; samples mustn't have more than (32-QB) bits. Adding the
  24. // outputs of the sound sources together yields a max. of 18 bits, restricting
  25. // QB to a maximum of 14.
  26. #define QB 12
  27. // NB alpha for DC filtering shouldn't be smaller than 1/(1<<QB) to avoid loss.
  28. // exponential moving average combined DC filter and lowpass filter
  29. // y0[n] = (x[n]-y0[n-1])*alpha+y0[n-1], y1[n] = (y0[n] - y1[n-1])*(1-1/8192)
  30. static inline int filter_band(struct iir *fi2, int x)
  31. {
  32. // low pass. alpha is Q8 to avoid loss by 32 bit overflow.
  33. // fi2->y[0] += ((x<<(QB-8)) - (fi2->y[0]>>8)) * fi2->alpha;
  34. fi2->y[0] += (x - (fi2->y[0]>>QB)) * fi2->alpha;
  35. // DC filter. for alpha=1-1/8192 cutoff ~1HZ, for 1-1/1024 ~7Hz
  36. fi2->y[1] += (fi2->y[0] - fi2->y[1]) >> QB;
  37. return (fi2->y[0] - fi2->y[1]) >> QB;
  38. }
  39. // exponential moving average filter for DC filtering
  40. // y[n] = (x[n]-y[n-1])*(1-1/8192) (corner approx. 1Hz, gain 1)
  41. static inline int filter_exp(struct iir *fi2, int x)
  42. {
  43. fi2->y[1] += ((x << QB) - fi2->y[1]) >> QB;
  44. return x - (fi2->y[1] >> QB);
  45. }
  46. // unfiltered (for testing)
  47. static inline int filter_null(struct iir *fi2, int x)
  48. {
  49. return x;
  50. }
  51. #define filter filter_band
  52. #define mix_32_to_16l_stereo_core(dest, src, count, lv, fl) { \
  53. int l, r; \
  54. struct iir lf = lfi2, rf = rfi2; \
  55. \
  56. for (; count > 0; count--) \
  57. { \
  58. l = r = *dest; \
  59. l += *src++ >> lv; \
  60. r += *src++ >> lv; \
  61. l = fl(&lf, l); \
  62. r = fl(&rf, r); \
  63. Limit16(l); \
  64. Limit16(r); \
  65. *dest++ = l; \
  66. *dest++ = r; \
  67. } \
  68. lfi2 = lf, rfi2 = rf; \
  69. }
  70. void mix_32_to_16l_stereo_lvl(short *dest, int *src, int count)
  71. {
  72. mix_32_to_16l_stereo_core(dest, src, count, mix_32_to_16l_level, filter);
  73. }
  74. void mix_32_to_16l_stereo(short *dest, int *src, int count)
  75. {
  76. mix_32_to_16l_stereo_core(dest, src, count, 0, filter);
  77. }
  78. void mix_32_to_16_mono(short *dest, int *src, int count)
  79. {
  80. int l;
  81. struct iir lf = lfi2;
  82. for (; count > 0; count--)
  83. {
  84. l = *dest;
  85. l += *src++;
  86. l = filter(&lf, l);
  87. Limit16(l);
  88. *dest++ = l;
  89. }
  90. lfi2 = lf;
  91. }
  92. void mix_16h_to_32(int *dest_buf, short *mp3_buf, int count)
  93. {
  94. while (count--)
  95. {
  96. *dest_buf++ += *mp3_buf++ >> 1;
  97. }
  98. }
  99. void mix_16h_to_32_s1(int *dest_buf, short *mp3_buf, int count)
  100. {
  101. count >>= 1;
  102. while (count--)
  103. {
  104. *dest_buf++ += *mp3_buf++ >> 1;
  105. *dest_buf++ += *mp3_buf++ >> 1;
  106. mp3_buf += 1*2;
  107. }
  108. }
  109. void mix_16h_to_32_s2(int *dest_buf, short *mp3_buf, int count)
  110. {
  111. count >>= 1;
  112. while (count--)
  113. {
  114. *dest_buf++ += *mp3_buf++ >> 1;
  115. *dest_buf++ += *mp3_buf++ >> 1;
  116. mp3_buf += 3*2;
  117. }
  118. }
  119. void mix_reset(int alpha_q16)
  120. {
  121. memset(&lfi2, 0, sizeof(lfi2));
  122. memset(&rfi2, 0, sizeof(rfi2));
  123. lfi2.alpha = rfi2.alpha = (0x10000-alpha_q16) >> 4; // filter alpha, Q12
  124. }