The bottleneck combine_inten_a_and_inten_a_pixels() function is a couple

Mon Jan 11 22:02:10 GMT 1999 Adam D. Moss <adam@gimp.org>

	* app/paint_funcs.c:
	The bottleneck combine_inten_a_and_inten_a_pixels()
	function is a couple of times faster when there is a
	layer mask, for the common case, due to working with whole
	word-aligned ints where feasible instead of a char at a time.
	The same optimization could be implemented in lots of other
	places, but I'm going to bed.  Good night!

	* app/gimage_cmds.c: #include <cursorutil.h>
This commit is contained in:
GMT 1999 Adam D. Moss 1999-01-11 22:08:07 +00:00 committed by Adam D. Moss
parent 5e7d70556d
commit d182f93904
4 changed files with 363 additions and 8 deletions

View File

@ -1,3 +1,15 @@
Mon Jan 11 22:02:10 GMT 1999 Adam D. Moss <adam@gimp.org>
* app/paint_funcs.c:
The bottleneck combine_inten_a_and_inten_a_pixels()
function is a couple of times faster when there is a
layer mask, for the common case, due to working with whole
word-aligned ints where feasible instead of a char at a time.
The same optimization could be implemented in lots of other
places, but I'm going to bed. Good night!
* app/gimage_cmds.c: #include <cursorutil.h>
Mon Jan 11 21:35:44 MET 1999 Sven Neumann <sven@gimp.org>
* configure.in: build the Makefile in the modules directory

View File

@ -19,6 +19,7 @@
#include <stdlib.h>
#include <string.h>
#include "appenv.h"
#include "cursorutil.h"
#include "drawable.h"
#include "general.h"
#include "gdisplay.h"

View File

@ -1964,10 +1964,18 @@ combine_inten_a_and_inten_a_pixels (const unsigned char *src1,
if (mask)
{
m = mask;
if (opacity == OPAQUE_OPACITY) /* HAS MASK, FULL OPACITY */
{
while (length --)
int* mask_ip;
int i,j;
/* HEAD */
i = ((int)m) & (sizeof(int)-1);
length -= i;
while (i--)
{
/* GUTS */
src2_alpha = INT_MULT(src2[alpha], *m, tmp);
new_alpha = src1[alpha] +
INT_MULT((255 - src1[alpha]), src2_alpha, tmp);
@ -1987,13 +1995,98 @@ combine_inten_a_and_inten_a_pixels (const unsigned char *src1,
m++;
src1 += bytes;
src2 += bytes;
dest += bytes;
dest += bytes;
/* GUTS END */
}
/* BODY */
mask_ip = (int*)m;
i = length / sizeof(int);
length %= sizeof(int);
while (i--)
{
if (*mask_ip)
{
m = (const unsigned char*)mask_ip;
j = sizeof(int);
while (j--)
{
/* GUTS */
src2_alpha = INT_MULT(src2[alpha], *m, tmp);
new_alpha = src1[alpha] +
INT_MULT((255 - src1[alpha]), src2_alpha, tmp);
alphify (src2_alpha, new_alpha);
if (mode_affect)
{
dest[alpha] = (affect[alpha]) ? new_alpha : src1[alpha];
}
else
{
dest[alpha] = (src1[alpha]) ? src1[alpha] :
(affect[alpha] ? new_alpha : src1[alpha]);
}
m++;
src1 += bytes;
src2 += bytes;
dest += bytes;
/* GUTS END */
}
}
else
{
src1 += bytes * sizeof(int);
src2 += bytes * sizeof(int);
j = sizeof(int);
while (j--)
{
dest[alpha] = 255;
dest += bytes;
}
}
mask_ip++;
}
/* TAIL */
while (length--)
{
/* GUTS */
src2_alpha = INT_MULT(src2[alpha], *m, tmp);
new_alpha = src1[alpha] +
INT_MULT((255 - src1[alpha]), src2_alpha, tmp);
alphify (src2_alpha, new_alpha);
if (mode_affect)
{
dest[alpha] = (affect[alpha]) ? new_alpha : src1[alpha];
}
else
{
dest[alpha] = (src1[alpha]) ? src1[alpha] :
(affect[alpha] ? new_alpha : src1[alpha]);
}
m++;
src1 += bytes;
src2 += bytes;
dest += bytes;
/* GUTS END */
}
}
else /* HAS MASK, SEMI-OPACITY */
{
while (length --)
int* mask_ip;
int i,j;
/* HEAD */
i = ((int)m) & (sizeof(int)-1);
length -= i;
while (i--)
{
/* GUTS */
src2_alpha = INT_MULT3(src2[alpha], *m, opacity, tmp);
new_alpha = src1[alpha] +
INT_MULT((255 - src1[alpha]), src2_alpha, tmp);
@ -2009,11 +2102,89 @@ combine_inten_a_and_inten_a_pixels (const unsigned char *src1,
dest[alpha] = (src1[alpha]) ? src1[alpha] :
(affect[alpha] ? new_alpha : src1[alpha]);
}
m++;
src1 += bytes;
src2 += bytes;
dest += bytes;
/* GUTS END */
}
/* BODY */
mask_ip = (int*)m;
i = length / sizeof(int);
length %= sizeof(int);
while (i--)
{
if (*mask_ip)
{
m = (const unsigned char*)mask_ip;
j = sizeof(int);
while (j--)
{
/* GUTS */
src2_alpha = INT_MULT3(src2[alpha], *m, opacity, tmp);
new_alpha = src1[alpha] +
INT_MULT((255 - src1[alpha]), src2_alpha, tmp);
alphify (src2_alpha, new_alpha);
if (mode_affect)
{
dest[alpha] = (affect[alpha]) ? new_alpha : src1[alpha];
}
else
{
dest[alpha] = (src1[alpha]) ? src1[alpha] :
(affect[alpha] ? new_alpha : src1[alpha]);
}
m++;
src1 += bytes;
src2 += bytes;
dest += bytes;
/* GUTS END */
}
}
else
{
src1 += bytes * sizeof(int);
src2 += bytes * sizeof(int);
j = sizeof(int);
while (j--)
{
dest[alpha] = 255;
dest += bytes;
}
}
mask_ip++;
}
/* TAIL */
while (length--)
{
/* GUTS */
src2_alpha = INT_MULT3(src2[alpha], *m, opacity, tmp);
new_alpha = src1[alpha] +
INT_MULT((255 - src1[alpha]), src2_alpha, tmp);
alphify (src2_alpha, new_alpha);
if (mode_affect)
{
dest[alpha] = (affect[alpha]) ? new_alpha : src1[alpha];
}
else
{
dest[alpha] = (src1[alpha]) ? src1[alpha] :
(affect[alpha] ? new_alpha : src1[alpha]);
}
m++;
src1 += bytes;
src2 += bytes;
dest += bytes;
/* GUTS END */
}
}
}

View File

@ -1964,10 +1964,18 @@ combine_inten_a_and_inten_a_pixels (const unsigned char *src1,
if (mask)
{
m = mask;
if (opacity == OPAQUE_OPACITY) /* HAS MASK, FULL OPACITY */
{
while (length --)
int* mask_ip;
int i,j;
/* HEAD */
i = ((int)m) & (sizeof(int)-1);
length -= i;
while (i--)
{
/* GUTS */
src2_alpha = INT_MULT(src2[alpha], *m, tmp);
new_alpha = src1[alpha] +
INT_MULT((255 - src1[alpha]), src2_alpha, tmp);
@ -1987,13 +1995,98 @@ combine_inten_a_and_inten_a_pixels (const unsigned char *src1,
m++;
src1 += bytes;
src2 += bytes;
dest += bytes;
dest += bytes;
/* GUTS END */
}
/* BODY */
mask_ip = (int*)m;
i = length / sizeof(int);
length %= sizeof(int);
while (i--)
{
if (*mask_ip)
{
m = (const unsigned char*)mask_ip;
j = sizeof(int);
while (j--)
{
/* GUTS */
src2_alpha = INT_MULT(src2[alpha], *m, tmp);
new_alpha = src1[alpha] +
INT_MULT((255 - src1[alpha]), src2_alpha, tmp);
alphify (src2_alpha, new_alpha);
if (mode_affect)
{
dest[alpha] = (affect[alpha]) ? new_alpha : src1[alpha];
}
else
{
dest[alpha] = (src1[alpha]) ? src1[alpha] :
(affect[alpha] ? new_alpha : src1[alpha]);
}
m++;
src1 += bytes;
src2 += bytes;
dest += bytes;
/* GUTS END */
}
}
else
{
src1 += bytes * sizeof(int);
src2 += bytes * sizeof(int);
j = sizeof(int);
while (j--)
{
dest[alpha] = 255;
dest += bytes;
}
}
mask_ip++;
}
/* TAIL */
while (length--)
{
/* GUTS */
src2_alpha = INT_MULT(src2[alpha], *m, tmp);
new_alpha = src1[alpha] +
INT_MULT((255 - src1[alpha]), src2_alpha, tmp);
alphify (src2_alpha, new_alpha);
if (mode_affect)
{
dest[alpha] = (affect[alpha]) ? new_alpha : src1[alpha];
}
else
{
dest[alpha] = (src1[alpha]) ? src1[alpha] :
(affect[alpha] ? new_alpha : src1[alpha]);
}
m++;
src1 += bytes;
src2 += bytes;
dest += bytes;
/* GUTS END */
}
}
else /* HAS MASK, SEMI-OPACITY */
{
while (length --)
int* mask_ip;
int i,j;
/* HEAD */
i = ((int)m) & (sizeof(int)-1);
length -= i;
while (i--)
{
/* GUTS */
src2_alpha = INT_MULT3(src2[alpha], *m, opacity, tmp);
new_alpha = src1[alpha] +
INT_MULT((255 - src1[alpha]), src2_alpha, tmp);
@ -2009,11 +2102,89 @@ combine_inten_a_and_inten_a_pixels (const unsigned char *src1,
dest[alpha] = (src1[alpha]) ? src1[alpha] :
(affect[alpha] ? new_alpha : src1[alpha]);
}
m++;
src1 += bytes;
src2 += bytes;
dest += bytes;
/* GUTS END */
}
/* BODY */
mask_ip = (int*)m;
i = length / sizeof(int);
length %= sizeof(int);
while (i--)
{
if (*mask_ip)
{
m = (const unsigned char*)mask_ip;
j = sizeof(int);
while (j--)
{
/* GUTS */
src2_alpha = INT_MULT3(src2[alpha], *m, opacity, tmp);
new_alpha = src1[alpha] +
INT_MULT((255 - src1[alpha]), src2_alpha, tmp);
alphify (src2_alpha, new_alpha);
if (mode_affect)
{
dest[alpha] = (affect[alpha]) ? new_alpha : src1[alpha];
}
else
{
dest[alpha] = (src1[alpha]) ? src1[alpha] :
(affect[alpha] ? new_alpha : src1[alpha]);
}
m++;
src1 += bytes;
src2 += bytes;
dest += bytes;
/* GUTS END */
}
}
else
{
src1 += bytes * sizeof(int);
src2 += bytes * sizeof(int);
j = sizeof(int);
while (j--)
{
dest[alpha] = 255;
dest += bytes;
}
}
mask_ip++;
}
/* TAIL */
while (length--)
{
/* GUTS */
src2_alpha = INT_MULT3(src2[alpha], *m, opacity, tmp);
new_alpha = src1[alpha] +
INT_MULT((255 - src1[alpha]), src2_alpha, tmp);
alphify (src2_alpha, new_alpha);
if (mode_affect)
{
dest[alpha] = (affect[alpha]) ? new_alpha : src1[alpha];
}
else
{
dest[alpha] = (src1[alpha]) ? src1[alpha] :
(affect[alpha] ? new_alpha : src1[alpha]);
}
m++;
src1 += bytes;
src2 += bytes;
dest += bytes;
/* GUTS END */
}
}
}