mirror of
https://github.com/xomboverlord/ldc.git
synced 2026-08-02 20:40:05 +02:00
Fix white space.
This commit is contained in:
422
dmd/constfold.c
422
dmd/constfold.c
@@ -1,6 +1,6 @@
|
||||
|
||||
// Compiler implementation of the D programming language
|
||||
// Copyright (c) 1999-2011 by Digital Mars
|
||||
// Copyright (c) 1999-2011 by Digital Mars
|
||||
// All Rights Reserved
|
||||
// written by Walter Bright
|
||||
// http://www.digitalmars.com
|
||||
@@ -38,8 +38,8 @@ static real_t zero; // work around DMC bug for now
|
||||
|
||||
#define LOG 0
|
||||
|
||||
int RealEquals(real_t x1, real_t x2);
|
||||
|
||||
int RealEquals(real_t x1, real_t x2);
|
||||
|
||||
Expression *expType(Type *type, Expression *e)
|
||||
{
|
||||
if (type != e->type)
|
||||
@@ -493,7 +493,7 @@ Expression *Mod(Type *type, Expression *e1, Expression *e2)
|
||||
{ real_t r2 = e2->toReal();
|
||||
|
||||
#ifdef __DMC__
|
||||
c = Port::fmodl(e1->toReal(), r2) + Port::fmodl(e1->toImaginary(), r2) * I;
|
||||
c = Port::fmodl(e1->toReal(), r2) + Port::fmodl(e1->toImaginary(), r2) * I;
|
||||
#elif defined(IN_GCC)
|
||||
c = complex_t(e1->toReal() % r2, e1->toImaginary() % r2);
|
||||
#elif (defined(__FreeBSD__) && __FreeBSD_version < 800000) || defined(__arm__) || defined(__thumb__)
|
||||
@@ -501,14 +501,14 @@ Expression *Mod(Type *type, Expression *e1, Expression *e2)
|
||||
// arm also doesn't like fmodl
|
||||
c = complex_t(fmod(e1->toReal(), r2), fmod(e1->toImaginary(), r2));
|
||||
#else
|
||||
c = complex_t(Port::fmodl(e1->toReal(), r2), Port::fmodl(e1->toImaginary(), r2));
|
||||
c = complex_t(Port::fmodl(e1->toReal(), r2), Port::fmodl(e1->toImaginary(), r2));
|
||||
#endif
|
||||
}
|
||||
else if (e2->type->isimaginary())
|
||||
{ real_t i2 = e2->toImaginary();
|
||||
|
||||
#ifdef __DMC__
|
||||
c = Port::fmodl(e1->toReal(), i2) + Port::fmodl(e1->toImaginary(), i2) * I;
|
||||
c = Port::fmodl(e1->toReal(), i2) + Port::fmodl(e1->toImaginary(), i2) * I;
|
||||
#elif defined(IN_GCC)
|
||||
c = complex_t(e1->toReal() % i2, e1->toImaginary() % i2);
|
||||
#elif (defined(__FreeBSD__) && __FreeBSD_version < 800000) || defined(__arm__) || defined(__thumb__)
|
||||
@@ -516,7 +516,7 @@ Expression *Mod(Type *type, Expression *e1, Expression *e2)
|
||||
// arm also doesn't like fmodl
|
||||
c = complex_t(fmod(e1->toReal(), i2), fmod(e1->toImaginary(), i2));
|
||||
#else
|
||||
c = complex_t(Port::fmodl(e1->toReal(), i2), Port::fmodl(e1->toImaginary(), i2));
|
||||
c = complex_t(Port::fmodl(e1->toReal(), i2), Port::fmodl(e1->toImaginary(), i2));
|
||||
#endif
|
||||
}
|
||||
else
|
||||
@@ -543,21 +543,21 @@ Expression *Mod(Type *type, Expression *e1, Expression *e2)
|
||||
e2 = new IntegerExp(loc, 1, e2->type);
|
||||
n2 = 1;
|
||||
}
|
||||
if (n2 == -1 && !type->isunsigned())
|
||||
{ // Check for int.min % -1
|
||||
if (n1 == 0xFFFFFFFF80000000ULL && type->toBasetype()->ty != Tint64)
|
||||
{
|
||||
e2->error("integer overflow: int.min % -1");
|
||||
e2 = new IntegerExp(loc, 1, e2->type);
|
||||
n2 = 1;
|
||||
}
|
||||
else if (n1 == 0x8000000000000000LL) // long.min % -1
|
||||
{
|
||||
e2->error("integer overflow: long.min % -1");
|
||||
e2 = new IntegerExp(loc, 1, e2->type);
|
||||
n2 = 1;
|
||||
}
|
||||
}
|
||||
if (n2 == -1 && !type->isunsigned())
|
||||
{ // Check for int.min % -1
|
||||
if (n1 == 0xFFFFFFFF80000000ULL && type->toBasetype()->ty != Tint64)
|
||||
{
|
||||
e2->error("integer overflow: int.min % -1");
|
||||
e2 = new IntegerExp(loc, 1, e2->type);
|
||||
n2 = 1;
|
||||
}
|
||||
else if (n1 == 0x8000000000000000LL) // long.min % -1
|
||||
{
|
||||
e2->error("integer overflow: long.min % -1");
|
||||
e2 = new IntegerExp(loc, 1, e2->type);
|
||||
n2 = 1;
|
||||
}
|
||||
}
|
||||
if (e1->type->isunsigned() || e2->type->isunsigned())
|
||||
n = ((d_uns64) n1) % ((d_uns64) n2);
|
||||
else
|
||||
@@ -580,9 +580,9 @@ Expression *Shr(Type *type, Expression *e1, Expression *e2)
|
||||
Loc loc = e1->loc;
|
||||
|
||||
dinteger_t value = e1->toInteger();
|
||||
dinteger_t dcount = e2->toInteger();
|
||||
assert(dcount <= 0xFFFFFFFF);
|
||||
unsigned count = (unsigned)dcount;
|
||||
dinteger_t dcount = e2->toInteger();
|
||||
assert(dcount <= 0xFFFFFFFF);
|
||||
unsigned count = (unsigned)dcount;
|
||||
switch (e1->type->toBasetype()->ty)
|
||||
{
|
||||
case Tint8:
|
||||
@@ -590,7 +590,7 @@ Expression *Shr(Type *type, Expression *e1, Expression *e2)
|
||||
break;
|
||||
|
||||
case Tuns8:
|
||||
case Tchar:
|
||||
case Tchar:
|
||||
value = (d_uns8)(value) >> count;
|
||||
break;
|
||||
|
||||
@@ -599,7 +599,7 @@ Expression *Shr(Type *type, Expression *e1, Expression *e2)
|
||||
break;
|
||||
|
||||
case Tuns16:
|
||||
case Twchar:
|
||||
case Twchar:
|
||||
value = (d_uns16)(value) >> count;
|
||||
break;
|
||||
|
||||
@@ -608,7 +608,7 @@ Expression *Shr(Type *type, Expression *e1, Expression *e2)
|
||||
break;
|
||||
|
||||
case Tuns32:
|
||||
case Tdchar:
|
||||
case Tdchar:
|
||||
value = (d_uns32)(value) >> count;
|
||||
break;
|
||||
|
||||
@@ -635,28 +635,28 @@ Expression *Ushr(Type *type, Expression *e1, Expression *e2)
|
||||
Loc loc = e1->loc;
|
||||
|
||||
dinteger_t value = e1->toInteger();
|
||||
dinteger_t dcount = e2->toInteger();
|
||||
assert(dcount <= 0xFFFFFFFF);
|
||||
unsigned count = (unsigned)dcount;
|
||||
dinteger_t dcount = e2->toInteger();
|
||||
assert(dcount <= 0xFFFFFFFF);
|
||||
unsigned count = (unsigned)dcount;
|
||||
switch (e1->type->toBasetype()->ty)
|
||||
{
|
||||
case Tint8:
|
||||
case Tuns8:
|
||||
case Tchar:
|
||||
// Possible only with >>>=. >>> always gets promoted to int.
|
||||
case Tchar:
|
||||
// Possible only with >>>=. >>> always gets promoted to int.
|
||||
value = (value & 0xFF) >> count;
|
||||
break;
|
||||
|
||||
case Tint16:
|
||||
case Tuns16:
|
||||
case Twchar:
|
||||
// Possible only with >>>=. >>> always gets promoted to int.
|
||||
case Twchar:
|
||||
// Possible only with >>>=. >>> always gets promoted to int.
|
||||
value = (value & 0xFFFF) >> count;
|
||||
break;
|
||||
|
||||
case Tint32:
|
||||
case Tuns32:
|
||||
case Tdchar:
|
||||
case Tdchar:
|
||||
value = (value & 0xFFFFFFFF) >> count;
|
||||
break;
|
||||
|
||||
@@ -764,8 +764,8 @@ Expression *Equal(enum TOK op, Type *type, Expression *e1, Expression *e2)
|
||||
else
|
||||
{
|
||||
for (size_t i = 0; i < es1->elements->dim; i++)
|
||||
{ Expression *ee1 = (*es1->elements)[i];
|
||||
Expression *ee2 = (*es2->elements)[i];
|
||||
{ Expression *ee1 = (*es1->elements)[i];
|
||||
Expression *ee2 = (*es2->elements)[i];
|
||||
|
||||
Expression *v = Equal(TOKequal, Type::tint32, ee1, ee2);
|
||||
if (v == EXP_CANT_INTERPRET)
|
||||
@@ -778,9 +778,9 @@ Expression *Equal(enum TOK op, Type *type, Expression *e1, Expression *e2)
|
||||
}
|
||||
else if (e1->op == TOKarrayliteral && e2->op == TOKstring)
|
||||
{ // Swap operands and use common code
|
||||
Expression *etmp = e1;
|
||||
Expression *etmp = e1;
|
||||
e1 = e2;
|
||||
e2 = etmp;
|
||||
e2 = etmp;
|
||||
goto Lsa;
|
||||
}
|
||||
else if (e1->op == TOKstring && e2->op == TOKarrayliteral)
|
||||
@@ -794,11 +794,11 @@ Expression *Equal(enum TOK op, Type *type, Expression *e1, Expression *e2)
|
||||
cmp = 0;
|
||||
else
|
||||
{
|
||||
cmp = 1; // if dim1 winds up being 0
|
||||
cmp = 1; // if dim1 winds up being 0
|
||||
for (size_t i = 0; i < dim1; i++)
|
||||
{
|
||||
uinteger_t c = es1->charAt(i);
|
||||
Expression *ee2 = (*es2->elements)[i];
|
||||
Expression *ee2 = (*es2->elements)[i];
|
||||
if (ee2->isConst() != 1)
|
||||
return EXP_CANT_INTERPRET;
|
||||
cmp = (c == ee2->toInteger());
|
||||
@@ -824,8 +824,8 @@ Expression *Equal(enum TOK op, Type *type, Expression *e1, Expression *e2)
|
||||
{
|
||||
cmp = 1;
|
||||
for (size_t i = 0; i < es1->elements->dim; i++)
|
||||
{ Expression *ee1 = (*es1->elements)[i];
|
||||
Expression *ee2 = (*es2->elements)[i];
|
||||
{ Expression *ee1 = (*es1->elements)[i];
|
||||
Expression *ee2 = (*es2->elements)[i];
|
||||
|
||||
if (ee1 == ee2)
|
||||
continue;
|
||||
@@ -909,11 +909,11 @@ Expression *Identity(enum TOK op, Type *type, Expression *e1, Expression *e2)
|
||||
|
||||
cmp = (es1->var == es2->var && es1->offset == es2->offset);
|
||||
}
|
||||
else
|
||||
{
|
||||
else
|
||||
{
|
||||
return Equal((op == TOKidentity) ? TOKequal : TOKnotequal,
|
||||
type, e1, e2);
|
||||
}
|
||||
}
|
||||
if (op == TOKnotidentity)
|
||||
cmp ^= 1;
|
||||
return new IntegerExp(loc, cmp, type);
|
||||
@@ -1158,7 +1158,7 @@ Expression *Cast(Type *type, Type *to, Expression *e1)
|
||||
assert(sd);
|
||||
Expressions *elements = new Expressions;
|
||||
for (size_t i = 0; i < sd->fields.dim; i++)
|
||||
{ Dsymbol *s = sd->fields.tdata()[i];
|
||||
{ Dsymbol *s = sd->fields.tdata()[i];
|
||||
VarDeclaration *v = s->isVarDeclaration();
|
||||
assert(v);
|
||||
|
||||
@@ -1221,13 +1221,13 @@ Expression *Index(Type *type, Expression *e1, Expression *e2)
|
||||
uinteger_t i = e2->toInteger();
|
||||
|
||||
if (i >= es1->len)
|
||||
{
|
||||
{
|
||||
e1->error("string index %ju is out of bounds [0 .. %zu]", i, es1->len);
|
||||
e = new ErrorExp();
|
||||
}
|
||||
e = new ErrorExp();
|
||||
}
|
||||
else
|
||||
{
|
||||
e = new IntegerExp(loc, es1->charAt(i), type);
|
||||
{
|
||||
e = new IntegerExp(loc, es1->charAt(i), type);
|
||||
}
|
||||
}
|
||||
else if (e1->type->toBasetype()->ty == Tsarray && e2->op == TOKint64)
|
||||
@@ -1236,38 +1236,38 @@ Expression *Index(Type *type, Expression *e1, Expression *e2)
|
||||
uinteger_t i = e2->toInteger();
|
||||
|
||||
if (i >= length)
|
||||
{
|
||||
e1->error("array index %ju is out of bounds %s[0 .. %ju]", i, e1->toChars(), length);
|
||||
e = new ErrorExp();
|
||||
{
|
||||
e1->error("array index %ju is out of bounds %s[0 .. %ju]", i, e1->toChars(), length);
|
||||
e = new ErrorExp();
|
||||
}
|
||||
else if (e1->op == TOKarrayliteral)
|
||||
else if (e1->op == TOKarrayliteral)
|
||||
{ ArrayLiteralExp *ale = (ArrayLiteralExp *)e1;
|
||||
e = ale->elements->tdata()[i];
|
||||
e = ale->elements->tdata()[i];
|
||||
e->type = type;
|
||||
if (e->hasSideEffect())
|
||||
e = EXP_CANT_INTERPRET;
|
||||
if (e->hasSideEffect())
|
||||
e = EXP_CANT_INTERPRET;
|
||||
}
|
||||
}
|
||||
else if (e1->type->toBasetype()->ty == Tarray && e2->op == TOKint64)
|
||||
{
|
||||
uinteger_t i = e2->toInteger();
|
||||
|
||||
if (e1->op == TOKarrayliteral)
|
||||
if (e1->op == TOKarrayliteral)
|
||||
{ ArrayLiteralExp *ale = (ArrayLiteralExp *)e1;
|
||||
if (i >= ale->elements->dim)
|
||||
{
|
||||
e1->error("array index %ju is out of bounds %s[0 .. %u]", i, e1->toChars(), ale->elements->dim);
|
||||
e = new ErrorExp();
|
||||
{
|
||||
e1->error("array index %ju is out of bounds %s[0 .. %u]", i, e1->toChars(), ale->elements->dim);
|
||||
e = new ErrorExp();
|
||||
}
|
||||
else
|
||||
{ e = ale->elements->tdata()[i];
|
||||
{ e = ale->elements->tdata()[i];
|
||||
e->type = type;
|
||||
if (e->hasSideEffect())
|
||||
e = EXP_CANT_INTERPRET;
|
||||
if (e->hasSideEffect())
|
||||
e = EXP_CANT_INTERPRET;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (e1->op == TOKassocarrayliteral)
|
||||
else if (e1->op == TOKassocarrayliteral)
|
||||
{
|
||||
AssocArrayLiteralExp *ae = (AssocArrayLiteralExp *)e1;
|
||||
/* Search the keys backwards, in case there are duplicate keys
|
||||
@@ -1275,15 +1275,15 @@ Expression *Index(Type *type, Expression *e1, Expression *e2)
|
||||
for (size_t i = ae->keys->dim; i;)
|
||||
{
|
||||
i--;
|
||||
Expression *ekey = ae->keys->tdata()[i];
|
||||
Expression *ekey = ae->keys->tdata()[i];
|
||||
Expression *ex = Equal(TOKequal, Type::tbool, ekey, e2);
|
||||
if (ex == EXP_CANT_INTERPRET)
|
||||
return ex;
|
||||
if (ex->isBool(TRUE))
|
||||
{ e = ae->values->tdata()[i];
|
||||
{ e = ae->values->tdata()[i];
|
||||
e->type = type;
|
||||
if (e->hasSideEffect())
|
||||
e = EXP_CANT_INTERPRET;
|
||||
if (e->hasSideEffect())
|
||||
e = EXP_CANT_INTERPRET;
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -1311,12 +1311,12 @@ Expression *Slice(Type *type, Expression *e1, Expression *lwr, Expression *upr)
|
||||
uinteger_t iupr = upr->toInteger();
|
||||
|
||||
if (iupr > es1->len || ilwr > iupr)
|
||||
{
|
||||
{
|
||||
e1->error("string slice [%ju .. %ju] is out of bounds", ilwr, iupr);
|
||||
e = new ErrorExp();
|
||||
}
|
||||
e = new ErrorExp();
|
||||
}
|
||||
else
|
||||
{
|
||||
{
|
||||
void *s;
|
||||
size_t len = iupr - ilwr;
|
||||
int sz = es1->sz;
|
||||
@@ -1335,23 +1335,23 @@ Expression *Slice(Type *type, Expression *e1, Expression *lwr, Expression *upr)
|
||||
}
|
||||
else if (e1->op == TOKarrayliteral &&
|
||||
lwr->op == TOKint64 && upr->op == TOKint64 &&
|
||||
!e1->hasSideEffect())
|
||||
!e1->hasSideEffect())
|
||||
{ ArrayLiteralExp *es1 = (ArrayLiteralExp *)e1;
|
||||
uinteger_t ilwr = lwr->toInteger();
|
||||
uinteger_t iupr = upr->toInteger();
|
||||
|
||||
if (iupr > es1->elements->dim || ilwr > iupr)
|
||||
{
|
||||
{
|
||||
e1->error("array slice [%ju .. %ju] is out of bounds", ilwr, iupr);
|
||||
e = new ErrorExp();
|
||||
}
|
||||
e = new ErrorExp();
|
||||
}
|
||||
else
|
||||
{
|
||||
Expressions *elements = new Expressions();
|
||||
elements->setDim(iupr - ilwr);
|
||||
memcpy(elements->tdata(),
|
||||
es1->elements->tdata() + ilwr,
|
||||
(iupr - ilwr) * sizeof(es1->elements->tdata()[0]));
|
||||
memcpy(elements->tdata(),
|
||||
es1->elements->tdata() + ilwr,
|
||||
(iupr - ilwr) * sizeof(es1->elements->tdata()[0]));
|
||||
e = new ArrayLiteralExp(e1->loc, elements);
|
||||
e->type = type;
|
||||
}
|
||||
@@ -1359,64 +1359,64 @@ Expression *Slice(Type *type, Expression *e1, Expression *lwr, Expression *upr)
|
||||
return e;
|
||||
}
|
||||
|
||||
/* Set a slice of char array literal 'existingAE' from a string 'newval'.
|
||||
* existingAE[firstIndex..firstIndex+newval.length] = newval.
|
||||
*/
|
||||
void sliceAssignArrayLiteralFromString(ArrayLiteralExp *existingAE, StringExp *newval, int firstIndex)
|
||||
{
|
||||
size_t newlen = newval->len;
|
||||
size_t sz = newval->sz;
|
||||
unsigned char *s = (unsigned char *)newval->string;
|
||||
Type *elemType = existingAE->type->nextOf();
|
||||
for (size_t j = 0; j < newlen; j++)
|
||||
{
|
||||
dinteger_t val;
|
||||
switch (sz)
|
||||
{
|
||||
case 1: val = s[j]; break;
|
||||
case 2: val = ((unsigned short *)s)[j]; break;
|
||||
case 4: val = ((unsigned *)s)[j]; break;
|
||||
default:
|
||||
assert(0);
|
||||
break;
|
||||
}
|
||||
existingAE->elements->tdata()[j+firstIndex]
|
||||
= new IntegerExp(newval->loc, val, elemType);
|
||||
}
|
||||
}
|
||||
|
||||
/* Set a slice of string 'existingSE' from a char array literal 'newae'.
|
||||
* existingSE[firstIndex..firstIndex+newae.length] = newae.
|
||||
*/
|
||||
void sliceAssignStringFromArrayLiteral(StringExp *existingSE, ArrayLiteralExp *newae, int firstIndex)
|
||||
{
|
||||
unsigned char *s = (unsigned char *)existingSE->string;
|
||||
for (size_t j = 0; j < newae->elements->dim; j++)
|
||||
{
|
||||
unsigned value = (unsigned)(newae->elements->tdata()[j]->toInteger());
|
||||
switch (existingSE->sz)
|
||||
{
|
||||
case 1: s[j+firstIndex] = value; break;
|
||||
case 2: ((unsigned short *)s)[j+firstIndex] = value; break;
|
||||
case 4: ((unsigned *)s)[j+firstIndex] = value; break;
|
||||
default:
|
||||
assert(0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Set a slice of string 'existingSE' from a string 'newstr'.
|
||||
* existingSE[firstIndex..firstIndex+newstr.length] = newstr.
|
||||
*/
|
||||
void sliceAssignStringFromString(StringExp *existingSE, StringExp *newstr, int firstIndex)
|
||||
{
|
||||
unsigned char *s = (unsigned char *)existingSE->string;
|
||||
size_t sz = existingSE->sz;
|
||||
assert(sz == newstr->sz);
|
||||
memcpy(s + firstIndex * sz, newstr->string, sz * newstr->len);
|
||||
}
|
||||
|
||||
/* Set a slice of char array literal 'existingAE' from a string 'newval'.
|
||||
* existingAE[firstIndex..firstIndex+newval.length] = newval.
|
||||
*/
|
||||
void sliceAssignArrayLiteralFromString(ArrayLiteralExp *existingAE, StringExp *newval, int firstIndex)
|
||||
{
|
||||
size_t newlen = newval->len;
|
||||
size_t sz = newval->sz;
|
||||
unsigned char *s = (unsigned char *)newval->string;
|
||||
Type *elemType = existingAE->type->nextOf();
|
||||
for (size_t j = 0; j < newlen; j++)
|
||||
{
|
||||
dinteger_t val;
|
||||
switch (sz)
|
||||
{
|
||||
case 1: val = s[j]; break;
|
||||
case 2: val = ((unsigned short *)s)[j]; break;
|
||||
case 4: val = ((unsigned *)s)[j]; break;
|
||||
default:
|
||||
assert(0);
|
||||
break;
|
||||
}
|
||||
existingAE->elements->tdata()[j+firstIndex]
|
||||
= new IntegerExp(newval->loc, val, elemType);
|
||||
}
|
||||
}
|
||||
|
||||
/* Set a slice of string 'existingSE' from a char array literal 'newae'.
|
||||
* existingSE[firstIndex..firstIndex+newae.length] = newae.
|
||||
*/
|
||||
void sliceAssignStringFromArrayLiteral(StringExp *existingSE, ArrayLiteralExp *newae, int firstIndex)
|
||||
{
|
||||
unsigned char *s = (unsigned char *)existingSE->string;
|
||||
for (size_t j = 0; j < newae->elements->dim; j++)
|
||||
{
|
||||
unsigned value = (unsigned)(newae->elements->tdata()[j]->toInteger());
|
||||
switch (existingSE->sz)
|
||||
{
|
||||
case 1: s[j+firstIndex] = value; break;
|
||||
case 2: ((unsigned short *)s)[j+firstIndex] = value; break;
|
||||
case 4: ((unsigned *)s)[j+firstIndex] = value; break;
|
||||
default:
|
||||
assert(0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Set a slice of string 'existingSE' from a string 'newstr'.
|
||||
* existingSE[firstIndex..firstIndex+newstr.length] = newstr.
|
||||
*/
|
||||
void sliceAssignStringFromString(StringExp *existingSE, StringExp *newstr, int firstIndex)
|
||||
{
|
||||
unsigned char *s = (unsigned char *)existingSE->string;
|
||||
size_t sz = existingSE->sz;
|
||||
assert(sz == newstr->sz);
|
||||
memcpy(s + firstIndex * sz, newstr->string, sz * newstr->len);
|
||||
}
|
||||
|
||||
/* Also return EXP_CANT_INTERPRET if this fails
|
||||
*/
|
||||
Expression *Cat(Type *type, Expression *e1, Expression *e2)
|
||||
@@ -1450,11 +1450,11 @@ Expression *Cat(Type *type, Expression *e1, Expression *e2)
|
||||
|
||||
dinteger_t v = e->toInteger();
|
||||
|
||||
size_t len = (t->ty == tn->ty) ? 1 : utf_codeLength(sz, v);
|
||||
size_t len = (t->ty == tn->ty) ? 1 : utf_codeLength(sz, v);
|
||||
s = mem.malloc((len + 1) * sz);
|
||||
if (t->ty == tn->ty)
|
||||
memcpy((unsigned char *)s, &v, sz);
|
||||
else
|
||||
if (t->ty == tn->ty)
|
||||
memcpy((unsigned char *)s, &v, sz);
|
||||
else
|
||||
utf_encode(sz, s, v);
|
||||
|
||||
// Add terminating 0
|
||||
@@ -1474,24 +1474,24 @@ Expression *Cat(Type *type, Expression *e1, Expression *e2)
|
||||
e->type = type;
|
||||
return e;
|
||||
}
|
||||
else if (e1->op == TOKnull && e2->op == TOKnull)
|
||||
{
|
||||
if (type == e1->type)
|
||||
{
|
||||
// Handle null ~= null
|
||||
if (t1->ty == Tarray && t2 == t1->nextOf())
|
||||
{
|
||||
e = new ArrayLiteralExp(e1->loc, e2);
|
||||
e->type = type;
|
||||
return e;
|
||||
}
|
||||
else
|
||||
return e1;
|
||||
}
|
||||
if (type == e2->type)
|
||||
return e2;
|
||||
return new NullExp(e1->loc, type);
|
||||
}
|
||||
else if (e1->op == TOKnull && e2->op == TOKnull)
|
||||
{
|
||||
if (type == e1->type)
|
||||
{
|
||||
// Handle null ~= null
|
||||
if (t1->ty == Tarray && t2 == t1->nextOf())
|
||||
{
|
||||
e = new ArrayLiteralExp(e1->loc, e2);
|
||||
e->type = type;
|
||||
return e;
|
||||
}
|
||||
else
|
||||
return e1;
|
||||
}
|
||||
if (type == e2->type)
|
||||
return e2;
|
||||
return new NullExp(e1->loc, type);
|
||||
}
|
||||
else if (e1->op == TOKstring && e2->op == TOKstring)
|
||||
{
|
||||
// Concatenate the strings
|
||||
@@ -1520,65 +1520,65 @@ Expression *Cat(Type *type, Expression *e1, Expression *e2)
|
||||
es = new StringExp(loc, s, len);
|
||||
es->sz = sz;
|
||||
es->committed = es1->committed | es2->committed;
|
||||
es->type = type;
|
||||
e = es;
|
||||
}
|
||||
else if (e2->op == TOKstring && e1->op == TOKarrayliteral &&
|
||||
t1->nextOf()->isintegral())
|
||||
{
|
||||
// [chars] ~ string --> [chars]
|
||||
StringExp *es = (StringExp *)e2;
|
||||
ArrayLiteralExp *ea = (ArrayLiteralExp *)e1;
|
||||
size_t len = es->len + ea->elements->dim;
|
||||
Expressions * elems = new Expressions;
|
||||
elems->setDim(len);
|
||||
for (size_t i= 0; i < ea->elements->dim; ++i)
|
||||
{
|
||||
elems->tdata()[i] = ea->elements->tdata()[i];
|
||||
}
|
||||
ArrayLiteralExp *dest = new ArrayLiteralExp(e1->loc, elems);
|
||||
dest->type = type;
|
||||
sliceAssignArrayLiteralFromString(dest, es, ea->elements->dim);
|
||||
return dest;
|
||||
}
|
||||
else if (e1->op == TOKstring && e2->op == TOKarrayliteral &&
|
||||
t2->nextOf()->isintegral())
|
||||
{
|
||||
// string ~ [chars] --> [chars]
|
||||
StringExp *es = (StringExp *)e1;
|
||||
ArrayLiteralExp *ea = (ArrayLiteralExp *)e2;
|
||||
size_t len = es->len + ea->elements->dim;
|
||||
Expressions * elems = new Expressions;
|
||||
elems->setDim(len);
|
||||
for (size_t i= 0; i < ea->elements->dim; ++i)
|
||||
{
|
||||
elems->tdata()[es->len + i] = ea->elements->tdata()[i];
|
||||
}
|
||||
ArrayLiteralExp *dest = new ArrayLiteralExp(e1->loc, elems);
|
||||
dest->type = type;
|
||||
sliceAssignArrayLiteralFromString(dest, es, 0);
|
||||
return dest;
|
||||
es->type = type;
|
||||
e = es;
|
||||
}
|
||||
else if (e2->op == TOKstring && e1->op == TOKarrayliteral &&
|
||||
t1->nextOf()->isintegral())
|
||||
{
|
||||
// [chars] ~ string --> [chars]
|
||||
StringExp *es = (StringExp *)e2;
|
||||
ArrayLiteralExp *ea = (ArrayLiteralExp *)e1;
|
||||
size_t len = es->len + ea->elements->dim;
|
||||
Expressions * elems = new Expressions;
|
||||
elems->setDim(len);
|
||||
for (size_t i= 0; i < ea->elements->dim; ++i)
|
||||
{
|
||||
elems->tdata()[i] = ea->elements->tdata()[i];
|
||||
}
|
||||
ArrayLiteralExp *dest = new ArrayLiteralExp(e1->loc, elems);
|
||||
dest->type = type;
|
||||
sliceAssignArrayLiteralFromString(dest, es, ea->elements->dim);
|
||||
return dest;
|
||||
}
|
||||
else if (e1->op == TOKstring && e2->op == TOKarrayliteral &&
|
||||
t2->nextOf()->isintegral())
|
||||
{
|
||||
// string ~ [chars] --> [chars]
|
||||
StringExp *es = (StringExp *)e1;
|
||||
ArrayLiteralExp *ea = (ArrayLiteralExp *)e2;
|
||||
size_t len = es->len + ea->elements->dim;
|
||||
Expressions * elems = new Expressions;
|
||||
elems->setDim(len);
|
||||
for (size_t i= 0; i < ea->elements->dim; ++i)
|
||||
{
|
||||
elems->tdata()[es->len + i] = ea->elements->tdata()[i];
|
||||
}
|
||||
ArrayLiteralExp *dest = new ArrayLiteralExp(e1->loc, elems);
|
||||
dest->type = type;
|
||||
sliceAssignArrayLiteralFromString(dest, es, 0);
|
||||
return dest;
|
||||
}
|
||||
else if (e1->op == TOKstring && e2->op == TOKint64)
|
||||
{
|
||||
// string ~ char --> string
|
||||
// string ~ char --> string
|
||||
void *s;
|
||||
StringExp *es1 = (StringExp *)e1;
|
||||
StringExp *es;
|
||||
int sz = es1->sz;
|
||||
dinteger_t v = e2->toInteger();
|
||||
|
||||
// Is it a concatentation of homogenous types?
|
||||
// (char[] ~ char, wchar[]~wchar, or dchar[]~dchar)
|
||||
bool homoConcat = (sz == t2->size());
|
||||
size_t len = es1->len;
|
||||
len += homoConcat ? 1 : utf_codeLength(sz, v);
|
||||
|
||||
// Is it a concatentation of homogenous types?
|
||||
// (char[] ~ char, wchar[]~wchar, or dchar[]~dchar)
|
||||
bool homoConcat = (sz == t2->size());
|
||||
size_t len = es1->len;
|
||||
len += homoConcat ? 1 : utf_codeLength(sz, v);
|
||||
|
||||
s = mem.malloc((len + 1) * sz);
|
||||
memcpy(s, es1->string, es1->len * sz);
|
||||
if (homoConcat)
|
||||
memcpy((unsigned char *)s + (sz * es1->len), &v, sz);
|
||||
else
|
||||
if (homoConcat)
|
||||
memcpy((unsigned char *)s + (sz * es1->len), &v, sz);
|
||||
else
|
||||
utf_encode(sz, (unsigned char *)s + (sz * es1->len), v);
|
||||
|
||||
// Add terminating 0
|
||||
|
||||
Reference in New Issue
Block a user