/*---------------------------------------------------------------------------- * (function: hard_node_name) * This creates the unique node name for a hard block *--------------------------------------------------------------------------*/ char *hard_node_name(nnode_t * /*node*/, char *instance_name_prefix, char *hb_name, char *hb_inst) { char *return_node_name; /* create the unique name for this node */ return_node_name = make_full_ref_name(instance_name_prefix, hb_name, hb_inst, NULL, -1); unique_node_name_id ++; return return_node_name; }
/*--------------------------------------------------------------------------------------------- * (function: node_name) * This creates the unique node name *-------------------------------------------------------------------------------------------*/ char *node_name(nnode_t *node, char *instance_name_prefix) { char *return_node_name; /* create the unique name for this node */ return_node_name = make_full_ref_name(instance_name_prefix, NULL, NULL, node_name_based_on_op(node), unique_node_name_id); //oassert(unique_node_name_id != 199803); unique_node_name_id++; return return_node_name; }
/*--------------------------------------------------------------------------------------------- * (function: get_name_of_pins_with_prefix *-------------------------------------------------------------------------------------------*/ char_list_t *get_name_of_pins_with_prefix(ast_node_t *var_node, char *instance_name_prefix) { int i; char_list_t *return_list; /* get the list */ return_list = get_name_of_pins(var_node, instance_name_prefix); for (i = 0; i < return_list->num_strings; i++) { return_list->strings[i] = make_full_ref_name(instance_name_prefix, NULL, NULL, return_list->strings[i], -1); } return return_list; }
/*--------------------------------------------------------------------------------------------- * (function: get_name of_port_at_bit) * Assume module connections can be one of: Array entry, Concat, Signal, Array range reference *-------------------------------------------------------------------------------------------*/ char *get_name_of_var_declare_at_bit(ast_node_t *var_declare, int bit) { char *return_string; /* calculate the port details */ if (var_declare->children[1] == NULL) { oassert(bit == 0); return_string = make_full_ref_name(NULL, NULL, NULL, var_declare->children[0]->types.identifier, -1); } else if (var_declare->children[3] == NULL) { oassert(var_declare->children[2]->type == NUMBERS); return_string = make_full_ref_name(NULL, NULL, NULL, var_declare->children[0]->types.identifier, var_declare->children[2]->types.number.value+bit); } else if (var_declare->children[3] != NULL) { return_string = NULL; /* MEMORY output */ oassert(FALSE); } return return_string; }
/*--------------------------------------------------------------------------------------------- * (function: get_name_of_pins * Assume module connections can be one of: Array entry, Concat, Signal, Array range reference * Return a list of strings *-------------------------------------------------------------------------------------------*/ char_list_t *get_name_of_pins(ast_node_t *var_node, char *instance_name_prefix) { char **return_string = NULL; char_list_t *return_list = (char_list_t*)malloc(sizeof(char_list_t)); ast_node_t *rnode[3]; int i; int width = 0; if (var_node->type == ARRAY_REF) { width = 1; return_string = (char**)malloc(sizeof(char*)); rnode[1] = resolve_node(instance_name_prefix, var_node->children[1]); oassert(rnode[1]->type == NUMBERS); oassert(var_node->children[0]->type == IDENTIFIERS); return_string[0] = make_full_ref_name(NULL, NULL, NULL, var_node->children[0]->types.identifier, rnode[1]->types.number.value); } else if (var_node->type == RANGE_REF) { rnode[0] = resolve_node(instance_name_prefix, var_node->children[0]); rnode[1] = resolve_node(instance_name_prefix, var_node->children[1]); rnode[2] = resolve_node(instance_name_prefix, var_node->children[2]); oassert(rnode[1]->type == NUMBERS && rnode[2]->type == NUMBERS); width = abs(rnode[1]->types.number.value - rnode[2]->types.number.value) + 1; if (rnode[0]->type == IDENTIFIERS) { return_string = (char**)malloc(sizeof(char*)*width); for (i = 0; i < width; i++) return_string[i] = make_full_ref_name(NULL, NULL, NULL, rnode[0]->types.identifier, rnode[2]->types.number.value+i); } else { oassert(rnode[0]->type == NUMBERS); return_string = get_name_of_pins_number(rnode[0], rnode[2]->types.number.value, width); } } else if (var_node->type == IDENTIFIERS) { /* need to look in the symbol table for details about this identifier (i.e. is it a port) */ long sc_spot; ast_node_t *sym_node; // try and resolve var_node sym_node = resolve_node(instance_name_prefix, var_node); if (sym_node == var_node) { char *temp_string = make_full_ref_name(NULL, NULL, NULL, var_node->types.identifier, -1); if ((sc_spot = sc_lookup_string(local_symbol_table_sc, temp_string)) == -1) { error_message(NETLIST_ERROR, var_node->line_number, var_node->file_number, "Missing declaration of this symbol %s\n", temp_string); } free(temp_string); sym_node = (ast_node_t*)local_symbol_table_sc->data[sc_spot]; if (sym_node->children[1] == NULL) { width = 1; return_string = (char**)malloc(sizeof(char*)*width); return_string[0] = make_full_ref_name(NULL, NULL, NULL, var_node->types.identifier, -1); } else if (sym_node->children[3] == NULL) { int index = 0; rnode[1] = resolve_node(instance_name_prefix, sym_node->children[1]); rnode[2] = resolve_node(instance_name_prefix, sym_node->children[2]); oassert(rnode[1]->type == NUMBERS && rnode[2]->type == NUMBERS); width = (rnode[1]->types.number.value - rnode[2]->types.number.value + 1); return_string = (char**)malloc(sizeof(char*)*width); for (i = 0; i < width; i++) { return_string[index] = make_full_ref_name(NULL, NULL, NULL, var_node->types.identifier, i+rnode[2]->types.number.value); index++; } } else if (sym_node->children[3] != NULL) { oassert(FALSE); } else { } } else { oassert(sym_node->type == NUMBERS); width = sym_node->types.number.binary_size; return_string = get_name_of_pins_number(sym_node, 0, width); } } else if (var_node->type == NUMBERS) { width = var_node->types.number.binary_size; return_string = get_name_of_pins_number(var_node, 0, width); } else if (var_node->type == CONCATENATE) { if (var_node->types.concat.num_bit_strings == 0) { oassert(FALSE); } else { if (var_node->types.concat.num_bit_strings == -1) { /* If this hasn't been made into a string list then do it */ make_concat_into_list_of_strings(var_node, instance_name_prefix); } width = var_node->types.concat.num_bit_strings; return_string = (char**)malloc(sizeof(char*)*width); for (i = 0; i < width; i++) // 0th bit is MSB so need to access reverse { return_string[i] = (char*)malloc(sizeof(char)*strlen(var_node->types.concat.bit_strings[var_node->types.concat.num_bit_strings-i-1])+1); sprintf(return_string[i], "%s", var_node->types.concat.bit_strings[var_node->types.concat.num_bit_strings-i-1]); } } } else { oassert(FALSE); } return_list->strings = return_string; return_list->num_strings = width; return return_list; }
/*--------------------------------------------------------------------------------------------- * (function: get_name of_port_at_bit) * Assume module connections can be one of: Array entry, Concat, Signal, Array range reference *-------------------------------------------------------------------------------------------*/ char *get_name_of_pin_at_bit(ast_node_t *var_node, int bit, char *instance_name_prefix) { char *return_string; ast_node_t *rnode[3]; if (var_node->type == ARRAY_REF) { oassert(var_node->children[0]->type == IDENTIFIERS); oassert(var_node->children[1]->type == NUMBERS); return_string = make_full_ref_name(NULL, NULL, NULL, var_node->children[0]->types.identifier, (int)var_node->children[1]->types.number.value); } else if (var_node->type == RANGE_REF) { rnode[1] = resolve_node(instance_name_prefix, var_node->children[1]); rnode[2] = resolve_node(instance_name_prefix, var_node->children[2]); oassert(var_node->children[0]->type == IDENTIFIERS); oassert(rnode[1]->type == NUMBERS && rnode[2]->type == NUMBERS); oassert((rnode[1]->types.number.value >= rnode[2]->types.number.value+bit) && bit >= 0); return_string = make_full_ref_name(NULL, NULL, NULL, var_node->children[0]->types.identifier, rnode[2]->types.number.value+bit); } else if ((var_node->type == IDENTIFIERS) && (bit == -1)) { return_string = make_full_ref_name(NULL, NULL, NULL, var_node->types.identifier, -1); } else if (var_node->type == IDENTIFIERS) { long sc_spot; int pin_index; if ((sc_spot = sc_lookup_string(local_symbol_table_sc, var_node->types.identifier)) == -1) { pin_index = 0; error_message(NETLIST_ERROR, var_node->line_number, var_node->file_number, "Missing declaration of this symbol %s\n", var_node->types.identifier); } if (((ast_node_t*)local_symbol_table_sc->data[sc_spot])->children[1] == NULL) { pin_index = bit; } else if (((ast_node_t*)local_symbol_table_sc->data[sc_spot])->children[3] == NULL) { oassert(((ast_node_t*)local_symbol_table_sc->data[sc_spot])->children[2]->type == NUMBERS); pin_index = ((ast_node_t*)local_symbol_table_sc->data[sc_spot])->children[2]->types.number.value + bit; } else oassert(FALSE); return_string = make_full_ref_name(NULL, NULL, NULL, var_node->types.identifier, pin_index); } else if (var_node->type == NUMBERS) { if (bit == -1) bit = 0; oassert(bit < var_node->types.number.binary_size); if (var_node->types.number.binary_string[var_node->types.number.binary_size-bit-1] == '1') { return_string = (char*)malloc(sizeof(char)*11+1); // ONE_VCC_CNS sprintf(return_string, "ONE_VCC_CNS"); } else if (var_node->types.number.binary_string[var_node->types.number.binary_size-bit-1] == '0') { return_string = (char*)malloc(sizeof(char)*13+1); // ZERO_GND_ZERO sprintf(return_string, "ZERO_GND_ZERO"); } else { return_string = NULL; oassert(FALSE); } } else if (var_node->type == CONCATENATE) { if (var_node->types.concat.num_bit_strings == 0) { return_string = NULL; oassert(FALSE); } else { if (var_node->types.concat.num_bit_strings == -1) { /* If this hasn't been made into a string list then do it */ make_concat_into_list_of_strings(var_node, instance_name_prefix); } return_string = (char*)malloc(sizeof(char)*strlen(var_node->types.concat.bit_strings[bit])+1); sprintf(return_string, "%s", var_node->types.concat.bit_strings[bit]); } } else { return_string = NULL; error_message(NETLIST_ERROR, var_node->line_number, var_node->file_number, "Unsupported variable type.\n"); oassert(FALSE); } return return_string; }
/*--------------------------------------------------------------------------------------------- * (function: make_concat_into_list_of_strings) * 0th idx will be the MSbit *-------------------------------------------------------------------------------------------*/ void make_concat_into_list_of_strings(ast_node_t *concat_top, char *instance_name_prefix) { int i, j; ast_node_t *rnode[3]; concat_top->types.concat.num_bit_strings = 0; concat_top->types.concat.bit_strings = NULL; /* recursively do all embedded concats */ for (i = 0; i < concat_top->num_children; i++) { if (concat_top->children[i]->type == CONCATENATE) { make_concat_into_list_of_strings(concat_top->children[i], instance_name_prefix); } } for (i = 0; i < concat_top->num_children; i++) { if (concat_top->children[i]->type == IDENTIFIERS) { char *temp_string = make_full_ref_name(NULL, NULL, NULL, concat_top->children[i]->types.identifier, -1); long sc_spot; if ((sc_spot = sc_lookup_string(local_symbol_table_sc, temp_string)) == -1) { error_message(NETLIST_ERROR, concat_top->line_number, concat_top->file_number, "Missing declaration of this symbol %s\n", temp_string); } free(temp_string); if (((ast_node_t*)local_symbol_table_sc->data[sc_spot])->children[1] == NULL) { concat_top->types.concat.num_bit_strings ++; concat_top->types.concat.bit_strings = (char**)realloc(concat_top->types.concat.bit_strings, sizeof(char*)*(concat_top->types.concat.num_bit_strings)); concat_top->types.concat.bit_strings[concat_top->types.concat.num_bit_strings-1] = get_name_of_pin_at_bit(concat_top->children[i], -1, instance_name_prefix); } else if (((ast_node_t*)local_symbol_table_sc->data[sc_spot])->children[3] == NULL) { /* reverse thorugh the range since highest bit in index will be lower in the string indx */ rnode[1] = resolve_node(instance_name_prefix, ((ast_node_t*)local_symbol_table_sc->data[sc_spot])->children[1]); rnode[2] = resolve_node(instance_name_prefix, ((ast_node_t*)local_symbol_table_sc->data[sc_spot])->children[2]); oassert(rnode[1]->type == NUMBERS && rnode[2]->type == NUMBERS); for (j = rnode[1]->types.number.value - rnode[2]->types.number.value; j >= 0; j--) { concat_top->types.concat.num_bit_strings ++; concat_top->types.concat.bit_strings = (char**)realloc(concat_top->types.concat.bit_strings, sizeof(char*)*(concat_top->types.concat.num_bit_strings)); concat_top->types.concat.bit_strings[concat_top->types.concat.num_bit_strings-1] = get_name_of_pin_at_bit(concat_top->children[i], j, instance_name_prefix); } } else if (((ast_node_t*)local_symbol_table_sc->data[sc_spot])->children[3] != NULL) { oassert(FALSE); } } else if (concat_top->children[i]->type == ARRAY_REF) { concat_top->types.concat.num_bit_strings ++; concat_top->types.concat.bit_strings = (char**)realloc(concat_top->types.concat.bit_strings, sizeof(char*)*(concat_top->types.concat.num_bit_strings)); concat_top->types.concat.bit_strings[concat_top->types.concat.num_bit_strings-1] = get_name_of_pin_at_bit(concat_top->children[i], 0, instance_name_prefix); } else if (concat_top->children[i]->type == RANGE_REF) { rnode[1] = resolve_node(instance_name_prefix, concat_top->children[i]->children[1]); rnode[2] = resolve_node(instance_name_prefix, concat_top->children[i]->children[2]); oassert(rnode[1]->type == NUMBERS && rnode[2]->type == NUMBERS); oassert(rnode[1]->types.number.value >= rnode[2]->types.number.value); int width = abs(rnode[1]->types.number.value - rnode[2]->types.number.value) + 1; //for (j = rnode[1]->types.number.value - rnode[2]->types.number.value; j >= 0; j--) // Changed to forward to fix concatenation bug. for (j = 0; j < width; j++) { concat_top->types.concat.num_bit_strings ++; concat_top->types.concat.bit_strings = (char**)realloc(concat_top->types.concat.bit_strings, sizeof(char*)*(concat_top->types.concat.num_bit_strings)); concat_top->types.concat.bit_strings[concat_top->types.concat.num_bit_strings-1] = get_name_of_pin_at_bit(concat_top->children[i], ((rnode[1]->types.number.value - rnode[2]->types.number.value))-j, instance_name_prefix); } } else if (concat_top->children[i]->type == NUMBERS) { if(concat_top->children[i]->types.number.base == DEC) { error_message(NETLIST_ERROR, concat_top->line_number, concat_top->file_number, "Concatenation can't include decimal numbers due to conflict on bits\n"); } // Changed to reverse to fix concatenation bug. for (j = concat_top->children[i]->types.number.binary_size-1; j>= 0; j--) { concat_top->types.concat.num_bit_strings ++; concat_top->types.concat.bit_strings = (char**)realloc(concat_top->types.concat.bit_strings, sizeof(char*)*(concat_top->types.concat.num_bit_strings)); concat_top->types.concat.bit_strings[concat_top->types.concat.num_bit_strings-1] = get_name_of_pin_at_bit(concat_top->children[i], j, instance_name_prefix); } } else if (concat_top->children[i]->type == CONCATENATE) { /* forward through list since we build concatenate list in idx order of MSB at index 0 and LSB at index list_size */ for (j = 0; j < concat_top->children[i]->types.concat.num_bit_strings; j++) { concat_top->types.concat.num_bit_strings ++; concat_top->types.concat.bit_strings = (char**)realloc(concat_top->types.concat.bit_strings, sizeof(char*)*(concat_top->types.concat.num_bit_strings)); concat_top->types.concat.bit_strings[concat_top->types.concat.num_bit_strings-1] = get_name_of_pin_at_bit(concat_top->children[i], j, instance_name_prefix); } } else { error_message(NETLIST_ERROR, concat_top->line_number, concat_top->file_number, "Unsupported operation within a concatenation.\n"); } } }