Welcome to mirror list, hosted at ThFree Co, Russian Federation.

rint-clip.h « src - github.com/alexmarsev/soxr.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
blob: 06764a8f041c5275dcf8aed77259db7b2d7b4e92 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
/* SoX Resampler Library      Copyright (c) 2007-13 robs@users.sourceforge.net
 * Licence for this file: LGPL v2.1                  See LICENCE for details. */

#if defined DITHER

#define DITHERING (1./32)*(int)(((ran1>>=3)&31)-((ran2>>=3)&31))
#define DITHER_RAND (seed = 1664525UL * seed + 1013904223UL) >> 3
#define DITHER_VARS unsigned long ran1 = DITHER_RAND, ran2 = DITHER_RAND
#define SEED_ARG , unsigned long * seed0
#define SAVE_SEED *seed0 = seed
#define COPY_SEED unsigned long seed = *seed0;
#define COPY_SEED1 unsigned long seed1 = seed
#define PASS_SEED1 , &seed1
#define PASS_SEED  , &seed

#else

#define DITHERING 0
#define DITHER_VARS
#define SEED_ARG
#define SAVE_SEED
#define COPY_SEED
#define COPY_SEED1
#define PASS_SEED1
#define PASS_SEED

#endif



#if defined FE_INVALID && defined FPU_RINT
static void RINT_CLIP(RINT_T * const dest, FLOATX const * const src,
    unsigned stride, size_t i, size_t const n, size_t * const clips SEED_ARG)
{
  COPY_SEED
  DITHER_VARS;
  for (; i < n; ++i) {
    double d = src[i] + DITHERING;
    dest[stride * i] = RINT(d);
    if (fe_test_invalid()) {
      fe_clear_invalid();
      dest[stride * i] = d > 0? RINT_MAX : -RINT_MAX - 1;
      ++*clips;
    }
  }
  SAVE_SEED;
}
#endif



static size_t LSX_RINT_CLIP(void * * const dest0, FLOATX const * const src,
    size_t const n SEED_ARG)
{
  size_t i, clips = 0;
  RINT_T * dest = *dest0;
  COPY_SEED
#if defined FE_INVALID && defined FPU_RINT
#define _ dest[i] = RINT(src[i] + DITHERING), ++i,
  fe_clear_invalid();
  for (i = 0; i < (n & ~7u);) {
    COPY_SEED1;
    DITHER_VARS;
    _ _ _ _ _ _ _ _ (void)0;
    if (fe_test_invalid()) {
      fe_clear_invalid();
      RINT_CLIP(dest, src, 1, i - 8, i, &clips PASS_SEED1);
    }
  }
  RINT_CLIP(dest, src, 1, i, n, &clips PASS_SEED);
#else
#define _ d = src[i] + DITHERING, dest[i++] = (RINT_T)(d > 0? d+.5 >= N? ++clips, N-1 : d+.5 : d-.5 <= -N-1? ++clips, -N:d-.5),
  const double N = 1. + RINT_MAX;
  double d;
  for (i = 0; i < (n & ~7u);) {
    DITHER_VARS;
    _ _ _ _ _ _ _ _ (void)0;
  }
  {
    DITHER_VARS;
    for (; i < n; _ (void)0);
  }
#endif
  SAVE_SEED;
  *dest0 = dest + n;
  return clips;
}
#undef _



static size_t LSX_RINT_CLIP_2(void * * dest0, FLOATX const * const * srcs,
    unsigned const stride, size_t const n SEED_ARG)
{
  unsigned j;
  size_t i, clips = 0;
  RINT_T * dest = *dest0;
  COPY_SEED
#if defined FE_INVALID && defined FPU_RINT
#define _ dest[stride * i] = RINT(src[i] + DITHERING), ++i,
  fe_clear_invalid();
  for (j = 0; j < stride; ++j, ++dest) {
    FLOATX const * const src = srcs[j];
    for (i = 0; i < (n & ~7u);) {
      COPY_SEED1;
      DITHER_VARS;
      _ _ _ _ _ _ _ _ (void)0;
      if (fe_test_invalid()) {
        fe_clear_invalid();
        RINT_CLIP(dest, src, stride, i - 8, i, &clips PASS_SEED1);
      }
    }
    RINT_CLIP(dest, src, stride, i, n, &clips PASS_SEED);
  }
#else
#define _ d = src[i] + DITHERING, dest[stride * i++] = (RINT_T)(d > 0? d+.5 >= N? ++clips, N-1 : d+.5 : d-.5 <= -N-1? ++clips, -N:d-.5),
  const double N = 1. + RINT_MAX;
  double d;
  for (j = 0; j < stride; ++j, ++dest) {
    FLOATX const * const src = srcs[j];
    for (i = 0; i < (n & ~7u);) {
      DITHER_VARS;
      _ _ _ _ _ _ _ _ (void)0;
    }
    {
      DITHER_VARS;
      for (; i < n; _ (void)0);
    }
  }
#endif
  SAVE_SEED;
  *dest0 = dest + stride * (n - 1);
  return clips;
}
#undef _

#undef PASS_SEED
#undef PASS_SEED1
#undef COPY_SEED1
#undef COPY_SEED
#undef SAVE_SEED
#undef SEED_ARG
#undef DITHER_VARS
#undef DITHERING
#undef DITHER

#undef RINT_MAX
#undef RINT_T
#undef FPU_RINT
#undef RINT
#undef RINT_CLIP
#undef LSX_RINT_CLIP
#undef LSX_RINT_CLIP_2