static.h File Reference


Detailed Description

Contains functions for handling creation of static expressions.

Author:
Trevor Williams (phase1geo@gmail.com)
Date:
10/02/2002

#include "defines.h"

Go to the source code of this file.

Functions

static_exprstatic_expr_gen_unary (static_expr *stexp, int op, int line, int first, int last)
 Calculates new values for unary static expressions and returns the new static expression.
static_exprstatic_expr_gen (static_expr *right, static_expr *left, int op, int line, int first, int last, char *func_name)
 Calculates new values for static expression and returns the new static expression.
void static_expr_calc_lsb_and_width_pre (static_expr *left, static_expr *right, int *width, int *lsb, int *big_endian)
 Calculates LSB, width and endianness for specified left/right pair for vector (used before parameter resolve).
void static_expr_calc_lsb_and_width_post (static_expr *left, static_expr *right, int *width, int *lsb, int *big_endian)
 Calculates LSB, width and endianness for specified left/right pair for vector (used after parameter resolve).
void static_expr_dealloc (static_expr *stexp, bool rm_exp)
 Deallocates static_expr memory from heap.


Function Documentation

void static_expr_calc_lsb_and_width_post ( static_expr left,
static_expr right,
int *  width,
int *  lsb,
int *  big_endian 
)

Calculates LSB, width and endianness for specified left/right pair for vector (used after parameter resolve).

Parameters:
left Pointer to static expression on left of vector.
right Pointer to static expression on right of vector.
width Calculated width of combined right/left static expressions.
lsb Calculated lsb of combined right/left static expressions.
big_endian Set to 1 if the left expression is less than the right expression.
Calculates the LSB and width of a vector defined by the specified left and right static expressions. This function assumes that any expressions have been calculated for a legal value.
00354                                                                                                                          { PROFILE(STATIC_EXPR_CALC_LSB_AND_WIDTH_POST);
00355   
00356   assert( left  != NULL );
00357   assert( right != NULL );
00358 
00359   *width      = 1;
00360   *lsb        = -1;
00361   *big_endian = 0;
00362 
00363   /* If the right static expression contains an expression, get its integer value and place it in the num field */
00364   if( right->exp != NULL ) {
00365     right->num = vector_to_int( right->exp->value );
00366   }
00367 
00368   /* If the left static expression contains an expression, get its integer value and place it in the num field */
00369   if( left->exp != NULL ) {
00370     left->num = vector_to_int( left->exp->value );
00371     // expression_display( left->exp );
00372   }
00373   
00374   /* Get initial value for LSB */
00375   *lsb = right->num;
00376   assert( *lsb >= 0 );
00377 
00378   /* Calculate width and make sure that LSB is the lower of the two values */
00379   if( *lsb <= left->num ) {
00380     *width = (left->num - *lsb) + 1;
00381     assert( *width > 0 );
00382   } else {
00383     *width      = (*lsb - left->num) + 1;
00384     *lsb        = left->num;
00385     *big_endian = 1;
00386     assert( *width > 0 );
00387     assert( *lsb >= 0 );
00388   }
00389 
00390 }

void static_expr_calc_lsb_and_width_pre ( static_expr left,
static_expr right,
int *  width,
int *  lsb,
int *  big_endian 
)

Calculates LSB, width and endianness for specified left/right pair for vector (used before parameter resolve).

Parameters:
left Pointer to static expression on left of vector.
right Pointer to static expression on right of vector.
width Calculated width of combined right/left static expressions.
lsb Calculated lsb of combined right/left static expressions.
big_endian Set to 1 if the MSB/LSB is specified in big endian order.
Calculates the LSB, width and endianness of a vector defined by the specified left and right static expressions. If the width cannot be obtained immediately (parameter in static expression), set width to -1. If the LSB cannot be obtained immediately (parameter in static expression), set LSB to -1. The endianness can only be used if the width is known. The returned width and lsb parameters can be used to size a vector instantiation.
00312                                                                                                                         { PROFILE(STATIC_EXPR_CALC_LSB_AND_WIDTH_PRE);
00313 
00314   *width      = -1;
00315   *lsb        = -1;
00316   *big_endian = 0;
00317 
00318   if( (right != NULL) && (right->exp == NULL) ) {
00319     *lsb = right->num;
00320     assert( *lsb >= 0 );
00321   }
00322 
00323   if( (left != NULL) && (left->exp == NULL) ) {
00324     if( *lsb != -1 ) {
00325       if( *lsb <= left->num ) {
00326         *width = (left->num - *lsb) + 1;
00327         assert( *width > 0 );
00328       } else {
00329         *width      = (*lsb - left->num) + 1;
00330         *lsb        = left->num;
00331         *big_endian = 1;
00332         assert( *width > 0 );
00333         assert( *lsb >= 0 );
00334       }
00335     } else {
00336       *lsb = left->num;
00337       assert( *lsb >= 0 );
00338     }
00339   }
00340 
00341 }

void static_expr_dealloc ( static_expr stexp,
bool  rm_exp 
)

Deallocates static_expr memory from heap.

Parameters:
stexp Pointer to static expression to deallocate.
rm_exp Specifies that expression tree should be deallocated.
Deallocates all allocated memory from the heap for the specified static_expr structure.
00399                                                             { PROFILE(STATIC_EXPR_DEALLOC);
00400 
00401   if( stexp != NULL ) {
00402 
00403     if( rm_exp && (stexp->exp != NULL) ) {
00404       expression_dealloc( stexp->exp, FALSE );
00405     }
00406 
00407     free_safe( stexp );
00408 
00409   }
00410 
00411 }

static_expr* static_expr_gen ( static_expr right,
static_expr left,
int  op,
int  line,
int  first,
int  last,
char *  func_name 
)

Calculates new values for static expression and returns the new static expression.

Parameters:
right Pointer to right static expression.
left Pointer to left static expression.
op Static expression operation.
line Line number that static expression operation found on.
first Column index of first character in expression.
last Column index of last character in expression.
func_name Name of function to call (only valid when op == EXP_OP_FUNC_CALL)
Returns:
Returns pointer to new static_expr structure.
Used by the parser to calculate a new static_expr structure based on the operation encountered while parsing. Based on the operation type specified in the argument list, performs unary operation (if both operands are static numbers, storing result into original static_expr number field and returns If only one of the operands is an expression, create a EXP_OP_STATIC expression for the other operand and create an expression consisting of these two expressions and the specified operation. If both operands are expressions, simply create a new expression consisting of those two expressions and specified operator. Store the newly create expression in the original right static_expr and deallocate the left static_expr.
00189                                                                                                                               { PROFILE(STATIC_EXPR_GEN);
00190 
00191   expression* tmpexp;     /* Temporary expression for holding newly created parent expression */
00192   int         i;          /* Loop iterator */
00193   int         value = 1;  /* Temporary value */
00194   
00195   assert( (op == EXP_OP_XOR)    || (op == EXP_OP_MULTIPLY) || (op == EXP_OP_DIVIDE) || (op == EXP_OP_MOD)       ||
00196           (op == EXP_OP_ADD)    || (op == EXP_OP_SUBTRACT) || (op == EXP_OP_AND)    || (op == EXP_OP_OR)        ||
00197           (op == EXP_OP_NOR)    || (op == EXP_OP_NAND)     || (op == EXP_OP_NXOR)   || (op == EXP_OP_EXPONENT)  ||
00198           (op == EXP_OP_LSHIFT) || (op == EXP_OP_RSHIFT)   || (op == EXP_OP_LIST)   || (op == EXP_OP_FUNC_CALL) ||
00199           (op == EXP_OP_GE)     || (op == EXP_OP_LE)       || (op == EXP_OP_EQ)     || (op == EXP_OP_GT)        ||
00200           (op == EXP_OP_LT)     || (op == EXP_OP_SBIT_SEL) );
00201 
00202   if( (right != NULL) && (left != NULL) ) {
00203 
00204     if( right->exp == NULL ) {
00205 
00206       if( left->exp == NULL ) {
00207 
00208         switch( op ) {
00209           case EXP_OP_XOR      :  right->num = left->num ^ right->num;     break;
00210           case EXP_OP_MULTIPLY :  right->num = left->num * right->num;     break;
00211           case EXP_OP_DIVIDE   :  right->num = left->num / right->num;     break;
00212           case EXP_OP_MOD      :  right->num = left->num % right->num;     break;
00213           case EXP_OP_ADD      :  right->num = left->num + right->num;     break;
00214           case EXP_OP_SUBTRACT :  right->num = left->num - right->num;     break;
00215           case EXP_OP_EXPONENT :
00216             for( i=0; i<right->num; i++ ) {
00217               value *= left->num;
00218             }
00219             right->num = value;
00220             break;
00221           case EXP_OP_AND      :  right->num = left->num & right->num;     break;
00222           case EXP_OP_OR       :  right->num = left->num | right->num;     break;
00223           case EXP_OP_NOR      :  right->num = ~(left->num | right->num);  break;
00224           case EXP_OP_NAND     :  right->num = ~(left->num & right->num);  break;
00225           case EXP_OP_NXOR     :  right->num = ~(left->num ^ right->num);  break;
00226           /*@-shiftnegative -shiftimplementation@*/
00227           case EXP_OP_LSHIFT   :  right->num = left->num << right->num;    break;
00228           case EXP_OP_RSHIFT   :  right->num = left->num >> right->num;    break;
00229           /*@=shiftnegative =shiftimplementation@*/
00230           case EXP_OP_GE       :  right->num = (left->num >= right->num) ? 1 : 0;  break;
00231           case EXP_OP_LE       :  right->num = (left->num <= right->num) ? 1 : 0;  break;
00232           case EXP_OP_EQ       :  right->num = (left->num == right->num) ? 1 : 0;  break;
00233           case EXP_OP_GT       :  right->num = (left->num > right->num)  ? 1 : 0;  break;
00234           case EXP_OP_LT       :  right->num = (left->num < right->num)  ? 1 : 0;  break;
00235           default              :  break;
00236         }
00237 
00238       } else {
00239 
00240         right->exp = expression_create( NULL, NULL, EXP_OP_STATIC, FALSE, curr_expr_id, line, first, last, FALSE );
00241         curr_expr_id++;
00242         vector_init( right->exp->value, (vec_data*)malloc_safe( sizeof( vec_data ) * 32 ), TRUE, 32, VTYPE_EXP );  
00243         vector_from_int( right->exp->value, right->num );
00244 
00245         tmpexp = expression_create( right->exp, left->exp, op, FALSE, curr_expr_id, line, first, last, FALSE );
00246         curr_expr_id++;
00247         right->exp = tmpexp;
00248         
00249       }
00250 
00251     } else {
00252 
00253       if( left->exp == NULL ) {
00254 
00255         left->exp = expression_create( NULL, NULL, EXP_OP_STATIC, FALSE, curr_expr_id, line, first, last, FALSE );
00256         curr_expr_id++;
00257         vector_init( left->exp->value, (vec_data*)malloc_safe( sizeof( vec_data ) * 32 ), TRUE, 32, VTYPE_EXP );
00258         vector_from_int( left->exp->value, left->num );
00259 
00260         tmpexp = expression_create( right->exp, left->exp, op, FALSE, curr_expr_id, line, first, last, FALSE );
00261         curr_expr_id++;
00262         right->exp = tmpexp;
00263 
00264       } else {
00265 
00266         tmpexp = expression_create( right->exp, left->exp, op, FALSE, curr_expr_id, line, first, last, FALSE );
00267         curr_expr_id++;
00268         right->exp = tmpexp;
00269 
00270       }
00271 
00272     }
00273 
00274   } else if( (op == EXP_OP_FUNC_CALL) || (op == EXP_OP_SBIT_SEL) ) {
00275 
00276     /*
00277      If this is a function call or SBIT_SEL, only the left expression will be a valid expression (so we need to special
00278      handle this)
00279     */
00280 
00281     assert( right == NULL );
00282     assert( left  != NULL );
00283 
00284     right = (static_expr*)malloc_safe( sizeof( static_expr ) );
00285     right->exp = expression_create( NULL, left->exp, op, FALSE, curr_expr_id, line, first, last, FALSE );
00286     curr_expr_id++;
00287 
00288     /* Make sure that we bind this later */
00289     bind_add( FUNIT_FUNCTION, func_name, right->exp, curr_funit );
00290 
00291   }
00292 
00293   static_expr_dealloc( left, FALSE );
00294 
00295   return( right );
00296 
00297 }

static_expr* static_expr_gen_unary ( static_expr stexp,
int  op,
int  line,
int  first,
int  last 
)

Calculates new values for unary static expressions and returns the new static expression.

Parameters:
stexp Pointer to static expression.
op Unary static expression operation.
line Line number that this expression was found on in file.
first Column index of first character in this expression.
last Column index of last character in this expression.
Returns:
Returns pointer to new static_expr structure.
Used by the parser to calculate a new static_expr structure based on the unary operation encountered while parsing. Based on the operation type specified in the argument list, performs unary operation (if operand is a static number and not an expression -- parameter in operand expression tree), storing result into original static_expr number field and returns the original structure back to the calling function. If the operand is an expression, create an expression for the specified operation type and store this expression in the original expression pointer field.
00087                                                                                                 { PROFILE(STATIC_EXPR_GEN_UNARY);
00088 
00089   expression*  tmpexp;  /* Container for newly created expression */
00090   int          uop;     /* Temporary bit holder */
00091   unsigned int i;       /* Loop iterator */
00092 
00093   if( stexp != NULL ) {
00094 
00095     assert( (op == EXP_OP_UINV)  || (op == EXP_OP_UAND) || (op == EXP_OP_UOR)   || (op == EXP_OP_UXOR)  ||
00096             (op == EXP_OP_UNAND) || (op == EXP_OP_UNOR) || (op == EXP_OP_UNXOR) || (op == EXP_OP_UNOT)  ||
00097             (op == EXP_OP_PASSIGN) );
00098 
00099     if( stexp->exp == NULL ) {
00100 
00101       switch( op ) {
00102 
00103         case EXP_OP_UINV :
00104           stexp->num = ~stexp->num;
00105           break;
00106 
00107         case EXP_OP_UAND  :
00108         case EXP_OP_UOR   :
00109         case EXP_OP_UXOR  :
00110         case EXP_OP_UNAND :
00111         case EXP_OP_UNOR  :
00112         case EXP_OP_UNXOR :
00113           uop = stexp->num & 0x1;
00114           for( i=1; i<(SIZEOF_INT * 8); i++ ) {
00115             switch( op ) {
00116               case EXP_OP_UNAND :
00117               /*@-shiftimplementation@*/
00118               case EXP_OP_UAND  :  uop = uop & ((stexp->num >> i) & 0x1);  break;
00119               case EXP_OP_UNOR  :
00120               case EXP_OP_UOR   :  uop = uop | ((stexp->num >> i) & 0x1);  break;
00121               case EXP_OP_UNXOR :
00122               case EXP_OP_UXOR  :  uop = uop ^ ((stexp->num >> i) & 0x1);  break;
00123               /*@=shiftimplementation@*/
00124               default           :  break;
00125             }
00126           }
00127           switch( op ) {
00128             case EXP_OP_UAND  :
00129             case EXP_OP_UOR   :
00130             case EXP_OP_UXOR  :  stexp->num = uop;                 break;
00131             case EXP_OP_UNAND :
00132             case EXP_OP_UNOR  :
00133             case EXP_OP_UNXOR :  stexp->num = (uop == 0) ? 1 : 0;  break;
00134             default           :  break;
00135           }
00136           break;
00137 
00138         case EXP_OP_UNOT :
00139           stexp->num = (stexp->num == 0) ? 1 : 0;
00140           break;
00141 
00142         case EXP_OP_PASSIGN :
00143           tmpexp = expression_create( NULL, NULL, EXP_OP_STATIC, FALSE, curr_expr_id, line, first, last, FALSE );
00144           curr_expr_id++;
00145           vector_init( tmpexp->value, (vec_data*)malloc_safe( sizeof( vec_data ) * 32 ), TRUE, 32, VTYPE_EXP );
00146           vector_from_int( tmpexp->value, stexp->num );
00147         
00148           stexp->exp = expression_create( tmpexp, NULL, op, FALSE, curr_expr_id, line, first, last, FALSE );
00149           curr_expr_id++;
00150           break;
00151         default :  break;
00152       }
00153 
00154     } else {
00155 
00156       tmpexp = expression_create( stexp->exp, NULL, op, FALSE, curr_expr_id, line, first, last, FALSE );
00157       curr_expr_id++;
00158       stexp->exp = tmpexp;
00159 
00160     }
00161 
00162   }
00163 
00164   return( stexp );
00165 
00166 }


Generated on Wed Jan 30 22:43:51 2008 for Covered by  doxygen 1.5.4