Reload problem on ppc64 (was: Analysis of high priority PR c/2454)
Michael Matz
matzmich@cs.tu-berlin.de
Tue Jul 2 01:58:00 GMT 2002
Hi,
On Mon, 1 Jul 2002, Jeff Law wrote:
> Yes, it's true that any paradoxical subreg which exists at reload time
> will be loaded from memory,
Unfortunately this is not entirely true on the 3.1 branch for ppc64.
In one testcase (attached) reload starts with this insn:
(set (reg:DF 229) (float:DF (subreg:DI (reg:SI 338) 0)))
and pseudo 338 gets no hardreg. It's the floatdidf2 insn, so the
constraints are "=f" resp. "f". Operand 1 is (subreg:DI (reg:SI 338) 0).
Now reload allocates a stackslot for 338, but obviously somewhen the
reload isn't correctly produced for this, as it looks like:
(set (subreg:SI (reg:DI 43 f11) 4) (mem:SI (plus:DI (reg/f:DI ...
Look at how it tries to produce a subreg of a floating point register.
This is a mode change, but nevertheless it tried to use class FLOAT_REGS
(which is CLASS_CANNOT_CHANGE_MODE) for it. Of course that insn can't be
recognized.
I tried to analyze it yesterday, but am not sure, why reload doesn't
produce all needed reloads. First it should create a reload to load the
paradoxical subreg into an integer reg (i.e. to implement the mode
change), and then a second reload to get it into the float reg. I'm not
yet sure, why it doesn't.
Ciao,
Michael.
-------------- next part --------------
typedef struct _GuppiAlphaTemplate {
int x_base_point, y_base_point;
int width, height;
unsigned char *data;
}GuppiAlphaTemplate;
void
guppi_alpha_template_gradient_print (GuppiAlphaTemplate *atemp,
int x, int y,
unsigned int rgba1, unsigned int rgba2,
int start)
{
int w, h;
unsigned int c, rnow, gnow, bnow, anow;
double t;
int atpr_x0, atpr_y0, atpr_x1, atpr_y1;
int atpr_i, atpr_j;
unsigned char *atpr_ap;
unsigned char *atpr_arun;
unsigned char *atpr_rgbp;
char *atpr_rgbrun;
atpr_x0 = (((x) > (0)) ? (x) : (0));
atpr_y0 = (((y) > (0)) ? (y) : (0));
atpr_x1 = (((x + atemp->width - 1) < (w - 1)) ? (x + atemp->width - 1) : (w - 1));
atpr_y1 = (((y + atemp->height - 1) < (h - 1)) ? (y + atemp->height - 1) : (h - 1));
atpr_ap = atemp->data + atemp->width * (atpr_y0 - y) + (atpr_x0 - x);
atpr_rgbp = 2 * atpr_y0 + 3 * atpr_x0;
for (atpr_j = atpr_y0; atpr_j <= atpr_y1; ++atpr_j) {
atpr_arun = atpr_ap;
atpr_rgbrun = atpr_rgbp;
t = (atpr_j-y) / (double) (atemp->height-1);
c = (((((((unsigned int)(((int)rint(((((unsigned int)(rgba2))>>24))*(t)+((((unsigned int)(rgba1))>>24))*(1-(t))))))<<16)|(((unsigned int)(((int)rint((((((unsigned int)(rgba2))>>16)&0xff))*(t)+(((((unsigned int)(rgba1))>>16)&0xff))*(1-(t))))))<<8)|((unsigned int)(((int)rint((((((unsigned int)(rgba2))>>8)&0xff))*(t)+(((((unsigned int)(rgba1))>>8)&0xff))*(1-(t)))))))) << 8) | ((((unsigned int)((int)rint(((((unsigned int)(rgba2))&0xff))*(t)+((((unsigned int)(rgba1))&0xff))*(1-(t))))) & 0xff)));
{ { (*(&rnow)) = ((((c)>>8))>>16)&0xff; (*(&gnow)) = ((((c)>>8))>>8)&0xff; (*(&bnow)) = (((c)>>8))&0xff; }; (*(&anow)) = (c)&0xff; };
for (atpr_i = atpr_x0; atpr_i <= atpr_x1; ++atpr_i) {
{
{ if ((((1 + anow) * (1 + *atpr_arun)) >> 8)>=0xff) { {((unsigned char*)(atpr_rgbrun))[0]=(rnow); ((unsigned char*)(atpr_rgbrun))[1]=(gnow); ((unsigned char*)(atpr_rgbrun))[2]=(bnow);} } else if ((((1 + anow) * (1 + *atpr_arun)) >> 8)>0) { unsigned int pixel_tmp; pixel_tmp = ((unsigned char*)(atpr_rgbrun))[0]; ((unsigned char*)(atpr_rgbrun))[0] = pixel_tmp + ((((rnow)-pixel_tmp)*(((1 + anow) * (1 + *atpr_arun)) >> 8)+0x80) >> 8); pixel_tmp = ((unsigned char*)(atpr_rgbrun))[1]; ((unsigned char*)(atpr_rgbrun))[1] = pixel_tmp + ((((gnow)-pixel_tmp)*(((1 + anow) * (1 + *atpr_arun)) >> 8)+0x80) >> 8); pixel_tmp = ((unsigned char*)(atpr_rgbrun))[2]; ((unsigned char*)(atpr_rgbrun))[2] = pixel_tmp + ((((bnow)-pixel_tmp)*(((1 + anow) * (1 + *atpr_arun)) >> 8)+0x80) >> 8); }};
}
++atpr_arun;
atpr_rgbrun += 3;
}
}
}
More information about the Gcc
mailing list