📄 cfunc.mod
字号:
be found */ ram_offset; /* offset from ram base address at which bit[0] of the required word can be found */ short base; /* variable to hold current base integer for comparison purposes. */ double double1, double2; /* holding variables for modf routine */ /** first obtain word_number from *address values **/ err = cm_address_to_decimal(address,address_size,&word_number); if ( FALSE == err ) { /** valid data was returned **/ /* obtain offset value from word_number, word_width & bit_number */ int1 = word_number * word_width + bit_number; double1 = int1 / 8.0; modf(double1, &double2); ram_offset = int1 - (double2 * 8.0); /* obtain ram_index value */ modf( int1/8.0, &double1); ram_index = double1; /* retrieve entire base_address ram integer... */ base = ram[ram_index]; /* for each offset, mask off the bits and determine values */ cm_mask_and_retrieve(base,ram_offset,out); } else { /** incorrect data returned...return UNKNOWN values **/ *out = UNKNOWN; }}/*==============================================================================FUNCTION cm_d_ram()AUTHORS 26 Jun 1991 Jeffrey P. MurrayMODIFICATIONS 30 Sep 1991 Jeffrey P. MurraySUMMARY This function implements the d_ram code model.INTERFACES FILE ROUTINE CALLED CMevt.c void *cm_event_alloc() void *cm_event_get_ptr()RETURNED VALUE Returns inputs and outputs via ARGS structure.GLOBAL VARIABLES NONENON-STANDARD FEATURES NONE==============================================================================*//*=== CM_D_RAM ROUTINE ===*//************************************************* The following is the model for the ** digital M x N random access memory for the ** ATESSE Version 2.0 system. ** ** Created 6/26/91 J.P.Murray *************************************************/void cm_d_ram(ARGS) { int i, /* generic loop counter index */ j, /* generic loop counter index */ ram_size, /* total number of words in ram */ num_of_ram_ints, /* actual number of "short" integer values necessary to store all of the ram_size integers */ address_size, /* total number of address lines */ select_size, /* total number of address lines */ select_value, /* decimal value compared with select inputs to confirm that the ram has indeed been activated */ word_width, /* width of each word in bits */ int_test, /* integer test variable */ address_changed, /* TRUE if address is different from that on the previous call...FALSE otherwise */ address_unknown; /* TRUE if currently-read address has at least one line which is an unknown value. */ short int *ram, /* storage words...note that the total ram data will be stored in the two-bytes-per-Digital_State_t...since we require 2 bits per ram bit (for ZERO, ONE & UNKNOWN), we will store 8 ram bits per Digital_State_t location */ *ram_old; /* previous values of storage words */ Digital_State_t *address, /* address line values */ *address_old, /* previous address line values */ *write_en, /* write_en value */ *write_en_old, /* previous write_en value */ *select, /* current selected state of ram... note that this is derived from all of the select lines into the ram */ *select_old, /* previous selected state of ram */ d_test, /* digital debugging variable */ out; /* current output bit */ /** retrieve device size values...& other parameters **/ address_size = PORT_SIZE(address); /* calculate ram word size from address size */ ram_size = 1; for (i=0; i<address_size; i++) { ram_size *= 2; } select_size = PORT_SIZE(select); select_value = PARAM(select_value); word_width = PORT_SIZE(data_in); num_of_ram_ints = ram_size * word_width / 8; /*** Setup required state variables ***/ if(INIT) { /* initial pass */ /* allocate storage */ address = address_old = (Digital_State_t *) cm_event_alloc(0,address_size * sizeof(Digital_State_t)); write_en = write_en_old = (Digital_State_t *) cm_event_alloc(1,sizeof(Digital_State_t)); select = select_old = (Digital_State_t *) cm_event_alloc(2,select_size * sizeof(Digital_State_t)); /* allocate storage for ram memory */ ram = ram_old = (short *) cm_event_alloc(3,num_of_ram_ints * sizeof(short)); /* declare load values */ for (i=0; i<word_width; i++) { LOAD(data_in[i]) = PARAM(data_load); } for (i=0; i<address_size; i++) { LOAD(address[i]) = PARAM(address_load); } LOAD(write_en) = PARAM(enable_load); for (i=0; i<select_size; i++) { LOAD(select[i]) = PARAM(select_load); } } else { /* Retrieve previous values */ /* retrieve storage for the outputs */ address = (Digital_State_t *) cm_event_get_ptr(0,0); address_old = (Digital_State_t *) cm_event_get_ptr(0,1); write_en = (Digital_State_t *) cm_event_get_ptr(1,0); write_en_old = (Digital_State_t *) cm_event_get_ptr(1,1); select = (Digital_State_t *) cm_event_get_ptr(2,0); select_old = (Digital_State_t *) cm_event_get_ptr(2,1); /* retrieve ram base addresses */ ram = (short *) cm_event_get_ptr(3,0); ram_old = (short *) cm_event_get_ptr(3,1); } /**** retrieve inputs ****/ *write_en = INPUT_STATE(write_en); address_changed = FALSE; address_unknown = FALSE; for (i=0; i<address_size; i++) { address[i] = INPUT_STATE(address[i]); if (UNKNOWN == address[i]) address_unknown = TRUE; if (address[i] != address_old[i]) address_changed = TRUE; } /** Determine whether we are selected or not... **/ /* retrieve the bit equivalents for the select lines */ *select = ONE; for (i=0; i<select_size; i++) { /* compare each bit in succession with the value of each of the select input lines. */ if ( (d_test = INPUT_STATE(select[i])) != (int_test = (select_value & 0x0001)) ) { *select = ZERO; } /* shift the values select_value bits for next compare... */ select_value = select_value>>1; } /******* Determine analysis type and output appropriate values *******/ if (0.0 == TIME) { /****** DC analysis...output w/o delays ******/ /** initialize ram to ic value **/ out = PARAM(ic); for (i=0; i<word_width; i++) { for (j=0; j<ram_size; j++) { cm_initialize_ram(out,word_width,i,j,ram); } } if ( (ONE==*select) && (ZERO==*write_en) ) { /* output STRONG initial conditions */ for (i=0; i<word_width; i++) { OUTPUT_STATE(data_out[i]) = PARAM(ic); OUTPUT_STRENGTH(data_out[i]) = STRONG; } } else { /* change output to high impedance */ for (i=0; i<word_width; i++) { OUTPUT_STATE(data_out[i]) = UNKNOWN; OUTPUT_STRENGTH(data_out[i]) = HI_IMPEDANCE; } } } else { /****** Transient Analysis ******/ /***** Find input that has changed... *****/ /**** Test select value for change ****/ if ( *select != *select_old ) { /* either selected or de-selected */ switch ( *select ) { case ONE: /** chip is selected **/ if ( ZERO == *write_en ) { /* need to retrieve new output */ for (i=0; i<word_width; i++) { /* for each output bit in the word, */ /* retrieve the state value. */ cm_get_ram_value(word_width,i,address,address_size,ram,&out); OUTPUT_STATE(data_out[i]) = out; OUTPUT_STRENGTH(data_out[i]) = STRONG; OUTPUT_DELAY(data_out[i]) = PARAM(read_delay); } } else { /* store word & output current value */ for (i=0; i<word_width; i++) { if (address_unknown) { /** entire ram goes unknown!!! **/ for (j=0; j<ram_size; j++) { cm_initialize_ram(UNKNOWN,word_width,i,j,ram); } } else { out = INPUT_STATE(data_in[i]); cm_store_ram_value(out,word_width,i,address, address_size,ram); } OUTPUT_STRENGTH(data_out[i]) = HI_IMPEDANCE; OUTPUT_DELAY(data_out[i]) = PARAM(read_delay); } } break; case UNKNOWN: case ZERO: /* output goes tristate unless already so... */ if ( ZERO == *write_en ) { /* output needs tristating */ for (i=0; i<word_width; i++) { OUTPUT_STRENGTH(data_out[i]) = HI_IMPEDANCE; OUTPUT_DELAY(data_out[i]) = PARAM(read_delay); } } else { /* output will not change */ for (i=0; i<word_width; i++) { OUTPUT_CHANGED(data_out[i]) = FALSE; } } break; } } else { /**** Either a change in write_en, a change in address or a change in data values must have occurred... all of these are treated similarly. ****/ switch ( *write_en ) { case ONE: if ( (ONE == *select) ) { /* need to output tristates & store current data word */ for (i=0; i<word_width; i++) { if (address_unknown) { /** entire ram goes unknown!!! **/ for (j=0; j<ram_size; j++) { cm_initialize_ram(UNKNOWN,word_width,i,j,ram); } } else { out = INPUT_STATE(data_in[i]); cm_store_ram_value(out,word_width,i,address, address_size,ram); } OUTPUT_STRENGTH(data_out[i]) = HI_IMPEDANCE; OUTPUT_DELAY(data_out[i]) = PARAM(read_delay); } } else { /* output will not change */ for (i=0; i<word_width; i++) { OUTPUT_CHANGED(data_out[i]) = FALSE; } } break; case UNKNOWN: case ZERO: /** output contents of current address if selected **/ if ( ONE == *select) { /* store word & output current value */ for (i=0; i<word_width; i++) { if (address_unknown) { /* output goes unknown */ OUTPUT_STATE(data_out[i]) = UNKNOWN; } else { /* for each output bit in the word, */ /* retrieve the state value. */ cm_get_ram_value(word_width,i,address, address_size,ram,&out); OUTPUT_STATE(data_out[i]) = out; } OUTPUT_STRENGTH(data_out[i]) = STRONG; OUTPUT_DELAY(data_out[i]) = PARAM(read_delay); } } else { /* output will not change */ for (i=0; i<word_width; i++) { OUTPUT_CHANGED(data_out[i]) = FALSE; } } break; } } }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -