Exemplo n.º 1
0
/**
 * 翻译break 语句
 * A break statement terminates the execution of associated
 * switch or loop.
 *
 * break is translated into:
 *     goto switch or loop's nextBB
 * nextBB:
 *     ...
 */
static void TranslateBreakStatement (AstStatement stmt)
{
	AstBreakStatement brkStmt = AsBreak(stmt);

	if (brkStmt->target->kind == NK_SwitchStatement) { 

        /* switch 在跳转 */
		GenerateJump (AsSwitch(brkStmt->target)->nextBB);
	} else {
    
        /* loop 跳转 */
		GenerateJump (AsLoop(brkStmt->target)->nextBB);
	}

	StartBBlock (CreateBBlock ());
}
Exemplo n.º 2
0
 /* 翻译switch 语句 
  * 创建case default 基本块 */
static void TranslateSwitchStatement (AstStatement stmt)
{
	AstSwitchStatement  swtchStmt = AsSwitch(stmt);
	AstCaseStatement    p, q;
	SwitchBucket        bucket, b;
	SwitchBucket        *bucketArray;
	int     i, val;
	Symbol  sym;

    /* 翻译switch 的表达式 */
    sym = TranslateExpression (swtchStmt->expr);

	bucket = b = NULL;
	p = swtchStmt->cases;

    /* 创建基本块, 并给case 语句排序 */
	while ( p ) {

		q = p;
		p = p->nextCase;

        /* 给case 创建基本块 */
		q->respBB = CreateBBlock ();
        /* case 的表达式 */
		val = q->expr->val.i[0];

		if (bucket && (bucket->ncase + 1) * 2 > (val - bucket->minVal)) {

			bucket->ncase++;
			bucket->maxVal  = val;
			*bucket->tail   = q;
			bucket->tail    = &(q->nextCase);
			swtchStmt->nbucket -= MergeSwitchBucket (&bucket);
		} else {

			CALLOC(b);

			b->cases    = q;
			b->ncase    = 1;
            /* 初始化最小大值 */
			b->minVal   = b->maxVal = val;
			b->tail     = &(q->nextCase);
			b->prev     = bucket;
			bucket      = b;
			swtchStmt->nbucket++;
		}
	}

	swtchStmt->buckets = bucket;

	bucketArray = HeapAllocate (CurrentHeap, swtchStmt->nbucket * sizeof (SwitchBucket));

	for (i = swtchStmt->nbucket - 1; i >= 0; i--) {

		bucketArray[i] = bucket;
		*bucket->tail  = NULL;
		bucket = bucket->prev;
	}

    /* default 语句 */
	swtchStmt->defBB = CreateBBlock();
	if (swtchStmt->defStmt) {

		swtchStmt->defStmt->respBB = swtchStmt->defBB;
		swtchStmt->nextBB = CreateBBlock();
	} else {

		swtchStmt->nextBB = swtchStmt->defBB;
	}

	TranslateSwitchBuckets (bucketArray, 0, swtchStmt->nbucket - 1, sym, NULL, swtchStmt->defBB);
	TranslateStatement (swtchStmt->stmt);
	StartBBlock (swtchStmt->nextBB);
}
Exemplo n.º 3
0
static void DumpStatement(AstStatement stmt, int pos)
{
	switch (stmt->kind)
	{
	case NK_ExpressionStatement:

		DumpExpression(AsExpr(stmt)->expr, pos);
		break;

	case NK_LabelStatement:

		fprintf(ASTFile, "(label %s:\n", AsLabel(stmt)->id);
		LeftAlign(ASTFile, pos + 2);
		DumpStatement(AsLabel(stmt)->stmt, pos + 2);
		LeftAlign(ASTFile, pos);
		fprintf(ASTFile, "end-label)");
		break;

	case NK_CaseStatement:

		fprintf(ASTFile, "(case  ");
		DumpExpression(AsCase(stmt)->expr, pos + 7);
		LeftAlign(ASTFile, pos + 2);
		DumpStatement(AsCase(stmt)->stmt, pos + 2);
		LeftAlign(ASTFile, pos);
		fprintf(ASTFile, "end-case)");
		break;

	case NK_DefaultStatement:

		fprintf(ASTFile, "(default  ");
		DumpStatement(AsDef(stmt)->stmt, pos + 10);
		LeftAlign(ASTFile, pos);
		fprintf(ASTFile, "end-default)");
		break;

	case NK_IfStatement:

		fprintf(ASTFile, "(if  ");
		DumpExpression(AsIf(stmt)->expr, pos + 5);
		LeftAlign(ASTFile, pos + 2);
		fprintf(ASTFile, "(then  ");
		LeftAlign(ASTFile, pos + 4);
		DumpStatement(AsIf(stmt)->thenStmt, pos + 4);
		LeftAlign(ASTFile, pos + 2);
		fprintf(ASTFile, "end-then)");
		if (AsIf(stmt)->elseStmt != NULL)
		{
			LeftAlign(ASTFile, pos + 2);
			fprintf(ASTFile, "(else  ");
			LeftAlign(ASTFile, pos + 4);
			DumpStatement(AsIf(stmt)->elseStmt, pos + 4);
			LeftAlign(ASTFile, pos + 2);
			fprintf(ASTFile, "end-else)");
		}
		LeftAlign(ASTFile, pos);
		fprintf(ASTFile, "end-if)");
		break;

	case NK_SwitchStatement:

		fprintf(ASTFile, "(switch ");
		DumpExpression(AsSwitch(stmt)->expr, pos + 9);
		LeftAlign(ASTFile, pos + 2);
		DumpStatement(AsSwitch(stmt)->stmt, pos + 2);
		LeftAlign(ASTFile, pos);
		fprintf(ASTFile, "end-switch)");
		break;

	case NK_WhileStatement:

		fprintf(ASTFile, "(while  ");
		DumpExpression(AsLoop(stmt)->expr, pos + 8);
		LeftAlign(ASTFile, pos + 2);
		DumpStatement(AsLoop(stmt)->stmt, pos + 2);
		LeftAlign(ASTFile, pos);
		fprintf(ASTFile, "end-while)");
		break;

	case NK_DoStatement:

		fprintf(ASTFile, "(do  ");
		DumpExpression(AsLoop(stmt)->expr, pos + 5);
		LeftAlign(ASTFile, pos + 2);
		DumpStatement(AsLoop(stmt)->stmt, pos + 2);
		LeftAlign(ASTFile, pos);
		fprintf(ASTFile, ")");
		break;

	case NK_ForStatement:

		fprintf(ASTFile, "(for  ");
		DumpExpression(AsFor(stmt)->initExpr, pos + 6);
		LeftAlign(ASTFile, pos + 6);
		DumpExpression(AsFor(stmt)->expr, pos + 6);
		LeftAlign(ASTFile, pos + 6);
		DumpExpression(AsFor(stmt)->incrExpr, pos + 6);
		LeftAlign(ASTFile, pos + 2);
		DumpStatement(AsFor(stmt)->stmt, pos + 2);
		LeftAlign(ASTFile, pos);
		fprintf(ASTFile, "end-for)");
		break;

	case NK_GotoStatement:

		fprintf(ASTFile, "(goto %s)", AsGoto(stmt)->id);
		break;

	case NK_ContinueStatement:

		fprintf(ASTFile, "(continue)");
		break;

	case NK_BreakStatement:

		fprintf(ASTFile, "(break)");
		break;

	case NK_ReturnStatement:

		fprintf(ASTFile, "(ret ");
		DumpExpression(AsRet(stmt)->expr, pos + 5);
		fprintf(ASTFile, ")");
		break;

	case NK_CompoundStatement:
		{
			AstNode p = ((AstCompoundStatement)stmt)->stmts;

			fprintf(ASTFile, "{");
			while (p != NULL)
			{
				LeftAlign(ASTFile, pos + 2);
				DumpStatement((AstStatement)p, pos + 2);
				if (p->next != NULL)
					fprintf(ASTFile, "\n");
				p = p->next;
			}
			LeftAlign(ASTFile, pos);
			fprintf(ASTFile, "}");
			break;
		}

	default:
		assert(0);
	}
}