Added builtin .min() and .max() pseudo functions to the assembler.
git-svn-id: svn://svn.cc65.org/cc65/trunk@4583 b7a2c559-68d2-44c3-8de9-860c34a00d81
This commit is contained in:
@@ -6,7 +6,7 @@
|
||||
/* */
|
||||
/* */
|
||||
/* */
|
||||
/* (C) 1998-2009, Ullrich von Bassewitz */
|
||||
/* (C) 1998-2010, Ullrich von Bassewitz */
|
||||
/* Roemerstrasse 52 */
|
||||
/* D-70794 Filderstadt */
|
||||
/* EMail: uz@cc65.org */
|
||||
@@ -535,6 +535,64 @@ static ExprNode* FuncMatch (void)
|
||||
|
||||
|
||||
|
||||
static ExprNode* FuncMax (void)
|
||||
/* Handle the .MAX function */
|
||||
{
|
||||
ExprNode* Left;
|
||||
ExprNode* Right;
|
||||
ExprNode* Expr;
|
||||
long LeftVal, RightVal;
|
||||
|
||||
/* Two arguments to the pseudo function */
|
||||
Left = Expression ();
|
||||
ConsumeComma ();
|
||||
Right = Expression ();
|
||||
|
||||
/* Check if we can evaluate the value immediately */
|
||||
if (IsEasyConst (Left, &LeftVal) && IsEasyConst (Right, &RightVal)) {
|
||||
FreeExpr (Left);
|
||||
FreeExpr (Right);
|
||||
Expr = GenLiteralExpr ((LeftVal > RightVal)? LeftVal : RightVal);
|
||||
} else {
|
||||
/* Make an expression node */
|
||||
Expr = NewExprNode (EXPR_MAX);
|
||||
Expr->Left = Left;
|
||||
Expr->Right = Right;
|
||||
}
|
||||
return Expr;
|
||||
}
|
||||
|
||||
|
||||
|
||||
static ExprNode* FuncMin (void)
|
||||
/* Handle the .MIN function */
|
||||
{
|
||||
ExprNode* Left;
|
||||
ExprNode* Right;
|
||||
ExprNode* Expr;
|
||||
long LeftVal, RightVal;
|
||||
|
||||
/* Two arguments to the pseudo function */
|
||||
Left = Expression ();
|
||||
ConsumeComma ();
|
||||
Right = Expression ();
|
||||
|
||||
/* Check if we can evaluate the value immediately */
|
||||
if (IsEasyConst (Left, &LeftVal) && IsEasyConst (Right, &RightVal)) {
|
||||
FreeExpr (Left);
|
||||
FreeExpr (Right);
|
||||
Expr = GenLiteralExpr ((LeftVal < RightVal)? LeftVal : RightVal);
|
||||
} else {
|
||||
/* Make an expression node */
|
||||
Expr = NewExprNode (EXPR_MIN);
|
||||
Expr->Left = Left;
|
||||
Expr->Right = Right;
|
||||
}
|
||||
return Expr;
|
||||
}
|
||||
|
||||
|
||||
|
||||
static ExprNode* FuncReferenced (void)
|
||||
/* Handle the .REFERENCED builtin function */
|
||||
{
|
||||
@@ -919,6 +977,14 @@ static ExprNode* Factor (void)
|
||||
N = Function (FuncMatch);
|
||||
break;
|
||||
|
||||
case TOK_MAX:
|
||||
N = Function (FuncMax);
|
||||
break;
|
||||
|
||||
case TOK_MIN:
|
||||
N = Function (FuncMin);
|
||||
break;
|
||||
|
||||
case TOK_REFERENCED:
|
||||
N = Function (FuncReferenced);
|
||||
break;
|
||||
|
||||
@@ -1862,8 +1862,10 @@ static CtrlDesc CtrlCmdTab [] = {
|
||||
{ ccNone, DoMacPack },
|
||||
{ ccNone, DoMacro },
|
||||
{ ccNone, DoUnexpected }, /* .MATCH */
|
||||
{ ccNone, DoUnexpected }, /* .MAX */
|
||||
{ ccNone, DoInvalid }, /* .MID */
|
||||
{ ccNone, DoNull },
|
||||
{ ccNone, DoUnexpected }, /* .MIN */
|
||||
{ ccNone, DoNull },
|
||||
{ ccNone, DoOrg },
|
||||
{ ccNone, DoOut },
|
||||
{ ccNone, DoP02 },
|
||||
|
||||
@@ -236,7 +236,9 @@ struct DotKeyword {
|
||||
{ ".MACPACK", TOK_MACPACK },
|
||||
{ ".MACRO", TOK_MACRO },
|
||||
{ ".MATCH", TOK_MATCH },
|
||||
{ ".MAX", TOK_MAX },
|
||||
{ ".MID", TOK_MID },
|
||||
{ ".MIN", TOK_MIN },
|
||||
{ ".MOD", TOK_MOD },
|
||||
{ ".NOT", TOK_BOOLNOT },
|
||||
{ ".NULL", TOK_NULL },
|
||||
|
||||
@@ -481,7 +481,7 @@ static void StudyBinaryExpr (ExprNode* Expr, ExprDesc* D)
|
||||
ED_Done (&Right);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
static void StudyLiteral (ExprNode* Expr, ExprDesc* D)
|
||||
/* Study a literal expression node */
|
||||
@@ -1002,6 +1002,34 @@ static void StudyBoolXor (ExprNode* Expr, ExprDesc* D)
|
||||
|
||||
|
||||
|
||||
static void StudyMax (ExprNode* Expr, ExprDesc* D)
|
||||
/* Study an MAX binary expression node */
|
||||
{
|
||||
/* Use helper function */
|
||||
StudyBinaryExpr (Expr, D);
|
||||
|
||||
/* If the result is valid, apply the operation */
|
||||
if (ED_IsValid (D)) {
|
||||
D->Val = (D->Val > D->Right)? D->Val : D->Right;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
static void StudyMin (ExprNode* Expr, ExprDesc* D)
|
||||
/* Study an MIN binary expression node */
|
||||
{
|
||||
/* Use helper function */
|
||||
StudyBinaryExpr (Expr, D);
|
||||
|
||||
/* If the result is valid, apply the operation */
|
||||
if (ED_IsValid (D)) {
|
||||
D->Val = (D->Val < D->Right)? D->Val : D->Right;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
static void StudyUnaryMinus (ExprNode* Expr, ExprDesc* D)
|
||||
/* Study an EXPR_UNARY_MINUS expression node */
|
||||
{
|
||||
@@ -1279,6 +1307,14 @@ static void StudyExprInternal (ExprNode* Expr, ExprDesc* D)
|
||||
StudyBoolXor (Expr, D);
|
||||
break;
|
||||
|
||||
case EXPR_MAX:
|
||||
StudyMax (Expr, D);
|
||||
break;
|
||||
|
||||
case EXPR_MIN:
|
||||
StudyMin (Expr, D);
|
||||
break;
|
||||
|
||||
case EXPR_UNARY_MINUS:
|
||||
StudyUnaryMinus (Expr, D);
|
||||
break;
|
||||
@@ -1368,7 +1404,7 @@ void StudyExpr (ExprNode* Expr, ExprDesc* D)
|
||||
*/
|
||||
if (D->AddrSize == ADDR_SIZE_DEFAULT && ED_IsConst (D)) {
|
||||
D->AddrSize = GetConstAddrSize (D->Val);
|
||||
}
|
||||
}
|
||||
|
||||
/* If the expression is valid, throw away the address size and recalculate
|
||||
* it using the data we have. This is more exact than the on-the-fly
|
||||
|
||||
@@ -206,7 +206,9 @@ typedef enum Token {
|
||||
TOK_MACPACK,
|
||||
TOK_MACRO,
|
||||
TOK_MATCH,
|
||||
TOK_MAX,
|
||||
TOK_MID,
|
||||
TOK_MIN,
|
||||
TOK_NULL,
|
||||
TOK_ORG,
|
||||
TOK_OUT,
|
||||
|
||||
Reference in New Issue
Block a user