Initial import of gattrib 20040806
[geda-gaf/whiteaudio.git] / gattrib / src / s_sheet_data.c
blobc8237c1e03f2e3952d88747bfda8299062621d87
1 /* gEDA - GPL Electronic Design Automation
2 * gattrib -- gEDA component and net attribute manipulation using spreadsheet.
3 * Copyright (C) 2003 Stuart D. Brorson.
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111 USA
20 /*------------------------------------------------------------------
21 * This file holds fcns involved in manipulating an entire SHEET_DATA
22 * structure. The SHEET_DATA structure is the intermediate structure
23 * between TOPLEVEL (gEDA's native format) and the graphical gtksheet
24 * widget (from gtkextra), which is the spreadsheet widget displaying
25 * the attribs.
26 *------------------------------------------------------------------*/
28 #include <config.h>
30 #include <stdio.h>
31 #ifdef HAVE_STRING_H
32 #include <string.h>
33 #endif
34 #include <math.h>
36 /*------------------------------------------------------------------
37 * Gattrib specific includes
38 *------------------------------------------------------------------*/
39 #include <libgeda/libgeda.h> /* geda library fcns */
40 #include "../include/struct.h" /* typdef and struct declarations */
41 #include "../include/prototype.h" /* function prototypes */
42 #include "../include/globals.h"
45 /*------------------------------------------------------------------
46 * This fcn is the sheet_data creator. It returns a pointer to
47 * an initialized SHEET_DATA struct.
48 *------------------------------------------------------------------*/
49 SHEET_DATA *s_sheet_data_new()
51 SHEET_DATA *new_sheet;
53 new_sheet = (SHEET_DATA *) malloc(sizeof(SHEET_DATA));
55 /* We will malloc and fill out the comp table later. */
56 new_sheet->component_table = NULL;
58 /* We will malloc and fill out the net table later. */
59 new_sheet->net_table = NULL;
61 /* We will malloc and fill out the pin table later. */
62 new_sheet->pin_table = NULL;
64 /* Now we create the first cell in each master list. */
65 new_sheet->master_comp_list_head = (STRING_LIST *) s_string_list_new();
66 new_sheet->master_comp_attrib_list_head = (STRING_LIST *) s_string_list_new();
67 new_sheet->comp_count = 0;
68 new_sheet->comp_attrib_count = 0;
70 new_sheet->master_net_list_head = (STRING_LIST *) s_string_list_new();
71 new_sheet->master_net_attrib_list_head = (STRING_LIST *) s_string_list_new();
72 new_sheet->net_count = 0;
73 new_sheet->net_attrib_count = 0;
75 new_sheet->master_pin_list_head = (STRING_LIST *) s_string_list_new();
76 new_sheet->master_pin_attrib_list_head = (STRING_LIST *) s_string_list_new();
77 new_sheet->pin_count = 0;
78 new_sheet->pin_attrib_count = 0;
80 return (new_sheet);
86 /*------------------------------------------------------------------
87 * This fcn adds to the master list of components refdeses by running
88 * through the components and recording the comp refdeses
89 * it discovers. Then it sorts them into alphabetical order.
90 * Data struct being searched is: OBJECT->attribs(->next. . .)->object->text->string
91 *------------------------------------------------------------------*/
92 void s_sheet_data_add_master_comp_list_items(OBJECT *start_obj) {
93 char *temp_uref;
94 OBJECT *o_current;
95 OBJECT *temp_object;
97 #ifdef DEBUG
98 fflush(stderr);
99 fflush(stdout);
100 printf("=========== Just entered s_sheet_data_add_master_comp_list_items! ==============\n");
101 #endif
103 if (verbose_mode) {
104 printf("- Starting master comp list creation.\n");
107 /* ----- Iterate through all objects found on page looking for components ----- */
108 o_current = start_obj;
109 while (o_current != NULL) {
111 #ifdef DEBUG
112 printf("In s_sheet_data_add_master_comp_list_items, examining o_current->name = %s\n", o_current->name);
113 #endif
115 /*----- only process if this is a non-graphical comp with attributes ----*/
116 if ( (o_current->type == OBJ_COMPLEX) &&
117 o_current->attribs &&
118 !o_attrib_search_component(o_current, "graphical") ) {
120 #if DEBUG
121 fflush(stderr);
122 fflush(stdout);
123 printf(" In s_sheet_data_add_master_comp_list_items; found component on page\n");
124 fprintf(stderr, ". . . . complex_basename = %s.\n", o_current->complex_basename);
125 #endif
126 verbose_print(" C");
128 /*------ Try to get the refdes -----*/
129 temp_uref = o_attrib_search_name_single(o_current, "refdes", NULL);
130 if (!temp_uref) {
131 temp_uref = o_attrib_search_name_single(o_current, "uref", NULL); // deprecated
132 if (temp_uref) {
133 printf("WARNING: Found uref=%s, uref= is deprecated, please use refdes=\n", temp_uref);
134 } else { /* didn't find refdes. Report error to log. */
135 fprintf(stderr, " In s_sheet_data_add_master_comp_list_items, found non-graphical component with no refdes.\n");
136 #ifdef DEBUG
137 fprintf(stderr, ". . . . complex_basename = %s.\n", o_current->complex_basename);
138 #endif
140 } /*--- if(!temp_uref) ---*/
143 /* Now that we have refdes, store refdes and attach attrib list to component */
144 if (temp_uref) {
145 #if DEBUG
146 fflush(stderr);
147 fflush(stdout);
148 printf(" In s_sheet_add_master_comp_list, about to add to master list refdes = %s\n", temp_uref);
149 #endif
150 s_string_list_add_item(sheet_head->master_comp_list_head, &(sheet_head->comp_count), temp_uref);
151 free(temp_uref);
154 } /* if (o_current->type == OBJ_COMPLEX . . . . .) */
156 o_current = o_current->next; /* iterate to next object on page */
157 } /* while o_current != NULL */
159 return;
163 /*------------------------------------------------------------------
164 * This fcn adds to the master list of comp attribs by running
165 * through each component on the page and recording all attribs
166 * it discovers. Then it sorts them into an order used for the
167 * horiz listing of the attribs on the spreadsheet.
168 * Data struct being searched is: sheet_head->component_list_head->attrib->name;
169 *------------------------------------------------------------------*/
170 void s_sheet_data_add_master_comp_attrib_list_items(OBJECT *start_obj) {
171 char *attrib_text;
172 char *attrib_name;
173 char *attrib_value;
174 char *temp_uref;
175 OBJECT *o_current;
176 OBJECT *temp_object;
177 ATTRIB *a_current;
179 #ifdef DEBUG
180 fflush(stderr);
181 fflush(stdout);
182 printf("=========== Just entered s_sheet_data_add_master_comp_attrib_list_items! ==============\n");
183 #endif
185 if (verbose_mode) {
186 printf("- Starting master comp attrib list creation.\n");
189 /* ----- Iterate through all objects found on page looking for components ----- */
190 o_current = start_obj;
191 while (o_current != NULL) {
193 #ifdef DEBUG
194 printf("In s_sheet_data_add_master_comp_attrib_list_items, examining o_current->name = %s\n", o_current->name);
195 #endif
197 /*----- only process if this is a non-graphical comp with attributes ----*/
198 if ( (o_current->type == OBJ_COMPLEX) &&
199 o_current->attribs &&
200 !o_attrib_search_component(o_current, "graphical") ) {
203 verbose_print(" C");
205 /*------ Iterate through all attribs found on component -----*/
206 a_current = o_current->attribs; /* This has a side effect. Why? */
207 while (a_current != NULL) {
208 if (a_current->object->type == OBJ_TEXT
209 && a_current->object->text != NULL) { /* found an attribute */
210 attrib_text = u_basic_strdup(a_current->object->text->string);
211 attrib_name = u_basic_breakup_string(attrib_text, '=', 0);
212 if (strcmp(attrib_name, "refdes") != 0) {
213 /* Don't include "refdes" because it is already in other master list */
214 #if DEBUG
215 temp_uref = o_attrib_search_name_single(o_current, "refdes", NULL);
216 fflush(stderr);
217 fflush(stdout);
218 printf("In s_sheet_data_add_master_comp_attrib_list, examining component refdes = %s\n", temp_uref);
219 free(temp_uref);
220 printf(" . . . from this component, about to add to master comp attrib list attrib = %s\n", attrib_name);
221 #endif
222 s_string_list_add_item(sheet_head->master_comp_attrib_list_head,
223 &(sheet_head->comp_attrib_count), attrib_name);
224 } /* if (strcmp(attrib_name, "refdes") != 0) */
225 free(attrib_name);
226 free(attrib_text);
228 a_current = a_current->next;
229 } /* while */
231 } /* if (o_current->type == OBJ_COMPLEX) */
233 o_current = o_current->next;
234 } /* while (o_current != NULL) */
236 /* ----- Now sort component list into alphabetical order ----- */
238 return;
243 /*------------------------------------------------------------------
244 * This fcn builds the master list of net names by running
245 * through the individual cells and recording the net refdeses
246 * it discovers.
247 *------------------------------------------------------------------*/
248 void s_sheet_data_add_master_net_list_items(OBJECT *start_obj) {
249 return;
253 /*------------------------------------------------------------------
254 * This fcn builds the master list of net attribs.
255 *------------------------------------------------------------------*/
256 void s_sheet_data_add_master_net_attrib_list_items(OBJECT *start_obj) {
257 return;
261 /*------------------------------------------------------------------
262 * This fcn builds the master list of pin names. It writes the
263 * label refdes:pinnumber into the global master pin list.
264 * Algorithm:
265 * 1. Loop on o_current looking for OBJ_COMPLEX
266 * 2. When we find a complex, save the refdes.
267 * 3. Dive down to o_lower_current = o_current->complex->prim_objs
268 * 4. Loop on o_lower_current looking for OBJ_PIN
269 * 5. When we find a pin, find the pinnumber by calling
270 * o_attrib_search_name_single(o_lower_current, "pinnumber", NULL)
271 * 6. Create the pin list label as "refdes=XXX", and stick it into
272 * the master pin list.
273 * Since this fcn operates on the global sheet_data->master_pin_list,
274 * it doesn't return a value.
275 *------------------------------------------------------------------*/
276 void s_sheet_data_add_master_pin_list_items(OBJECT *start_obj) {
277 char *temp_uref;
278 char *temp_pinnumber;
279 char *row_label;
280 OBJECT *o_current;
281 OBJECT *o_lower_current;
283 #ifdef DEBUG
284 fflush(stderr);
285 fflush(stdout);
286 printf("=========== Just entered s_sheet_data_add_master_pin_list_items! ==============\n");
287 #endif
289 if (verbose_mode) {
290 printf("- Starting master pin list creation.\n");
293 /* ----- Iterate through all objects found on page looking for components ----- */
294 o_current = start_obj;
295 while (o_current != NULL) {
297 #ifdef DEBUG
298 printf("In s_sheet_data_add_master_pin_list_items, examining o_current->name = %s\n", o_current->name);
299 #endif
301 if (o_current->type == OBJ_COMPLEX) {
302 temp_uref = o_attrib_search_name_single(o_current, "refdes", NULL);
303 if (temp_uref != NULL) { /* make sure object complex has a refdes */
305 /* ----- Now iterate through lower level objects looking for pins. ----- */
306 o_lower_current = o_current->complex->prim_objs;
307 while (o_lower_current != NULL) {
308 #if DEBUG
309 printf("In s_sheet_data_add_master_pin_list_items, examining object name %s\n", o_lower_current->name);
310 #endif
311 if (o_lower_current->type == OBJ_PIN) {
312 temp_pinnumber = o_attrib_search_name_single(o_lower_current, "pinnumber", NULL);
314 if( temp_pinnumber != NULL) {
315 row_label = u_basic_strdup_multiple(temp_uref, ":", temp_pinnumber, NULL);
316 #if DEBUG
317 printf("In s_sheet_data_add_master_pin_list_items, about to add to master pin list row_label = %s\n", row_label);
318 #endif
319 s_string_list_add_item(sheet_head->master_pin_list_head, &(sheet_head->pin_count), row_label);
321 } else { /* didn't find pinnumber. Report error to log. */
322 fprintf(stderr, "In s_sheet_data_add_master_pin_list_items, found component pin with no pinnumber.\n");
323 #ifdef DEBUG
324 fprintf(stderr, ". . . . refdes = %s.\n", temp_uref);
325 #endif
327 free(temp_pinnumber);
330 o_lower_current = o_lower_current->next;
331 } /* while (o_lower_current != NULL) */
333 } else { /* didn't find refdes. Report error to log. */
334 fprintf(stderr, "In s_sheet_data_add_master_pin_list_items, found non-graphical component with no refdes.\n");
335 #ifdef DEBUG
336 fprintf(stderr, ". . . . complex_basename = %s.\n", o_current->complex_basename);
337 #endif
339 free(temp_uref);
341 } /* if (o_current->type == OBJ_COMPLEX) */
342 o_current = o_current->next;
344 } /* while o_current != NULL */
346 return;
350 /*------------------------------------------------------------------
351 * This fcn builds the master list of pin attributes. It writes
352 * each attrib name into the master pin attrib list.
353 * Algorithm:
354 * 1. Loop on o_current looking for OBJ_COMPLEX
355 * 2. When we find a complex, save the refdes.
356 * 3. Dive down to o_lower_current = o_current->complex->prim_objs
357 * 4. Loop on o_lower_current looking for OBJ_PIN
358 * 5. When we find a pin, get pin_attribs = o_lower_current->attribs
359 * 6. Loop on attribs looking for non-NULL text.
360 * 7. When we find a non-NULL text attrib, extract the attrib name
361 * and stick it in the master pin attrib list.
362 *------------------------------------------------------------------*/
363 void s_sheet_data_add_master_pin_attrib_list_items(OBJECT *start_obj) {
364 char *temp_uref;
365 char *attrib_text;
366 char *attrib_name;
367 OBJECT *o_current;
368 OBJECT *o_lower_current;
369 ATTRIB *pin_attrib;
371 #ifdef DEBUG
372 fflush(stderr);
373 fflush(stdout);
374 printf("=========== Just entered s_sheet_data_add_master_pin_attrib_list_items! ==============\n");
375 #endif
377 if (verbose_mode) {
378 printf("- Starting master pin attrib list creation.\n");
381 /* ----- Iterate through all objects found on page looking for components ----- */
382 o_current = start_obj;
383 while (o_current != NULL) {
385 #ifdef DEBUG
386 printf("In s_sheet_data_add_master_pin_attrib_list_items, examining o_current->name = %s\n", o_current->name);
387 #endif
389 if (o_current->type == OBJ_COMPLEX) {
390 temp_uref = o_attrib_search_name_single(o_current, "refdes", NULL);
391 if (temp_uref != NULL) { /* make sure object complex has a refdes */
393 /* ----- Now iterate through lower level objects looking for pins. ----- */
394 o_lower_current = o_current->complex->prim_objs;
395 while (o_lower_current != NULL) {
396 #if DEBUG
397 printf("In s_sheet_data_add_master_pin_attrib_list_items, examining component refdes = %s\n", temp_uref);
398 #endif
399 if (o_lower_current->type == OBJ_PIN) {
400 /* ----- Found a pin. Now get attrib head and loop on attribs. ----- */
401 pin_attrib = o_lower_current->attribs;
402 while (pin_attrib != NULL) {
403 if (pin_attrib->object->type == OBJ_TEXT
404 && pin_attrib->object->text != NULL) { /* found an attribute */
405 attrib_text = u_basic_strdup(pin_attrib->object->text->string);
406 attrib_name = u_basic_breakup_string(attrib_text, '=', 0);
407 if (strcmp(attrib_name, "pinnumber") != 0) {
408 /* Don't include "pinnumber" because it is already in other master list */
410 #if DEBUG
411 printf("In s_sheet_data_add_master_pin_attrib_list_items, found pin attrib = %s\n", attrib_name);
412 printf(". . . . . adding it to master_pin_attrib_list\n");
413 #endif
415 s_string_list_add_item(sheet_head->master_pin_attrib_list_head,
416 &(sheet_head->pin_attrib_count), attrib_name);
417 } /* if (strcmp(attrib_name, "pinnumber") != 0) */
418 free(attrib_name);
419 free(attrib_text);
421 pin_attrib = pin_attrib->next;
422 } /* while (pin_attrib != NULL) */
424 o_lower_current = o_lower_current->next;
425 } /* while (o_lower_current != NULL) */
427 free(temp_uref);
428 } /* if (temp_uref != NULL ) */
430 } /* if (o_current->type == OBJ_COMPLEX) */
431 o_current = o_current->next;
433 } /* while (o_current != NULL) */
434 return;
441 /*------------------------------------------------------------------
442 * This fcn extracts the attribs from the gtksheet
443 * cells, and places them back into SHEET_DATA. This is the
444 * first step in saving out a project. Right now I just invoke
445 * s_table_gtksheet_to_table. Do I need to do anything else here?
446 *------------------------------------------------------------------*/
447 void s_sheet_data_gtksheet_to_sheetdata() {
448 s_table_gtksheet_to_all_tables();
449 /* do I need to do anything else here? */
451 return;