summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/lcms2_plugin.h2
-rw-r--r--plugins/fast_float/src/fast_16_tethra.c11
-rw-r--r--plugins/fast_float/testbed/fast_float_testbed.c94
-rw-r--r--src/cmsintrp.c480
4 files changed, 222 insertions, 365 deletions
diff --git a/include/lcms2_plugin.h b/include/lcms2_plugin.h
index c36998e..507acd6 100644
--- a/include/lcms2_plugin.h
+++ b/include/lcms2_plugin.h
@@ -286,7 +286,7 @@ typedef union {
#define CMS_LERP_FLAGS_TRILINEAR 0x0100 // Hint only
-#define MAX_INPUT_DIMENSIONS 8
+#define MAX_INPUT_DIMENSIONS 15
typedef struct _cms_interp_struc { // Used on all interpolations. Supplied by lcms2 when calling the interpolation function
diff --git a/plugins/fast_float/src/fast_16_tethra.c b/plugins/fast_float/src/fast_16_tethra.c
index 9252d93..ea07029 100644
--- a/plugins/fast_float/src/fast_16_tethra.c
+++ b/plugins/fast_float/src/fast_16_tethra.c
@@ -340,6 +340,17 @@ cmsBool Optimize16BitRGBTransform(_cmsTransformFn* TransformFn,
// Only on input RGB
if (T_COLORSPACE(*InputFormat) != PT_RGB) return FALSE;
+
+ // If this is a matrix-shaper, the default does already a good job
+ if (cmsPipelineCheckAndRetreiveStages(*Lut, 4,
+ cmsSigCurveSetElemType, cmsSigMatrixElemType, cmsSigMatrixElemType, cmsSigCurveSetElemType,
+ NULL, NULL, NULL, NULL)) return FALSE;
+
+ if (cmsPipelineCheckAndRetreiveStages(*Lut, 2,
+ cmsSigCurveSetElemType, cmsSigCurveSetElemType,
+ NULL, NULL)) return FALSE;
+
+
// Named color pipelines cannot be optimized either
for (mpe = cmsPipelineGetPtrToFirstStage(*Lut);
mpe != NULL;
diff --git a/plugins/fast_float/testbed/fast_float_testbed.c b/plugins/fast_float/testbed/fast_float_testbed.c
index 56ac39c..71f05bc 100644
--- a/plugins/fast_float/testbed/fast_float_testbed.c
+++ b/plugins/fast_float/testbed/fast_float_testbed.c
@@ -30,6 +30,7 @@ typedef struct { cmsUInt8Number r, g, b; } Scanline_rgb8bits;
typedef struct { cmsUInt8Number r, g, b, a; } Scanline_rgba8bits;
typedef struct { cmsUInt16Number r, g, b; } Scanline_rgb16bits;
typedef struct { cmsUInt16Number r, g, b, a; } Scanline_rgba16bits;
+typedef struct { cmsUInt16Number c, m, y, k; } Scanline_cmyk16bits;
typedef struct { cmsUInt16Number r, g, b; } Scanline_rgb15bits;
typedef struct { cmsUInt16Number r, g, b, a; } Scanline_rgba15bits;
typedef struct { cmsUInt16Number r, g, b, a; } Scanline_cmyk15bits;
@@ -1296,6 +1297,51 @@ cmsFloat64Number SpeedTest16bitsRGB(cmsContext ct, cmsHPROFILE hlcmsProfileIn, c
return MPixSec(diff);
}
+static
+cmsFloat64Number SpeedTest16bitsCMYK(cmsContext ct, cmsHPROFILE hlcmsProfileIn, cmsHPROFILE hlcmsProfileOut)
+{
+
+ cmsInt32Number r, g, b, j;
+ clock_t atime;
+ cmsFloat64Number diff;
+ cmsHTRANSFORM hlcmsxform;
+ Scanline_cmyk16bits* In;
+ cmsUInt32Number Mb;
+
+ if (hlcmsProfileIn == NULL || hlcmsProfileOut == NULL)
+ Fail("Unable to open profiles");
+
+ hlcmsxform = cmsCreateTransformTHR(ct, hlcmsProfileIn, TYPE_CMYK_16, hlcmsProfileOut, TYPE_CMYK_16, INTENT_PERCEPTUAL, cmsFLAGS_NOCACHE);
+ cmsCloseProfile(hlcmsProfileIn);
+ cmsCloseProfile(hlcmsProfileOut);
+
+ Mb = 256 * 256 * 256 * sizeof(Scanline_cmyk16bits);
+ In = (Scanline_cmyk16bits*)malloc(Mb);
+
+ j = 0;
+ for (r = 0; r < 256; r++)
+ for (g = 0; g < 256; g++)
+ for (b = 0; b < 256; b++) {
+
+ In[j].c = (cmsUInt16Number)r;
+ In[j].m = (cmsUInt16Number)g;
+ In[j].y = (cmsUInt16Number)b;
+ In[j].k = (cmsUInt16Number)r;
+
+ j++;
+ }
+
+ atime = clock();
+
+ cmsDoTransform(hlcmsxform, In, In, 256 * 256 * 256);
+
+ diff = clock() - atime;
+ free(In);
+
+ cmsDeleteTransform(hlcmsxform);
+ return MPixSec(diff);
+}
+
static
@@ -1332,22 +1378,6 @@ void SpeedTest8(void)
cmsDeleteContext(noPlugin);
}
-#if 0
-static
-void SpeedTest8(void)
-{
- printf("\n\nP E R F O R M A N C E T E S T S 8 B I T S\n");
- printf( "==============================================\n\n");
-
- PerformanceHeader();
- Performance("8 bits on CLUT profiles ", SpeedTest8bitsRGB, 0, "test5.icc", "test3.icc", sizeof(Scanline_rgb8bits), 0);
- Performance("8 bits on Matrix-Shaper profiles", SpeedTest8bitsRGB, 0, "test5.icc", "test0.icc", sizeof(Scanline_rgb8bits), 0);
- Performance("8 bits on same Matrix-Shaper ", SpeedTest8bitsRGB, 0, "test0.icc", "test0.icc", sizeof(Scanline_rgb8bits), 0);
- Performance("8 bits on curves ", SpeedTest8bitsRGB, 0, NULL, NULL, sizeof(Scanline_rgb8bits), 0);
-
-}
-#endif
-
static
void SpeedTest15(void)
@@ -1366,12 +1396,34 @@ void SpeedTest15(void)
static
void SpeedTest16(void)
{
- printf("\n\nP E R F O R M A N C E T E S T S 1 6 B I T S\n");
- printf("================================================\n\n");
+ cmsContext noPlugin = cmsCreateContext(0, 0);
+
+
+ printf("\n\n");
+ printf("P E R F O R M A N C E T E S T S 1 6 B I T S (D E F A U L T)\n");
+ printf("=================================================================\n\n");
+
PerformanceHeader();
- Performance("16 bits on CLUT profiles ", SpeedTest16bitsRGB, 0, "test5.icc", "test3.icc", sizeof(Scanline_rgb15bits), 0);
+
+ Performance("16 bits on CLUT profiles ", SpeedTest16bitsRGB, noPlugin, "test5.icc", "test3.icc", sizeof(Scanline_rgb16bits), 0);
+ Performance("16 bits on Matrix-Shaper profiles", SpeedTest16bitsRGB, noPlugin, "test5.icc", "test0.icc", sizeof(Scanline_rgb16bits), 0);
+ Performance("16 bits on same Matrix-Shaper ", SpeedTest16bitsRGB, noPlugin, "test0.icc", "test0.icc", sizeof(Scanline_rgb16bits), 0);
+ Performance("16 bits on curves ", SpeedTest16bitsRGB, noPlugin, NULL, NULL, sizeof(Scanline_rgb16bits), 0);
+ Performance("16 bits on CMYK CLUT profiles ", SpeedTest16bitsCMYK, noPlugin, "test1.icc", "test2.icc", sizeof(Scanline_cmyk16bits), 0);
+ printf("\n\n");
+ printf("P E R F O R M A N C E T E S T S 1 6 B I T S (P L U G I N)\n");
+ printf("===============================================================\n\n");
+
+
+ Performance("16 bits on CLUT profiles ", SpeedTest16bitsRGB, 0, "test5.icc", "test3.icc", sizeof(Scanline_rgb16bits), 0);
+ Performance("16 bits on Matrix-Shaper profiles", SpeedTest16bitsRGB, 0, "test5.icc", "test0.icc", sizeof(Scanline_rgb16bits), 0);
+ Performance("16 bits on same Matrix-Shaper ", SpeedTest16bitsRGB, 0, "test0.icc", "test0.icc", sizeof(Scanline_rgb16bits), 0);
+ Performance("16 bits on curves ", SpeedTest16bitsRGB, 0, NULL, NULL, sizeof(Scanline_rgb16bits), 0);
+ Performance("16 bits on CMYK CLUT profiles ", SpeedTest16bitsCMYK, 0, "test1.icc", "test2.icc", sizeof(Scanline_cmyk16bits), 0);
+
+
}
// The worst case is used, no cache and all rgb combinations
@@ -1456,10 +1508,6 @@ void SpeedTestFloat(void)
}
-
-
-
-
static
cmsFloat64Number SpeedTestFloatByUsing16BitsRGB(cmsContext ct, cmsHPROFILE hlcmsProfileIn, cmsHPROFILE hlcmsProfileOut)
{
diff --git a/src/cmsintrp.c b/src/cmsintrp.c
index 4fc5c59..cc3f4ae 100644
--- a/src/cmsintrp.c
+++ b/src/cmsintrp.c
@@ -1066,351 +1066,102 @@ void Eval4InputsFloat(const cmsFloat32Number Input[],
}
}
-
-static CMS_NO_SANITIZE
-void Eval5Inputs(CMSREGISTER const cmsUInt16Number Input[],
- CMSREGISTER cmsUInt16Number Output[],
-
- CMSREGISTER const cmsInterpParams* p16)
-{
- const cmsUInt16Number* LutTable = (cmsUInt16Number*) p16 -> Table;
- cmsS15Fixed16Number fk;
- cmsS15Fixed16Number k0, rk;
- int K0, K1;
- const cmsUInt16Number* T;
- cmsUInt32Number i;
- cmsUInt16Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
- cmsInterpParams p1;
-
-
- fk = _cmsToFixedDomain((cmsS15Fixed16Number) Input[0] * p16 -> Domain[0]);
- k0 = FIXED_TO_INT(fk);
- rk = FIXED_REST_TO_INT(fk);
-
- K0 = p16 -> opta[4] * k0;
- K1 = p16 -> opta[4] * (k0 + (Input[0] != 0xFFFFU ? 1 : 0));
-
- p1 = *p16;
- memmove(&p1.Domain[0], &p16 ->Domain[1], 4*sizeof(cmsUInt32Number));
-
- T = LutTable + K0;
- p1.Table = T;
-
- Eval4Inputs(Input + 1, Tmp1, &p1);
-
- T = LutTable + K1;
- p1.Table = T;
-
- Eval4Inputs(Input + 1, Tmp2, &p1);
-
- for (i=0; i < p16 -> nOutputs; i++) {
-
- Output[i] = LinearInterp(rk, Tmp1[i], Tmp2[i]);
- }
-
-}
-
-
-static
-void Eval5InputsFloat(const cmsFloat32Number Input[],
- cmsFloat32Number Output[],
- const cmsInterpParams* p)
-{
- const cmsFloat32Number* LutTable = (cmsFloat32Number*) p -> Table;
- cmsFloat32Number rest;
- cmsFloat32Number pk;
- int k0, K0, K1;
- const cmsFloat32Number* T;
- cmsUInt32Number i;
- cmsFloat32Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
- cmsInterpParams p1;
-
- pk = fclamp(Input[0]) * p->Domain[0];
- k0 = _cmsQuickFloor(pk);
- rest = pk - (cmsFloat32Number) k0;
-
- K0 = p -> opta[4] * k0;
- K1 = K0 + (fclamp(Input[0]) >= 1.0 ? 0 : p->opta[4]);
-
- p1 = *p;
- memmove(&p1.Domain[0], &p ->Domain[1], 4*sizeof(cmsUInt32Number));
-
- T = LutTable + K0;
- p1.Table = T;
-
- Eval4InputsFloat(Input + 1, Tmp1, &p1);
-
- T = LutTable + K1;
- p1.Table = T;
-
- Eval4InputsFloat(Input + 1, Tmp2, &p1);
-
- for (i=0; i < p -> nOutputs; i++) {
-
- cmsFloat32Number y0 = Tmp1[i];
- cmsFloat32Number y1 = Tmp2[i];
-
- Output[i] = y0 + (y1 - y0) * rest;
- }
-}
-
-
-
-static CMS_NO_SANITIZE
-void Eval6Inputs(CMSREGISTER const cmsUInt16Number Input[],
- CMSREGISTER cmsUInt16Number Output[],
- CMSREGISTER const cmsInterpParams* p16)
-{
- const cmsUInt16Number* LutTable = (cmsUInt16Number*) p16 -> Table;
- cmsS15Fixed16Number fk;
- cmsS15Fixed16Number k0, rk;
- int K0, K1;
- const cmsUInt16Number* T;
- cmsUInt32Number i;
- cmsUInt16Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
- cmsInterpParams p1;
-
- fk = _cmsToFixedDomain((cmsS15Fixed16Number) Input[0] * p16 -> Domain[0]);
- k0 = FIXED_TO_INT(fk);
- rk = FIXED_REST_TO_INT(fk);
-
- K0 = p16 -> opta[5] * k0;
- K1 = p16 -> opta[5] * (k0 + (Input[0] != 0xFFFFU ? 1 : 0));
-
- p1 = *p16;
- memmove(&p1.Domain[0], &p16 ->Domain[1], 5*sizeof(cmsUInt32Number));
-
- T = LutTable + K0;
- p1.Table = T;
-
- Eval5Inputs(Input + 1, Tmp1, &p1);
-
- T = LutTable + K1;
- p1.Table = T;
-
- Eval5Inputs(Input + 1, Tmp2, &p1);
-
- for (i=0; i < p16 -> nOutputs; i++) {
-
- Output[i] = LinearInterp(rk, Tmp1[i], Tmp2[i]);
- }
-
-}
-
-
-static
-void Eval6InputsFloat(const cmsFloat32Number Input[],
- cmsFloat32Number Output[],
- const cmsInterpParams* p)
-{
- const cmsFloat32Number* LutTable = (cmsFloat32Number*) p -> Table;
- cmsFloat32Number rest;
- cmsFloat32Number pk;
- int k0, K0, K1;
- const cmsFloat32Number* T;
- cmsUInt32Number i;
- cmsFloat32Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
- cmsInterpParams p1;
-
- pk = fclamp(Input[0]) * p->Domain[0];
- k0 = _cmsQuickFloor(pk);
- rest = pk - (cmsFloat32Number) k0;
-
- K0 = p -> opta[5] * k0;
- K1 = K0 + (fclamp(Input[0]) >= 1.0 ? 0 : p->opta[5]);
-
- p1 = *p;
- memmove(&p1.Domain[0], &p ->Domain[1], 5*sizeof(cmsUInt32Number));
-
- T = LutTable + K0;
- p1.Table = T;
-
- Eval5InputsFloat(Input + 1, Tmp1, &p1);
-
- T = LutTable + K1;
- p1.Table = T;
-
- Eval5InputsFloat(Input + 1, Tmp2, &p1);
-
- for (i=0; i < p -> nOutputs; i++) {
-
- cmsFloat32Number y0 = Tmp1[i];
- cmsFloat32Number y1 = Tmp2[i];
-
- Output[i] = y0 + (y1 - y0) * rest;
- }
+#define EVAL_FNS(N,NM) static CMS_NO_SANITIZE \
+void Eval##N##Inputs(CMSREGISTER const cmsUInt16Number Input[], CMSREGISTER cmsUInt16Number Output[], CMSREGISTER const cmsInterpParams* p16)\
+{\
+ const cmsUInt16Number* LutTable = (cmsUInt16Number*) p16 -> Table;\
+ cmsS15Fixed16Number fk;\
+ cmsS15Fixed16Number k0, rk;\
+ int K0, K1;\
+ const cmsUInt16Number* T;\
+ cmsUInt32Number i;\
+ cmsUInt16Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];\
+ cmsInterpParams p1;\
+\
+ fk = _cmsToFixedDomain((cmsS15Fixed16Number) Input[0] * p16 -> Domain[0]);\
+ k0 = FIXED_TO_INT(fk);\
+ rk = FIXED_REST_TO_INT(fk);\
+\
+ K0 = p16 -> opta[NM] * k0;\
+ K1 = p16 -> opta[NM] * (k0 + (Input[0] != 0xFFFFU ? 1 : 0));\
+\
+ p1 = *p16;\
+ memmove(&p1.Domain[0], &p16 ->Domain[1], NM*sizeof(cmsUInt32Number));\
+\
+ T = LutTable + K0;\
+ p1.Table = T;\
+\
+ Eval##NM##Inputs(Input + 1, Tmp1, &p1);\
+\
+ T = LutTable + K1;\
+ p1.Table = T;\
+\
+ Eval##NM##Inputs(Input + 1, Tmp2, &p1);\
+\
+ for (i=0; i < p16 -> nOutputs; i++) {\
+\
+ Output[i] = LinearInterp(rk, Tmp1[i], Tmp2[i]);\
+ }\
+}\
+\
+static void Eval##N##InputsFloat(const cmsFloat32Number Input[], \
+ cmsFloat32Number Output[],\
+ const cmsInterpParams * p)\
+{\
+ const cmsFloat32Number* LutTable = (cmsFloat32Number*) p -> Table;\
+ cmsFloat32Number rest;\
+ cmsFloat32Number pk;\
+ int k0, K0, K1;\
+ const cmsFloat32Number* T;\
+ cmsUInt32Number i;\
+ cmsFloat32Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];\
+ cmsInterpParams p1;\
+\
+ pk = fclamp(Input[0]) * p->Domain[0];\
+ k0 = _cmsQuickFloor(pk);\
+ rest = pk - (cmsFloat32Number) k0;\
+\
+ K0 = p -> opta[NM] * k0;\
+ K1 = K0 + (fclamp(Input[0]) >= 1.0 ? 0 : p->opta[NM]);\
+\
+ p1 = *p;\
+ memmove(&p1.Domain[0], &p ->Domain[1], NM*sizeof(cmsUInt32Number));\
+\
+ T = LutTable + K0;\
+ p1.Table = T;\
+\
+ Eval##NM##InputsFloat(Input + 1, Tmp1, &p1);\
+\
+ T = LutTable + K1;\
+ p1.Table = T;\
+\
+ Eval##NM##InputsFloat(Input + 1, Tmp2, &p1);\
+\
+ for (i=0; i < p -> nOutputs; i++) {\
+\
+ cmsFloat32Number y0 = Tmp1[i];\
+ cmsFloat32Number y1 = Tmp2[i];\
+\
+ Output[i] = y0 + (y1 - y0) * rest;\
+ }\
}
-static CMS_NO_SANITIZE
-void Eval7Inputs(CMSREGISTER const cmsUInt16Number Input[],
- CMSREGISTER cmsUInt16Number Output[],
- CMSREGISTER const cmsInterpParams* p16)
-{
- const cmsUInt16Number* LutTable = (cmsUInt16Number*) p16 -> Table;
- cmsS15Fixed16Number fk;
- cmsS15Fixed16Number k0, rk;
- int K0, K1;
- const cmsUInt16Number* T;
- cmsUInt32Number i;
- cmsUInt16Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
- cmsInterpParams p1;
-
+/**
+* Thanks to Carles Llopis for the templating idea
+*/
+EVAL_FNS(5, 4)
+EVAL_FNS(6, 5)
+EVAL_FNS(7, 6)
+EVAL_FNS(8, 7)
+EVAL_FNS(9, 8)
+EVAL_FNS(10, 9)
+EVAL_FNS(11, 10)
+EVAL_FNS(12, 11)
+EVAL_FNS(13, 12)
+EVAL_FNS(14, 13)
+EVAL_FNS(15, 14)
- fk = _cmsToFixedDomain((cmsS15Fixed16Number) Input[0] * p16 -> Domain[0]);
- k0 = FIXED_TO_INT(fk);
- rk = FIXED_REST_TO_INT(fk);
-
- K0 = p16 -> opta[6] * k0;
- K1 = p16 -> opta[6] * (k0 + (Input[0] != 0xFFFFU ? 1 : 0));
-
- p1 = *p16;
- memmove(&p1.Domain[0], &p16 ->Domain[1], 6*sizeof(cmsUInt32Number));
-
- T = LutTable + K0;
- p1.Table = T;
-
- Eval6Inputs(Input + 1, Tmp1, &p1);
-
- T = LutTable + K1;
- p1.Table = T;
-
- Eval6Inputs(Input + 1, Tmp2, &p1);
-
- for (i=0; i < p16 -> nOutputs; i++) {
- Output[i] = LinearInterp(rk, Tmp1[i], Tmp2[i]);
- }
-}
-
-
-static
-void Eval7InputsFloat(const cmsFloat32Number Input[],
- cmsFloat32Number Output[],
- const cmsInterpParams* p)
-{
- const cmsFloat32Number* LutTable = (cmsFloat32Number*) p -> Table;
- cmsFloat32Number rest;
- cmsFloat32Number pk;
- int k0, K0, K1;
- const cmsFloat32Number* T;
- cmsUInt32Number i;
- cmsFloat32Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
- cmsInterpParams p1;
-
- pk = fclamp(Input[0]) * p->Domain[0];
- k0 = _cmsQuickFloor(pk);
- rest = pk - (cmsFloat32Number) k0;
-
- K0 = p -> opta[6] * k0;
- K1 = K0 + (fclamp(Input[0]) >= 1.0 ? 0 : p->opta[6]);
-
- p1 = *p;
- memmove(&p1.Domain[0], &p ->Domain[1], 6*sizeof(cmsUInt32Number));
-
- T = LutTable + K0;
- p1.Table = T;
-
- Eval6InputsFloat(Input + 1, Tmp1, &p1);
-
- T = LutTable + K1;
- p1.Table = T;
-
- Eval6InputsFloat(Input + 1, Tmp2, &p1);
-
-
- for (i=0; i < p -> nOutputs; i++) {
-
- cmsFloat32Number y0 = Tmp1[i];
- cmsFloat32Number y1 = Tmp2[i];
-
- Output[i] = y0 + (y1 - y0) * rest;
-
- }
-}
-
-static CMS_NO_SANITIZE
-void Eval8Inputs(CMSREGISTER const cmsUInt16Number Input[],
- CMSREGISTER cmsUInt16Number Output[],
- CMSREGISTER const cmsInterpParams* p16)
-{
- const cmsUInt16Number* LutTable = (cmsUInt16Number*) p16 -> Table;
- cmsS15Fixed16Number fk;
- cmsS15Fixed16Number k0, rk;
- int K0, K1;
- const cmsUInt16Number* T;
- cmsUInt32Number i;
- cmsUInt16Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
- cmsInterpParams p1;
-
- fk = _cmsToFixedDomain((cmsS15Fixed16Number) Input[0] * p16 -> Domain[0]);
- k0 = FIXED_TO_INT(fk);
- rk = FIXED_REST_TO_INT(fk);
-
- K0 = p16 -> opta[7] * k0;
- K1 = p16 -> opta[7] * (k0 + (Input[0] != 0xFFFFU ? 1 : 0));
-
- p1 = *p16;
- memmove(&p1.Domain[0], &p16 ->Domain[1], 7*sizeof(cmsUInt32Number));
-
- T = LutTable + K0;
- p1.Table = T;
-
- Eval7Inputs(Input + 1, Tmp1, &p1);
-
- T = LutTable + K1;
- p1.Table = T;
- Eval7Inputs(Input + 1, Tmp2, &p1);
-
- for (i=0; i < p16 -> nOutputs; i++) {
- Output[i] = LinearInterp(rk, Tmp1[i], Tmp2[i]);
- }
-}
-
-
-
-static
-void Eval8InputsFloat(const cmsFloat32Number Input[],
- cmsFloat32Number Output[],
- const cmsInterpParams* p)
-{
- const cmsFloat32Number* LutTable = (cmsFloat32Number*) p -> Table;
- cmsFloat32Number rest;
- cmsFloat32Number pk;
- int k0, K0, K1;
- const cmsFloat32Number* T;
- cmsUInt32Number i;
- cmsFloat32Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
- cmsInterpParams p1;
-
- pk = fclamp(Input[0]) * p->Domain[0];
- k0 = _cmsQuickFloor(pk);
- rest = pk - (cmsFloat32Number) k0;
-
- K0 = p -> opta[7] * k0;
- K1 = K0 + (fclamp(Input[0]) >= 1.0 ? 0 : p->opta[7]);
-
- p1 = *p;
- memmove(&p1.Domain[0], &p ->Domain[1], 7*sizeof(cmsUInt32Number));
-
- T = LutTable + K0;
- p1.Table = T;
-
- Eval7InputsFloat(Input + 1, Tmp1, &p1);
-
- T = LutTable + K1;
- p1.Table = T;
-
- Eval7InputsFloat(Input + 1, Tmp2, &p1);
-
-
- for (i=0; i < p -> nOutputs; i++) {
-
- cmsFloat32Number y0 = Tmp1[i];
- cmsFloat32Number y1 = Tmp2[i];
-
- Output[i] = y0 + (y1 - y0) * rest;
- }
-}
// The default factory
static
@@ -1511,6 +1262,53 @@ cmsInterpFunction DefaultInterpolatorsFactory(cmsUInt32Number nInputChannels, cm
Interpolation.Lerp16 = Eval8Inputs;
break;
+ case 9:
+ if (IsFloat)
+ Interpolation.LerpFloat = Eval9InputsFloat;
+ else
+ Interpolation.Lerp16 = Eval9Inputs;
+ break;
+
+ case 10:
+ if (IsFloat)
+ Interpolation.LerpFloat = Eval10InputsFloat;
+ else
+ Interpolation.Lerp16 = Eval10Inputs;
+ break;
+
+ case 11:
+ if (IsFloat)
+ Interpolation.LerpFloat = Eval11InputsFloat;
+ else
+ Interpolation.Lerp16 = Eval11Inputs;
+ break;
+
+ case 12:
+ if (IsFloat)
+ Interpolation.LerpFloat = Eval12InputsFloat;
+ else
+ Interpolation.Lerp16 = Eval12Inputs;
+ break;
+
+ case 13:
+ if (IsFloat)
+ Interpolation.LerpFloat = Eval13InputsFloat;
+ else
+ Interpolation.Lerp16 = Eval13Inputs;
+ break;
+
+ case 14:
+ if (IsFloat)
+ Interpolation.LerpFloat = Eval14InputsFloat;
+ else
+ Interpolation.Lerp16 = Eval14Inputs;
+ break;
+
+ case 15:
+ if (IsFloat)
+ Interpolation.LerpFloat = Eval15InputsFloat;
+ else
+ Interpolation.Lerp16 = Eval15Inputs;
break;
default: