Exemplo n.º 1
0
BOOLEAN matchOverload(TYPE *tnew, TYPE *told)
{
    HASHREC *hnew = basetype(tnew)->syms->table[0];
    HASHREC *hold = basetype(told)->syms->table[0];
//    if (snew->templateLevel != sold->templateLevel)
//        return FALSE;
    if (isconst(tnew) != isconst(told))
        return FALSE;
    while (hnew && hold)
    {
        SYMBOL *snew = (SYMBOL *)hnew->p;
        SYMBOL *sold = (SYMBOL *)hold->p;
        if (sold->thisPtr)
        {
            hold = hold->next;
            if (!hold)
                break;
            sold = hold->p;
        }
        if (snew->thisPtr)
        {
            hnew = hnew->next;
            if (!hnew)
                break;
            snew = hnew->p;
        }
        if (snew->tp->type == bt_templateparam)
        {
            if (sold->tp->type != bt_templateparam || 
                snew->tp->templateParam->p->type != sold->tp->templateParam->p->type ||
                snew->tp->templateParam->p->type != kw_typename ||
                (snew->tp->templateParam->p->byClass.dflt || sold->tp->templateParam->p->byClass.dflt) &&
                (!snew->tp->templateParam->p->byClass.dflt || !sold->tp->templateParam->p->byClass.dflt ||
                !comparetypes(sold->tp->templateParam->p->byClass.dflt, snew->tp->templateParam->p->byClass.dflt, TRUE)))
                
                    break;                    
        }
        else if (sold->tp->type == bt_any || snew->tp->type == bt_any) // packed template param
            break;
        else if (!comparetypes(sold->tp, snew->tp, TRUE) && !sameTemplate(sold->tp, snew->tp) || basetype(sold->tp)->type != basetype(snew->tp)->type)
            break;
        else 
        {
            TYPE *tps = sold->tp;
            TYPE *tpn = snew->tp;
            if (isref(tps))
                tps = basetype(tps)->btp;
            if (isref(tpn))
                tpn = basetype(tpn)->btp;
            if (isconst(tpn) != isconst(tps) || isvolatile(tpn) != isvolatile(tps))
                break;                
        }
        hold = hold->next;
        hnew = hnew->next;
    }
    if (!hold && !hnew)
        return TRUE;
    return NULL;
}
Exemplo n.º 2
0
Tree condtree(Tree e, Tree l, Tree r) {
	Symbol t1;
	Type ty, xty = l->type, yty = r->type;
	Tree p;

	if (isarith(xty) && isarith(yty))
		ty = binary(xty, yty);
	else if (eqtype(xty, yty, 1))
		ty = unqual(xty);
	else if (isptr(xty)   && isnullptr(r))
		ty = xty;
	else if (isnullptr(l) && isptr(yty))
		ty = yty;
	else if (isptr(xty) && !isfunc(xty->type) && isvoidptr(yty)
	||       isptr(yty) && !isfunc(yty->type) && isvoidptr(xty))
		ty = voidptype;
	else if ((isptr(xty) && isptr(yty)
		 && eqtype(unqual(xty->type), unqual(yty->type), 1)))
		ty = xty;
	else {
		typeerror(COND, l, r);
		return consttree(0, inttype);
	}
	if (isptr(ty)) {
		ty = unqual(unqual(ty)->type);
		if (isptr(xty) && isconst(unqual(xty)->type)
		||  isptr(yty) && isconst(unqual(yty)->type))
			ty = qual(CONST, ty);
		if (isptr(xty) && isvolatile(unqual(xty)->type)
		||  isptr(yty) && isvolatile(unqual(yty)->type))
			ty = qual(VOLATILE, ty);
		ty = ptr(ty);
	}
	switch (e->op) {
	case CNST+I: return cast(e->u.v.i != 0   ? l : r, ty);
	case CNST+U: return cast(e->u.v.u != 0   ? l : r, ty);
	case CNST+P: return cast(e->u.v.p != 0   ? l : r, ty);
	case CNST+F: return cast(e->u.v.d != 0.0 ? l : r, ty);
	}
	if (ty != voidtype && ty->size > 0) {
		t1 = genident(REGISTER, unqual(ty), level);
	/*	t1 = temporary(REGISTER, unqual(ty)); */
		l = asgn(t1, l);
		r = asgn(t1, r);
	} else
		t1 = NULL;
	p = tree(COND, ty, cond(e),
		tree(RIGHT, ty, root(l), root(r)));
	p->u.sym = t1;
	return p;
}
Exemplo n.º 3
0
static TYPE *enumConst(char *buf, TYPE *tp)
{
    while (tp && (isconst(tp) || isvolatile(tp) || isrestrict(tp) || tp->type == bt_derivedfromtemplate))
    {
        switch(tp->type)
        {
            case bt_lrqual:
                strcat(buf, "& ");
                break;
            case bt_rrqual:
                strcat(buf, "&& ");
                break;
            case bt_const:
                strcat(buf, tn_const);
                break;
            case bt_volatile:
                strcat(buf, tn_volatile);
                break;
            case bt_restrict:
            case bt_derivedfromtemplate:
/*				strcat(buf, tn_restrict); */
                break;
            default:
                break;
        }
        tp = tp->btp;
    }
    return tp;
}
Exemplo n.º 4
0
Arquivo: stmt.c Projeto: 0culus/ioq3
static void swstmt(int loop, int lab, int lev) {
	Tree e;
	struct swtch sw;
	Code head, tail;

	t = gettok();
	expect('(');
	definept(NULL);
	e = expr(')');
	if (!isint(e->type)) {
		error("illegal type `%t' in switch expression\n",
			e->type);
		e = retype(e, inttype);
	}
	e = cast(e, promote(e->type));
	if (generic(e->op) == INDIR && isaddrop(e->kids[0]->op)
	&& e->kids[0]->u.sym->type == e->type
	&& !isvolatile(e->kids[0]->u.sym->type)) {
		sw.sym = e->kids[0]->u.sym;
		walk(NULL, 0, 0);
	} else {
		sw.sym = genident(REGISTER, e->type, level);
		addlocal(sw.sym);
		walk(asgn(sw.sym, e), 0, 0);
	}
	head = code(Switch);
	sw.lab = lab;
	sw.deflab = NULL;
	sw.ncases = 0;
	sw.size = SWSIZE;
	sw.values = newarray(SWSIZE, sizeof *sw.values, FUNC);
	sw.labels = newarray(SWSIZE, sizeof *sw.labels, FUNC);
	refinc /= 10.0;
	statement(loop, &sw, lev);
	if (sw.deflab == NULL) {
		sw.deflab = findlabel(lab);
		definelab(lab);
		if (sw.ncases == 0)
			warning("switch statement with no cases\n");
	}
	if (findlabel(lab + 1)->ref)
		definelab(lab + 1);
	tail = codelist;
	codelist = head->prev;
	codelist->next = head->prev = NULL;
	if (sw.ncases > 0)
		swgen(&sw);
	branch(lab);
	head->next->prev = codelist;
	codelist->next = head->next;
	codelist = tail;
}
Exemplo n.º 5
0
static TYPE *enumConst(char *buf, TYPE *tp)
{
    while (isconst(tp) || isvolatile(tp) || isrestrict(tp))
    {
        switch(tp->type)
        {
            case bt_const:
                strcat(buf, tn_const);
                break;
            case bt_volatile:
                strcat(buf, tn_volatile);
                break;
            case bt_restrict:
/*				strcat(buf, tn_restrict); */
                break;
        }
        tp = tp->btp;
    }
    return tp;
}
Exemplo n.º 6
0
Type assign(Type xty, Tree e) {
	Type yty = unqual(e->type);

	xty = unqual(xty);
	if (isenum(xty))
		xty = xty->type;
	if (xty->size == 0 || yty->size == 0)
		return NULL;
	if ( isarith(xty) && isarith(yty)
	||  isstruct(xty) && xty == yty)
		return xty;
	if (isptr(xty) && isnullptr(e))
		return xty;
	if ((isvoidptr(xty) && isptr(yty)
	  || isptr(xty)     && isvoidptr(yty))
	&& (  (isconst(xty->type)    || !isconst(yty->type))
	   && (isvolatile(xty->type) || !isvolatile(yty->type))))
		return xty;

	if ((isptr(xty) && isptr(yty)
	    && eqtype(unqual(xty->type), unqual(yty->type), 1))
	&&  (  (isconst(xty->type)    || !isconst(yty->type))
	    && (isvolatile(xty->type) || !isvolatile(yty->type))))
		return xty;
	if (isptr(xty) && isptr(yty)
	&& (  (isconst(xty->type)    || !isconst(yty->type))
	   && (isvolatile(xty->type) || !isvolatile(yty->type)))) {
		Type lty = unqual(xty->type), rty = unqual(yty->type);
		if (isenum(lty) && rty == inttype
		||  isenum(rty) && lty == inttype) {
			if (Aflag >= 1)
				warning("assignment between `%t' and `%t' is compiler-dependent\n",
					xty, yty);
			return xty;
		}
	}
	return NULL;
}
Exemplo n.º 7
0
static void *uid2type(int uid) {
	assert(uid >= 0 && uid < nuids);
	if (itemmap[uid] == NULL) {
		Type ty;
		rcc_type_ty type = (void *)items[uid];
		assert(items[uid]);
		assert(items[uid]->uid == uid);
		assert(items[uid]->kind == rcc_Type_enum);
		type = items[uid]->v.rcc_Type.type;
		assert(type);
		switch (type->kind) {
		case rcc_INT_enum:
			ty = btot(INT, type->size);
			assert(ty->align == type->align);
			break;
		case rcc_UNSIGNED_enum:
			ty = btot(UNSIGNED, type->size);
			assert(ty->align == type->align);
			break;
		case rcc_FLOAT_enum:
			ty = btot(FLOAT, type->size);
			assert(ty->align == type->align);
			break;
		case rcc_VOID_enum:
			ty = voidtype;
			break;
		case rcc_POINTER_enum:
			ty = ptr(uid2type(type->v.rcc_POINTER.type));
			break;
		case rcc_ARRAY_enum:
			ty = uid2type(type->v.rcc_ARRAY.type);
			assert(ty->size > 0);
			ty = array(ty, type->size/ty->size, 0);
			break;
		case rcc_CONST_enum:
			ty = qual(CONST, uid2type(type->v.rcc_CONST.type));
			break;
		case rcc_VOLATILE_enum:
			ty = qual(VOLATILE, uid2type(type->v.rcc_VOLATILE.type));
			break;
		case rcc_ENUM_enum: {
			int i, n = Seq_length(type->v.rcc_ENUM.ids);
			ty = newstruct(ENUM, string(type->v.rcc_ENUM.tag));
			ty->type = inttype;
			ty->size = ty->type->size;
			ty->align = ty->type->align;
			ty->u.sym->u.idlist = newarray(n + 1, sizeof *ty->u.sym->u.idlist, PERM);
			for (i = 0; i < n; i++) {
				rcc_enum__ty e = Seq_remlo(type->v.rcc_ENUM.ids);
				Symbol p = install(e->id, &identifiers, GLOBAL, PERM);
				p->type = ty;
				p->sclass = ENUM;
				p->u.value = e->value;
				ty->u.sym->u.idlist[i] = p;
				free(e);
			}
			ty->u.sym->u.idlist[i] = NULL;
			Seq_free(&type->v.rcc_ENUM.ids);
			break;
			}
		case rcc_STRUCT_enum: case rcc_UNION_enum: {
			int i, n;
			Field *tail;
			list_ty fields;
			if (type->kind == rcc_STRUCT_enum) {
				ty = newstruct(STRUCT, string(type->v.rcc_STRUCT.tag));
				fields = type->v.rcc_STRUCT.fields;
			} else {
				ty = newstruct(UNION, string(type->v.rcc_UNION.tag));
				fields = type->v.rcc_UNION.fields;
			}
			itemmap[uid] = ty;	/* recursive types */
			ty->size = type->size;
			ty->align = type->align;
			tail = &ty->u.sym->u.s.flist;
			n = Seq_length(fields);
			for (i = 0; i < n; i++) {
				rcc_field_ty field = Seq_remlo(fields);
				NEW0(*tail, PERM);
				(*tail)->name = (char *)field->id;
				(*tail)->type = uid2type(field->type);
				(*tail)->offset = field->offset;
				(*tail)->bitsize = field->bitsize;
				(*tail)->lsb = field->lsb;
				if (isconst((*tail)->type))
					ty->u.sym->u.s.cfields = 1;
				if (isvolatile((*tail)->type))
					ty->u.sym->u.s.vfields = 1;
				tail = &(*tail)->link;
				free(field);
			}
			Seq_free(&fields);
			break;
			}
		case rcc_FUNCTION_enum: {
			int n = Seq_length(type->v.rcc_FUNCTION.formals);
			if (n > 0) {
				int i;
				Type *proto = newarray(n + 1, sizeof *proto, PERM);
				for (i = 0; i < n; i++) {
					int *formal = Seq_remlo(type->v.rcc_FUNCTION.formals);
					proto[i] = uid2type(*formal);
					free(formal);
				}
				proto[i] = NULL;
				ty = func(uid2type(type->v.rcc_FUNCTION.type), proto, 0);
			} else
				ty = func(uid2type(type->v.rcc_FUNCTION.type), NULL, 1);
			Seq_free(&type->v.rcc_FUNCTION.formals);
			break;
			}
		default: assert(0);
		}
		if (itemmap[uid] == NULL) {
			itemmap[uid] = ty;
			free(type);
			free(items[uid]);
			items[uid] = NULL;
		} else
			assert(itemmap[uid] == ty);
	}
	return itemmap[uid];
}
Exemplo n.º 8
0
Arquivo: tree.c Projeto: UraKn0x/gbdk
static Tree root1(Tree p) {
	if (p == NULL)
		return p;
	if (p->type == voidtype)
		warn++;
	switch (generic(p->op)) {
	case COND: {
		Tree q = p->kids[1];
		assert(q && q->op == RIGHT);
		if (p->u.sym && q->kids[0] && generic(q->kids[0]->op) == ASGN)
			q->kids[0] = root1(q->kids[0]->kids[1]);
		else
			q->kids[0] = root1(q->kids[0]);
		if (p->u.sym && q->kids[1] && generic(q->kids[1]->op) == ASGN)
			q->kids[1] = root1(q->kids[1]->kids[1]);
		else
			q->kids[1] = root1(q->kids[1]);
		p->u.sym = 0;
		if (q->kids[0] == 0 && q->kids[1] == 0)
			p = root1(p->kids[0]);
		}
		break;
	case AND: case OR:
		if ((p->kids[1] = root1(p->kids[1])) == 0)
			p = root1(p->kids[0]);
		break;
	case NOT:
		if (warn++ == 0)
			warning("expression with no effect elided\n");
		return root1(p->kids[0]);
	case RIGHT:
		if (p->kids[1] == 0)
			return root1(p->kids[0]);
		if (p->kids[0] && p->kids[0]->op == CALL+B
		&&  p->kids[1] && p->kids[1]->op == INDIR+B)
			/* avoid premature release of the CALL+B temporary */
			return p->kids[0];
		if (p->kids[0] && p->kids[0]->op == RIGHT
		&&  p->kids[1] == p->kids[0]->kids[0])
			/* de-construct e++ construction */
			return p->kids[0]->kids[1];
		p = tree(RIGHT, p->type, root1(p->kids[0]), root1(p->kids[1]));
		return p->kids[0] || p->kids[1] ? p : (Tree)0;
	case EQ:  case NE:  case GT:   case GE:  case LE:  case LT: 
	case ADD: case SUB: case MUL:  case DIV: case MOD:
	case LSH: case RSH: case BAND: case BOR: case BXOR:
		if (warn++ == 0)
			warning("expression with no effect elided\n");
		p = tree(RIGHT, p->type, root1(p->kids[0]), root1(p->kids[1]));
		return p->kids[0] || p->kids[1] ? p : (Tree)0;
	case INDIR:
		if (p->type->size == 0 && unqual(p->type) != voidtype)
			warning("reference to `%t' elided\n", p->type);
		if (isptr(p->kids[0]->type) && isvolatile(p->kids[0]->type->type))
			warning("reference to `volatile %t' elided\n", p->type);
		/* fall thru */
	case CVI: case CVF: case CVU: case CVP:
	case NEG: case BCOM: case FIELD:
		if (warn++ == 0)
			warning("expression with no effect elided\n");
		return root1(p->kids[0]);
	case ADDRL: case ADDRG: case ADDRF: case CNST:
		if (needconst)
			return p;
		if (warn++ == 0)
			warning("expression with no effect elided\n");
		return NULL;
	case ARG: case ASGN: case CALL: case JUMP: case LABEL:
		break;
	default: assert(0);
	}
	return p;
}
Exemplo n.º 9
0
BOOL comparetypes(TYPE *typ1, TYPE *typ2, int exact)
{
    if (typ1->type == bt_any || typ2->type == bt_any)
        return TRUE;
    if (typ1->type == bt_typedef)
        typ1 = basetype(typ1);
    if (typ2->type == bt_typedef)
        typ2 = basetype(typ2);
    if (isref(typ1))
        typ1 = basetype(typ1)->btp;
    if (isref(typ2))
        typ2 = basetype(typ2)->btp;
    if (ispointer(typ1) && ispointer(typ2))
        if (exact)
        {
            int arr = FALSE;
            int first = TRUE;
            while (ispointer(typ1) && ispointer(typ2))
            {
                if (!first && (exact == 1))
                    if (isconst(typ2) && !isconst(typ1) || isvolatile(typ2) && !isvolatile(typ1))
                        return FALSE;
                first = FALSE;
                typ1 = basetype(typ1);
                typ2 = basetype(typ2);
                if (typ1->type != typ2->type)
                    return FALSE;
                if (arr && typ1->array != typ2->array)	
                    return FALSE;
                if (arr && typ1->size != typ2->size)
                    return FALSE;
                arr |= typ1->array | typ2->array;
                typ1 = typ1->btp;
                typ2 = typ2->btp;				
            }
            if ((exact == 1) && (isconst(typ2) && !isconst(typ1) || isvolatile(typ2) && !isvolatile(typ1)))
                return FALSE;
            return comparetypes(typ1, typ2, TRUE);
        }
            
        else
            return TRUE;
    
    typ1 = basetype(typ1);
    typ2 = basetype(typ2);
    if (exact && (isfunction(typ1) || isfuncptr(typ1)) && (isfunction(typ2) || isfuncptr(typ2)))
    {
        HASHREC *hr1;
        HASHREC *hr2;
        typ1 = basetype(typ1);
        typ2 = basetype(typ2);
        if (ispointer(typ1))
            typ1 = basetype(typ1->btp);
        if (ispointer(typ2))
            typ2 = basetype(typ2->btp);
        if (!comparetypes(typ1->btp, typ2->btp, exact))
            return FALSE;
        hr1 = typ1->syms->table[0];
        hr2 = typ2->syms->table[0];
        while (hr1 && hr2)
        {
            SYMBOL *sp1 = (SYMBOL *)hr1->p;
            SYMBOL *sp2 = (SYMBOL *)hr2->p;
            if (!comparetypes(sp1->tp, sp2->tp, exact))
                return FALSE;
            hr1 = hr1->next;
            hr2 = hr2->next;
        }
        if (hr1 || hr2)
            return FALSE;
        return TRUE;
    }
    if (cparams.prm_cplusplus)
    {
        if (typ1->scoped != typ2->scoped)
            return FALSE;
        if (typ1->type == bt_enum)
        {
            if (typ2->type == bt_enum)
                return typ1->sp == typ2->sp;
            else
                return isint(typ2);
        }
        else if (typ2->type == bt_enum)
        {
            return isint(typ1);
        }
        if (typ1->type == typ2->type && typ1->type == bt_memberptr)
        {
            if (typ1->sp != typ2->sp)
            {
                if (classRefCount(typ2->sp, typ1->sp) != 1)
                    return FALSE;
            }
            return comparetypes(typ1->btp, typ2->btp, exact);
        }
    }
    if (typ1->type == typ2->type && (isstructured(typ1) || exact && typ1->type == bt_enum))
        return typ1->sp == typ2->sp;
    if (typ1->type == typ2->type || !exact && isarithmetic(typ2) && isarithmetic(typ1))
        return TRUE;
    if (isfunction(typ1) && isfunction(typ2) && 
        typ1->sp->linkage == typ2->sp->linkage)
        return TRUE;
    else if (!exact && (ispointer(typ1) && (isfuncptr(typ2) || isfunction(typ2) || isint(typ2))
             || ispointer(typ2) && (isfuncptr(typ1) || isfunction(typ1) || isint(typ1))))
            return (TRUE);
    else if (typ1->type == bt_enum && isint(typ2))
    {
        return TRUE;
    }
    else if (typ2->type == bt_enum && isint(typ1))
    {
        return TRUE;
    }
    return FALSE;
}
Exemplo n.º 10
0
/*
 * emittype - emit ty's type number, emitting its definition if necessary.
 * Returns the output column number after emission; col is the approximate
 * output column before emission and is used to emit continuation lines for long
 * struct, union, and enum types. Continuations are not emitted for other types,
 * even if the definition is long. lev is the depth of calls to emittype.
 */
static int emittype(Type ty, int lev, int col) {
	int tc = ty->x.typeno;

	if (isconst(ty) || isvolatile(ty)) {
		col = emittype(ty->type, lev, col);
		ty->x.typeno = ty->type->x.typeno;
		ty->x.printed = 1;
		return col;
	}
	if (tc == 0) {
		ty->x.typeno = tc = ++ntypes;
/*              fprint(2,"`%t'=%d\n", ty, tc); */
	}
	print("%d", tc), col += 3;
	if (ty->x.printed)
		return col;
	ty->x.printed = 1;
	switch (ty->op) {
	case VOID:	/* void is defined as itself */
		print("=%d", tc), col += 1+3;
		break;
	case INT:
		if (ty == chartype)	/* plain char is a subrange of itself */
			print("=r%d;%d;%d;", tc, ty->u.sym->u.limits.min.i, ty->u.sym->u.limits.max.i),
				col += 2+3+2*2.408*ty->size+2;
		else			/* other signed ints are subranges of int */
			print("=r1;%D;%D;", ty->u.sym->u.limits.min.i, ty->u.sym->u.limits.max.i),
				col += 4+2*2.408*ty->size+2;
		break;
	case UNSIGNED:
		if (ty == chartype)	/* plain char is a subrange of itself */
			print("=r%d;0;%u;", tc, ty->u.sym->u.limits.max.i),
				col += 2+3+2+2.408*ty->size+1;
		else			/* other signed ints are subranges of int */
			print("=r1;0;%U;", ty->u.sym->u.limits.max.i),
				col += 4+2.408*ty->size+1;
		break;
	case FLOAT:	/* float, double, long double get sizes, not ranges */
		print("=r1;%d;0;", ty->size), col += 4+1+3;
		break;
	case POINTER:
		print("=*"), col += 2;
		col = emittype(ty->type, lev + 1, col);
		break;
	case FUNCTION:
		print("=f"), col += 2;
		col = emittype(ty->type, lev + 1, col);
		break;
	case ARRAY:	/* array includes subscript as an int range */
		if (ty->size && ty->type->size)
			print("=ar1;0;%d;", ty->size/ty->type->size - 1), col += 7+3+1;
		else
			print("=ar1;0;-1;"), col += 10;
		col = emittype(ty->type, lev + 1, col);
		break;
	case STRUCT: case UNION: {
		Field p;
		if (!ty->u.sym->defined) {
			print("=x%c%s:", ty->op == STRUCT ? 's' : 'u', ty->u.sym->name);
			col += 2+1+strlen(ty->u.sym->name)+1;
			break;
		}
		if (lev > 0 && (*ty->u.sym->name < '0' || *ty->u.sym->name > '9')) {
			ty->x.printed = 0;
			break;
		}
		print("=%c%d", ty->op == STRUCT ? 's' : 'u', ty->size), col += 1+1+3;
		for (p = fieldlist(ty); p; p = p->link) {
			if (p->name)
				print("%s:", p->name), col += strlen(p->name)+1;
			else
				print(":"), col += 1;
			col = emittype(p->type, lev + 1, col);
			if (p->lsb)
				print(",%d,%d;", 8*p->offset +
					(IR->little_endian ? fieldright(p) : fieldleft(p)),
					fieldsize(p));
			else
				print(",%d,%d;", 8*p->offset, 8*p->type->size);
			col += 1+3+1+3+1;	/* accounts for ,%d,%d; */
			if (col >= 80 && p->link) {
				print("\\\\\",%d,0,0,0\n.stabs \"", N_LSYM);
				col = 8;
			}
		}
		print(";"), col += 1;
		break;
		}
	case ENUM: {
		Symbol *p;
		if (lev > 0 && (*ty->u.sym->name < '0' || *ty->u.sym->name > '9')) {
			ty->x.printed = 0;
			break;
		}
		print("=e"), col += 2;
		for (p = ty->u.sym->u.idlist; *p; p++) {
			print("%s:%d,", (*p)->name, (*p)->u.value), col += strlen((*p)->name)+3;
			if (col >= 80 && p[1]) {
				print("\\\\\",%d,0,0,0\n.stabs \"", N_LSYM);
				col = 8;
			}
		}
		print(";"), col += 1;
		break;
		}
	default:
		assert(0);
	}
	return col;
}
Exemplo n.º 11
0
char *mangleType (char *in, TYPE *tp, BOOLEAN first)
{
    char nm[4096];
    int i;
    HASHREC *hr ;
    if(!tp)
    {
        sprintf(in, "%d%s", strlen("initializer-list"), "initializer-list");
        in += strlen(in);
    }
    else if (tp->type == bt_typedef)
    {
       in = mangleType(in, tp->btp, FALSE);
    }
    else if (isstructured(tp) && basetype(tp)->sp->templateLevel)
    {
        {
            if (isconst(tp))
                *in++ = 'x';
            if (isvolatile(tp))
                *in++ = 'y';
            if (islrqual(tp))
                *in++ = 'r';
            if (isrrqual(tp))
                *in++ = 'R';
        }
        in = mangleTemplate(in, basetype(tp)->sp, basetype(tp)->sp->templateParams);
    }
    else
    {
//        if (ispointer(tp) || isref(tp))
//        {
//            if (basetype(tp)->btp)
//            {
//                if (isconst(basetype(tp)->btp))
//                    *in++ = 'x';
//                if (isvolatile(basetype(tp)->btp))
//                    *in++ = 'y';
//            }
//        }
//        if (isfunction(tp))
        {
            if (isconst(tp))
                *in++ = 'x';
            if (isvolatile(tp))
                *in++ = 'y';
            if (islrqual(tp))
                *in++ = 'r';
            if (isrrqual(tp))
                *in++ = 'R';
        }
        tp = basetype(tp);
        switch (tp->type)
        {
        /*
            case bt_templateplaceholder:
                tplPlaceholder(nm, tp->lst.head->name, tp->lst.tail);
                sprintf(buf, "%d%s", strlen(nm), nm);
                buf += strlen(buf);
                break;
        */
            case bt_func:
            case bt_ifunc:
                if (basetype(tp)->sp && basetype(tp)->sp->parentClass && !first)
                {
                    *in++ = 'M';
                    in = getName(in, tp->sp->parentClass);
                    in += strlen(in);
                }
                *in++ = 'q';
                hr = tp->syms->table[0];
                while (hr)
                {
                    SYMBOL *sp = (SYMBOL *)hr->p;
                    if (!sp->thisPtr)
                        in = mangleType(in, sp->tp, TRUE);
                    hr = hr->next ;
                }
                *in++ = '$';
                // return value
                in = mangleType(in, tp->btp, TRUE);
                break;
            case bt_memberptr:
                *in++ = 'M';
                in = getName(in, tp->sp);
                if (isfunction(tp->btp))
                {
                    *in++ = 'q';
                    hr = basetype(tp->btp)->syms->table[0];
                    while (hr)
                    {
                        SYMBOL *sp = (SYMBOL *)hr->p;
                        if (!sp->thisPtr)
                            in = mangleType(in, sp->tp, TRUE);
                        hr = hr->next ;
                    }
                    *in++ = '$';
                    in = mangleType (in, tp->btp->btp, TRUE);
                }
                else
                {
                    *in++ = '$';
                    in = mangleType (in, basetype(tp)->btp, TRUE);
                }
                break;
            case bt_enum:
            case bt_struct:
            case bt_union:
            case bt_class:
                in = getName(in, tp->sp);
                break;
            case bt_bool:
                in = lookupName(in, "bool");
                in += strlen(in);
                break;
            case bt_unsigned_short:
                *in++ = 'u';
            case bt_short:
                *in++ = 's';
                break;
            case bt_unsigned:
                *in++ = 'u';
            case bt_int:
                *in++ = 'i';
                break;
            case bt_char16_t:
                *in++ = 'h';
                break;
            case bt_char32_t:
                *in++ = 'H';
                break;
            case bt_unsigned_long:
                *in++ = 'u';
            case bt_long:
                *in++ = 'l';
                break;
            case bt_unsigned_long_long:
                *in++ = 'u';
            case bt_long_long:
                *in++ = 'L';
                break;
            case bt_unsigned_char:
                *in++ = 'u';
            case bt_char:
                *in++ = 'c';
                break;
            case bt_signed_char:
                *in++ = 'S';
                *in++ = 'c';
                break;
            case bt_wchar_t:
                *in++ = 'C';
                break;
            case bt_float_complex:
                *in++ = 'F';
                break;
            case bt_double_complex:
                *in++ = 'D';
                break;
            case bt_long_double_complex:
                *in++ = 'G';
                break;
            case bt_float:
                *in++ = 'f';
                break;
            case bt_double:
                *in++ = 'd';
                break;
            case bt_long_double:
                *in++ = 'g';
                break;
            case bt_pointer:
                if (tp->nullptrType)
                {
                    in = lookupName(in, "nullptr_t");
                    in += strlen(in);
                }
                else
                {
                    if (first|| !tp->array)
                    {
                        *in++ = 'p';
                    }
                    else
                    {
                        sprintf(in,"A%ld",tp->btp->size ? tp->size / tp->btp->size : 0);
                        in += strlen(in);
                    }
                    in = mangleType(in, tp->btp, FALSE);
                }
                break;
            case bt_far:
                *in++ = 'P';
                in = mangleType(in, tp->btp, FALSE);
                break;
            case bt_lref:
                *in++ = 'r';
                in = mangleType(in, tp->btp, FALSE);
                break;
            case bt_rref:
                *in++ = 'R';
                in = mangleType(in, tp->btp, FALSE);
                break;
            case bt_ellipse:
                *in++ = 'e';
                break;
            case bt_void:
            case bt_any:
                *in++ = 'v';
                break;
            case bt_templateparam:
                in = getName(in, tp->templateParam->p->sym);
                break;
            case bt_templateselector:
            {
                TEMPLATESELECTOR *s = tp->sp->templateSelector;
                char *p;
                s = s->next;
                if (s->isTemplate)
                    p = mangleTemplate(nm, s->sym, s->templateParams);
                else
                    p = getName(nm, s->sym);
				p[0] =0;
				if (strlen(nm) > sizeof(nm))
                    p = mangleTemplate(nm, s->sym, s->templateParams);
                s = s->next ;
                while (s)
                {
                    strcat(nm , "@");
                    strcat(nm , s->name);
                    s= s->next;
                }
                p = nm;
                while (isdigit(*p))
                    p++;
                sprintf(in, "%d%s", strlen(p), p);
                in += strlen(in);
            }
                break;
            case bt_templatedecltype:
                // the index is being used to make names unique so two decltypes won't collide when storing them
                // in a symbol table...
                declTypeIndex = (declTypeIndex + 1) %1000;
                *in++ = 'E';
                sprintf(in, "%03d", declTypeIndex);
                in += 3;
                break;
            case bt_aggregate:
                in = getName(in, tp->sp);
                break;
            default:
                diag("mangleType: unknown type");
                break;
        }
    }
    *in= 0;
    return in;
}
Exemplo n.º 12
0
BOOLEAN comparetypes(TYPE *typ1, TYPE *typ2, int exact)
{
    if (typ1->type == bt_any || typ2->type == bt_any)
        return TRUE;
    while (typ1->type == bt_typedef)
        typ1 = basetype(typ1);
    while (typ2->type == bt_typedef)
        typ2 = basetype(typ2);
    typ1 = replaceTemplateSelector(typ1);
    typ2 = replaceTemplateSelector(typ2);
    if (isDerivedFromTemplate(typ1))
        typ1 = typ1->btp;
    if (isDerivedFromTemplate(typ2))
        typ2 = typ2->btp;
    while (isref(typ1))
        typ1 = basetype(typ1)->btp;
    while (isref(typ2))
        typ2 = basetype(typ2)->btp;
    while (typ1->type == bt_typedef)
        typ1 = basetype(typ1);
    while (typ2->type == bt_typedef)
        typ2 = basetype(typ2);
    if (typ1->type == bt_templateselector && typ2->type == bt_templateselector)
        return templateselectorcompare(typ1->sp->templateSelector, typ2->sp->templateSelector);
    if (typ1->type == bt_templatedecltype && typ2->type == bt_templatedecltype)
        return templatecompareexpressions(typ1->templateDeclType, typ2->templateDeclType);
    if (ispointer(typ1) && ispointer(typ2))
    {
        if (exact)
        {
            int arr = FALSE;
            int first = TRUE;
            while (ispointer(typ1) && ispointer(typ2))
            {
                if (!first && (exact == 1))
                    if ((isconst(typ2) && !isconst(typ1)) || (isvolatile(typ2) && !isvolatile(typ1)))
                        return FALSE;
                first = FALSE;
                typ1 = basetype(typ1);
                typ2 = basetype(typ2);
                if (typ1->type != typ2->type)
                    return FALSE;
                if (arr && typ1->array != typ2->array)	
                    return FALSE;
                if (arr && typ1->size != typ2->size)
                    return FALSE;
                arr |= typ1->array | typ2->array;
                typ1 = typ1->btp;
                typ2 = typ2->btp;				
            }
            if (exact == 1 && ((isconst(typ2) && !isconst(typ1)) || (isvolatile(typ2) && !isvolatile(typ1))))
                return FALSE;
            return comparetypes(typ1, typ2, TRUE);
        }
            
        else
            return TRUE;
    }
    typ1 = basetype(typ1);
    typ2 = basetype(typ2);
    if (exact && (isfunction(typ1) || isfuncptr(typ1)) && (isfunction(typ2) || isfuncptr(typ2)))
    {
        HASHREC *hr1;
        HASHREC *hr2;
        typ1 = basetype(typ1);
        typ2 = basetype(typ2);
        if (ispointer(typ1))
            typ1 = basetype(typ1)->btp;
        if (ispointer(typ2))
            typ2 = basetype(typ2)->btp;
        if (!comparetypes(typ1->btp, typ2->btp, exact))
            return FALSE;
        if (!matchOverload(typ1, typ2, TRUE))
            return FALSE;
        return TRUE;
    }
    if (cparams.prm_cplusplus)
    {
        if (typ1->scoped != typ2->scoped)
            return FALSE;
        if (typ1->type == bt_enum)
        {
            if (typ2->type == bt_enum)
                return typ1->sp == typ2->sp;
            else
                return isint(typ2);
        }
        else if (typ2->type == bt_enum)
        {
            return isint(typ1);
        }
        if (typ1->type == typ2->type && typ1->type == bt_memberptr)
        {
            if (typ1->sp != typ2->sp)
            {
                if (classRefCount(typ1->sp, typ2->sp) != 1)
                    return FALSE;
            }
            return comparetypes(typ1->btp, typ2->btp, exact);
        }
    }
    if (typ1->type == typ2->type && (isstructured(typ1) || (exact && typ1->type == bt_enum)))
        return typ1->sp == typ2->sp;
    if (typ1->type == typ2->type || (!exact && isarithmetic(typ2) && isarithmetic(typ1)))
        return TRUE;
    if (isfunction(typ1) && isfunction(typ2) && 
        typ1->sp->linkage == typ2->sp->linkage)
        return TRUE;
    else if (!exact && ((ispointer(typ1) && (isfuncptr(typ2) || isfunction(typ2) || isint(typ2)))
             || (ispointer(typ2) && (isfuncptr(typ1) || isfunction(typ1) || isint(typ1)))))
            return (TRUE);
    else if (typ1->type == bt_enum && isint(typ2))
    {
        return TRUE;
    }
    else if (typ2->type == bt_enum && isint(typ1))
    {
        return TRUE;
    }
    return FALSE;
}