gerbv
drill_stats.c
Go to the documentation of this file.
1 /*
2  * gEDA - GNU Electronic Design Automation
3  * drill_stats.c -- a part of gerbv.
4  *
5  * Copyright (C) 2007 Stuart Brorson (sdb@cloud9.net)
6  *
7  * $Id$
8  *
9  * This program is free software; you can redistribute it and/or modify
10  * it under the terms of the GNU General Public License as published by
11  * the Free Software Foundation; either version 2 of the License, or
12  * (at your option) any later version.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program; if not, write to the Free Software
21  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111 USA
22  */
23 
29 #include "gerbv.h"
30 
31 #include <stdio.h>
32 #include <stdlib.h>
33 #include <string.h>
34 #include <math.h>
35 
36 #include "common.h"
37 #include "drill_stats.h"
38 #include "gerb_stats.h"
39 
40 #undef DPRINTF
41 #define DPRINTF(...) do { if (DEBUG) printf(__VA_ARGS__); } while (0)
42 
43 
44 /* ------------------------------------------------------- */
49 
50  gerbv_drill_stats_t *stats;
53 
54  /* Malloc space for new stats struct. Return NULL if error. */
55  if (NULL == (stats = g_new0(gerbv_drill_stats_t, 1))) {
56  return NULL;
57  }
58 
59  /* Initialize drill list */
60  drill_list = gerbv_drill_stats_new_drill_list();
61  if (drill_list == NULL)
62  GERB_FATAL_ERROR("malloc drill_list failed in %s()", __FUNCTION__);
63  stats->drill_list = (gerbv_drill_list_t *) drill_list;
64 
65  /* Initialize error list */
66  error_list = gerbv_drill_stats_new_error_list();
67  if (error_list == NULL)
68  GERB_FATAL_ERROR("malloc error_list failed in %s()", __FUNCTION__);
69  stats->error_list = (gerbv_error_list_t *) error_list;
70 
71  stats->detect = NULL;
72 
73  return stats;
74 }
75 
76 void
77 gerbv_drill_destroy_error_list (gerbv_error_list_t *errorList) {
78  gerbv_error_list_t *nextError=errorList,*tempError;
79 
80  while (nextError) {
81  tempError = nextError->next;
82  g_free (nextError->error_text);
83  g_free (nextError);
84  nextError = tempError;
85  }
86 }
87 
88 void
89 gerbv_drill_destroy_drill_list (gerbv_drill_list_t *apertureList) {
90  gerbv_drill_list_t *nextAperture=apertureList,*tempAperture;
91 
92  while (nextAperture) {
93  tempAperture = nextAperture->next;
94  g_free(nextAperture->drill_unit);
95  g_free (nextAperture);
96  nextAperture = tempAperture;
97  }
98 }
99 
100 void
102  if (stats == NULL)
103  return;
104  gerbv_drill_destroy_error_list (stats->error_list);
105  gerbv_drill_destroy_drill_list (stats->drill_list);
106  g_free (stats);
107 }
108 
109 /* ------------------------------------------------------- */
110 void
112  gerbv_drill_stats_t *input_stats,
113  int this_layer) {
114 
115  gerbv_drill_list_t *drill;
116  gerbv_error_list_t *error;
117  char *tmps, *tmps2;
118 
119  DPRINTF("---> Entering gerbv_drill_stats_add_layer ..... \n");
120 
121  accum_stats->layer_count++;
122 
123  accum_stats->comment += input_stats->comment;
124  /* F codes go here */
125 
126  accum_stats->G00 += input_stats->G00;
127  accum_stats->G01 += input_stats->G01;
128  accum_stats->G02 += input_stats->G02;
129  accum_stats->G03 += input_stats->G03;
130  accum_stats->G04 += input_stats->G04;
131  accum_stats->G05 += input_stats->G05;
132  accum_stats->G85 += input_stats->G85;
133  accum_stats->G90 += input_stats->G90;
134  accum_stats->G91 += input_stats->G91;
135  accum_stats->G93 += input_stats->G93;
136  accum_stats->G_unknown += input_stats->G_unknown;
137 
138  accum_stats->M00 += input_stats->M00;
139  accum_stats->M01 += input_stats->M01;
140  accum_stats->M18 += input_stats->M18;
141  accum_stats->M25 += input_stats->M25;
142  accum_stats->M30 += input_stats->M30;
143  accum_stats->M31 += input_stats->M31;
144  accum_stats->M45 += input_stats->M45;
145  accum_stats->M47 += input_stats->M47;
146  accum_stats->M48 += input_stats->M48;
147  accum_stats->M71 += input_stats->M71;
148  accum_stats->M72 += input_stats->M72;
149  accum_stats->M95 += input_stats->M95;
150  accum_stats->M97 += input_stats->M97;
151  accum_stats->M98 += input_stats->M98;
152  accum_stats->M_unknown += input_stats->M_unknown;
153 
154  accum_stats->R += input_stats->R;
155 
156  /* ==== Now deal with the drill list ==== */
157  for (drill = input_stats->drill_list;
158  drill != NULL;
159  drill = drill->next) {
160  DPRINTF(" In gerbv_drill_stats_add_layer, adding drill_num = %d to list\n",
161  drill->drill_num);
162  /* First add this input drill to the accumulated list.
163  * Drills already in accum list will not be added. */
164  drill_stats_add_to_drill_list(accum_stats->drill_list,
165  drill->drill_num,
166  drill->drill_size,
167  drill->drill_unit);
168 
169  /* Now add count of input drill to accum list */
170  DPRINTF(" adding count %d of drills for drill %d\n",
171  drill->drill_count, drill->drill_num);
172  drill_stats_add_to_drill_counter(accum_stats->drill_list,
173  drill->drill_num,
174  drill->drill_count);
175  accum_stats->total_count += drill->drill_count;
176  }
177 
178  /* ==== Now deal with the error list ==== */
179  for (error = input_stats->error_list; error != NULL; error = error->next) {
180  if (error->error_text != NULL)
181  gerbv_stats_printf(accum_stats->error_list, error->type,
182  this_layer, "%s", error->error_text);
183  }
184 
185  /* ==== Now deal with the misc header stuff ==== */
186  tmps = NULL;
187  tmps2 = NULL;
188  if (input_stats->detect) {
189  tmps2 = g_strdup_printf (_("Broken tool detect %s (layer %d)"), input_stats->detect, this_layer);
190  }
191  if (accum_stats->detect) {
192  if (tmps2) {
193  tmps = g_strdup_printf ("%s\n%s", accum_stats->detect, tmps2);
194  g_free (accum_stats->detect);
195  accum_stats->detect = NULL;
196  }
197  } else {
198  if (tmps2) {
199  tmps = g_strdup_printf ("%s", tmps2);
200  }
201  }
202  if (tmps2) {
203  g_free (tmps2);
204  }
205  if (tmps != NULL) {
206  accum_stats->detect = tmps;
207  }
208 
209  for (error = input_stats->error_list;
210  error != NULL;
211  error = error->next) {
212  if (error->error_text != NULL) {
213  gerbv_stats_printf(accum_stats->error_list, error->type,
214  this_layer, "%s", error->error_text);
215  }
216  }
217 
218 
219  DPRINTF("<--- .... Leaving gerbv_drill_stats_add_layer.\n");
220 
221  return;
222 }
223 
224 
225 /* ------------------------------------------------------- */
226 gboolean
227 drill_stats_in_drill_list(gerbv_drill_list_t *drill_list_in,
228  int drill_num_in) {
229  gerbv_drill_list_t *drill;
230  for(drill = drill_list_in; drill != NULL; drill = drill->next) {
231  if (drill_num_in == drill->drill_num) {
232  return TRUE;
233  }
234  }
235  return FALSE;
236 
237 }
238 
239 /* ------------------------------------------------------- */
241 gerbv_drill_stats_new_drill_list() {
243 
244  /* Malloc space for new drill_list struct. Return NULL if error. */
245  if (NULL == (drill_list = g_new(gerbv_drill_list_t, 1))) {
246  return NULL;
247  }
248 
249  drill_list->drill_count = 0;
250  drill_list->drill_num = -1; /* default val */
251  drill_list->drill_size = 0.0;
252  drill_list->drill_unit = NULL;
253  drill_list->next = NULL;
254  return drill_list;
255 }
256 
257 
258 /* ------------------------------------------------------- */
259 void
260 drill_stats_add_to_drill_list(gerbv_drill_list_t *drill_list_in,
261  int drill_num_in, double drill_size_in,
262  char *drill_unit_in) {
263 
264  gerbv_drill_list_t *drill_list_new;
265  gerbv_drill_list_t *drill;
266  gerbv_drill_list_t *drill_last = NULL;
267 
268  DPRINTF("%s(%p, %d, %g, \"%s\")\n", __FUNCTION__, drill_list_in, drill_num_in,
269  drill_size_in, drill_unit_in);
270 
271  DPRINTF(" ---> Entering drill_stats_add_to_drill_list, first drill_num in list = %d ...\n",
272  drill_list_in->drill_num);
273 
274  /* First check for empty list. If empty, then just add this drill */
275  if (drill_list_in->drill_num == -1) {
276  DPRINTF(" .... In drill_stats_add_to_drill_list, adding first drill, no %d\n",
277  drill_num_in);
278  drill_list_in->drill_num = drill_num_in;
279  drill_list_in->drill_size = drill_size_in;
280  drill_list_in->drill_count = 0;
281  drill_list_in->drill_unit = g_strdup_printf("%s", drill_unit_in);
282  drill_list_in->next = NULL;
283  return;
284  }
285  /* Else check to see if this drill is already in the list */
286  for(drill = drill_list_in;
287  drill != NULL;
288  drill = (gerbv_drill_list_t *) drill->next) {
289  DPRINTF("checking this drill_num %d against that in list %d.\n",
290  drill_num_in, drill->drill_num);
291  if (drill_num_in == drill->drill_num) {
292  DPRINTF(" .... In drill_stats_add_to_drill_list, drill no %d already in list\n",
293  drill_num_in);
294  return; /* Found it in list, so return */
295  }
296  drill_last = drill;
297  }
298 
299  /* Now malloc space for new drill list element */
300  if (NULL == (drill_list_new = g_new(gerbv_drill_list_t, 1))) {
301  GERB_FATAL_ERROR("malloc format failed in %s()", __FUNCTION__);
302  }
303 
304  /* Now set various parameters based upon calling args */
305  DPRINTF(" .... In drill_stats_add_to_drill_list, adding new drill, no %d\n",
306  drill_num_in);
307  drill_list_new->drill_num = drill_num_in;
308  drill_list_new->drill_size = drill_size_in;
309  drill_list_new->drill_count = 0;
310  drill_list_new->drill_unit = g_strdup_printf("%s", drill_unit_in);
311  drill_list_new->next = NULL;
312  drill_last->next = drill_list_new;
313 
314  DPRINTF(" <---- ... leaving drill_stats_add_to_drill_list.\n");
315  return;
316 }
317 
318 /* ------------------------------------------------------- */
319 void
320 drill_stats_modify_drill_list(gerbv_drill_list_t *drill_list_in,
321  int drill_num_in, double drill_size_in,
322  char *drill_unit_in) {
323 
324  gerbv_drill_list_t *drill;
325 
326  DPRINTF(" ---> Entering drill_stats_modify_drill_list, first drill_num in list = %d ...\n",
327  drill_list_in->drill_num);
328 
329  /* Look for this drill num in list */
330  for(drill = drill_list_in;
331  drill != NULL;
332  drill = (gerbv_drill_list_t *) drill->next) {
333  DPRINTF("checking this drill_num %d against that in list %d.\n",
334  drill_num_in, drill->drill_num);
335  if (drill_num_in == drill->drill_num) {
336  DPRINTF(" .... Found it, now update it ....\n");
337  drill->drill_size = drill_size_in;
338  if (drill->drill_unit)
339  g_free(drill->drill_unit);
340  drill->drill_unit = g_strdup_printf("%s", drill_unit_in);
341  DPRINTF(" <---- ... Modified drill. leaving drill_stats_modify_drill_list.\n");
342  return;
343  }
344  }
345  DPRINTF(" <---- ... Did not find drill. leaving drill_stats_modify_drill_list.\n");
346  return;
347 }
348 
349 /* ------------------------------------------------------- */
350 void
351 drill_stats_increment_drill_counter(gerbv_drill_list_t *drill_list_in,
352  int drill_num_in) {
353 
354  DPRINTF(" ----> Entering drill_stats_increment_drill_counter......\n");
355  /* First check to see if this drill is already in the list */
356  gerbv_drill_list_t *drill;
357  for(drill = drill_list_in; drill != NULL; drill = drill->next) {
358  if (drill_num_in == drill->drill_num) {
359  drill->drill_count++;
360  DPRINTF(" .... incrementing drill count. drill_num = %d, drill_count = %d.\n",
361  drill_list_in->drill_num, drill->drill_count);
362  DPRINTF(" <---- .... Leaving drill_stats_increment_drill_counter after incrementing counter.\n");
363  return;
364  }
365  }
366  DPRINTF(" <---- .... Leaving drill_stats_increment_drill_counter without incrementing any counter.\n");
367 
368 }
369 
370 /* ------------------------------------------------------- */
371 void
372 drill_stats_add_to_drill_counter(gerbv_drill_list_t *drill_list_in,
373  int drill_num_in,
374  int increment) {
375 
376  gerbv_drill_list_t *drill;
377  for(drill = drill_list_in; drill != NULL; drill = drill->next) {
378  if (drill_num_in == drill->drill_num) {
379  DPRINTF(" In drill_stats_add_to_drill_counter, adding increment = %d drills to drill list\n", increment);
380  drill->drill_count += increment;
381  return;
382  }
383  }
384 }
385 
386 
387 /* ------------------------------------------------------- */
389 gerbv_drill_stats_new_error_list() {
391 
392  /* Malloc space for new error_list struct. Return NULL if error. */
393  if (NULL == (error_list = g_new(gerbv_error_list_t, 1))) {
394  return NULL;
395  }
396 
397  error_list->layer = -1;
398  error_list->error_text = NULL;
399  error_list->next = NULL;
400  return error_list;
401 }
402 
403 /* ------------------------------------------------------- */
406 void
408  int layer, const char *error_text,
410 {
411  gerbv_stats_add_error(error_list_in, layer, error_text, type);
412 }
void gerbv_drill_stats_destroy(gerbv_drill_stats_t *stats)
Definition: drill_stats.c:101
void gerbv_drill_stats_add_layer(gerbv_drill_stats_t *accum_stats, gerbv_drill_stats_t *input_stats, int this_layer)
Definition: drill_stats.c:111
void drill_stats_add_error(gerbv_error_list_t *error_list_in, int layer, const char *error_text, gerbv_message_type_t type)
Add statistic message for drill layer.
Definition: drill_stats.c:407
gerbv_drill_stats_t * gerbv_drill_stats_new(void)
Allocates a new drill_stats structure.
Definition: drill_stats.c:48
Header info to the statistics generating functions for Excellon drill files.
Header info for the statistics generating functions for RS274X files.
The main header file for the libgerbv library.
gerbv_message_type_t
Definition: gerbv.h:149