SDDS ToolKit Programs and Libraries for C and Python
All Classes Files Functions Variables Macros Pages
SDDSaps.c
Go to the documentation of this file.
1/**
2 * @file SDDSaps.c
3 * @brief Routines used by SDDS command-line applications.
4 *
5 * This file contains implementations of various routines that support the
6 * functionality of SDDS (Self Describing Data Sets) command-line applications.
7 * It includes functions for processing columns, filtering data, managing
8 * definitions, and handling edits and casts on SDDS datasets.
9 *
10 * @copyright
11 * - (c) 2002 The University of Chicago, as Operator of Argonne National Laboratory.
12 * - (c) 2002 The Regents of the University of California, as Operator of Los Alamos National Laboratory.
13 *
14 * @license
15 * This file is distributed under the terms of the Software License Agreement
16 * found in the file LICENSE included with this distribution.
17 *
18 * @author M. Borland, C. Saunders, R. Soliday, H. Shang
19 */
20
21#include <ctype.h>
22#include "mdb.h"
23#include "SDDS.h"
24#include "SDDSaps.h"
25#include "rpn.h"
26#if !defined(_WIN32)
27# include <sys/time.h>
28#endif
29
30#undef DEBUG
31
32char *data_class_keyword[DATA_CLASS_KEYWORDS] = {
33 "column",
34 "parameter",
35 "array",
36};
37
38typedef struct {
39 char *name, *description;
40 unsigned long flags;
42#define PROCMODE_NORMAL 0x0000UL
43#define PROCMODE_FUNCOF_REQUIRED 0x0001UL
44#define PROCMODE_FUNCOF_UNITS 0x0002UL
45#define PROCMODE_WEIGHT_OK 0x0004UL
46#define PROCMODE_POSITION_OK 0x0008UL
47#define PROCMODE_STRING_OK 0x0010UL
48#define PROCMODE_YoX_UNITS 0x0020UL
49#define PROCMODE_STRINGPOS_OK 0x0040UL
50#define PROCMODE_YtX_UNITS 0x0080UL
51#define PROCMODE_Y_UNITS 0x0100UL
52#define PROCMODE_NO_UNITS x00200UL
53
54static char *process_column_name[N_PROCESS_COLUMN_MODES] = {NULL};
55static PROCESS_COLUMN_DATA process_column_data[N_PROCESS_COLUMN_MODES] = {
56 {"average", "average of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_WEIGHT_OK},
57 {"rms", "rms of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_WEIGHT_OK},
58 {"sum", "sum of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_WEIGHT_OK},
59 {"standarddeviation", "standard deviation of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_WEIGHT_OK},
60 {"mad", "mean absolute deviation of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_WEIGHT_OK},
61 {"minimum", "minimum of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_POSITION_OK | PROCMODE_STRINGPOS_OK},
62 {"maximum", "maximum of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_POSITION_OK | PROCMODE_STRINGPOS_OK},
63 {"smallest", "smallest of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_POSITION_OK | PROCMODE_STRINGPOS_OK},
64 {"largest", "largest of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_POSITION_OK | PROCMODE_STRINGPOS_OK},
65 {"first", "first ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_STRING_OK},
66 {"last", "last ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_STRING_OK},
67 {"count", "count ", PROCMODE_NORMAL},
68 {"spread", "spread in ", PROCMODE_NORMAL | PROCMODE_Y_UNITS},
69 {"median", "median of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS},
70 {"baselevel", "base level of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS},
71 {"toplevel", "top level of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS},
72 {"amplitude", "amplitude of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS},
73 {"risetime", "risetime of ", PROCMODE_FUNCOF_REQUIRED | PROCMODE_FUNCOF_UNITS},
74 {"falltime", "falltime of", PROCMODE_FUNCOF_REQUIRED | PROCMODE_FUNCOF_UNITS},
75 {"fwhm", "fwhm of ", PROCMODE_FUNCOF_REQUIRED | PROCMODE_FUNCOF_UNITS},
76 {"fwtm", "fwtm of ", PROCMODE_FUNCOF_REQUIRED | PROCMODE_FUNCOF_UNITS},
77 {"center", "center of ", PROCMODE_FUNCOF_REQUIRED | PROCMODE_FUNCOF_UNITS},
78 {"zerocrossing", "zero crossing of ", PROCMODE_FUNCOF_REQUIRED | PROCMODE_FUNCOF_UNITS},
79 {"fwha", "fwha of ", PROCMODE_FUNCOF_REQUIRED | PROCMODE_FUNCOF_UNITS},
80 {"fwta", "fwta of ", PROCMODE_FUNCOF_REQUIRED | PROCMODE_FUNCOF_UNITS},
81 {"sigma", "sigma of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_WEIGHT_OK},
82 {"slope", "slope of ", PROCMODE_FUNCOF_REQUIRED | PROCMODE_YoX_UNITS},
83 {"intercept", "intercept of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS},
84 {"lfsd", "linear-fit standard deviation of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS},
85 {"qrange", "quartile range", PROCMODE_NORMAL | PROCMODE_Y_UNITS},
86 {"drange", "decile range", PROCMODE_NORMAL | PROCMODE_Y_UNITS},
87 {"percentile", "percentile", PROCMODE_NORMAL | PROCMODE_Y_UNITS},
88 {"mode", "mode of", PROCMODE_NORMAL | PROCMODE_Y_UNITS},
89 {"integral", "integral of ", PROCMODE_NORMAL | PROCMODE_FUNCOF_REQUIRED | PROCMODE_YtX_UNITS},
90 {"product", "product of ", PROCMODE_NORMAL | PROCMODE_WEIGHT_OK},
91 {"prange", "percentile range", PROCMODE_NORMAL | PROCMODE_Y_UNITS},
92 {"signedsmallest", "signed smallest of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_POSITION_OK | PROCMODE_STRINGPOS_OK},
93 {"signedlargest", "signed largest of ", PROCMODE_NORMAL | PROCMODE_Y_UNITS | PROCMODE_POSITION_OK | PROCMODE_STRINGPOS_OK},
94 {"gmintegral", "integral of ", PROCMODE_NORMAL | PROCMODE_FUNCOF_REQUIRED | PROCMODE_YtX_UNITS},
95 {"correlation", "correlation coefficient", PROCMODE_FUNCOF_REQUIRED}};
96
97/* these are used for options that support wildcard-based processing
98 * using syntax like -define=column,%sFoo,"%sBar 2 *",select=x*
99 */
100#define SELECT_QUALIFIER 0
101#define EDITSELECTION_QUALIFIER 1
102#define EXCLUDE_QUALIFIER 2
103#define SELECT_QUALIFIERS 3
104static char *selectQualifier[SELECT_QUALIFIERS] = {
105 "select", "editselection", "exclude"};
106
107void GillMillerIntegration1(double *indepData, double *data, long n_data, double *result);
108
109void show_process_modes(FILE *fp) {
110 long i, length, maxLength, nPerLine;
111 char format[30];
112
113 maxLength = 0;
114 for (i = 0; i < N_PROCESS_COLUMN_MODES; i++)
115 if ((length = strlen(process_column_data[i].name)) > maxLength)
116 maxLength = length;
117 sprintf(format, "%%%lds%%c", maxLength + 1);
118 nPerLine = 80 / (maxLength + 2);
119 fprintf(fp, "processing modes:\n");
120 for (i = 0; i < N_PROCESS_COLUMN_MODES; i++)
121 fprintf(fp, format, process_column_data[i].name, (i + 1) % nPerLine ? ' ' : '\n');
122 if (i % nPerLine)
123 fputc('\n', fp);
124}
125
126void add_ifitem(IFITEM_LIST *ifitem, char **name, long names) {
127 long i, type;
128 if (ifitem->items == 0) {
129 ifitem->name = NULL;
130 ifitem->type = NULL;
131 }
132 ifitem->name = trealloc(ifitem->name, sizeof(*ifitem->name) * (ifitem->items + names - 1));
133 ifitem->type = trealloc(ifitem->type, sizeof(*ifitem->type) * (ifitem->items + names - 1));
134 if ((type = match_string(name[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) < 0)
135 SDDS_Bomb("invalid -ifnot syntax---column, parameter, or array keyword required");
136 for (i = 1; i < names; i++)
137 ifitem->type[ifitem->items + i - 1] = type;
138 if (!SDDS_CopyStringArray(ifitem->name + ifitem->items, name + 1, names - 1))
139 SDDS_Bomb("problem copying names for -ifnot or -ifis option");
140 ifitem->items += names - 1;
141}
142
143long check_ifitems(SDDS_DATASET *SDDS_dataset, IFITEM_LIST *ifitem, long desired, long announce) {
144 long i, index;
145 for (i = 0; i < ifitem->items; i++) {
146 switch (ifitem->type[i]) {
147 case COLUMN_BASED:
148 index = SDDS_GetColumnIndex(SDDS_dataset, ifitem->name[i]);
149 break;
150 case PARAMETER_BASED:
151 index = SDDS_GetParameterIndex(SDDS_dataset, ifitem->name[i]);
152 break;
153 case ARRAY_BASED:
154 index = SDDS_GetArrayIndex(SDDS_dataset, ifitem->name[i]);
155 break;
156 default:
157 SDDS_Bomb("internal error---unknown ifitem type");
158 exit(1);
159 break;
160 }
161 if ((index >= 0) != desired) {
162 if (desired) {
163 if (announce)
164 fprintf(stderr, "%s %s does not exist--aborting\n",
165 data_class_keyword[ifitem->type[i]], ifitem->name[i]);
166 return 0;
167 }
168 if (announce)
169 fprintf(stderr, "%s %s exists--aborting\n",
170 data_class_keyword[ifitem->type[i]], ifitem->name[i]);
171 return 0;
172 }
173 }
174 return 1;
175}
176
177FILTER_DEFINITION *process_new_filter_definition(char **argument, long arguments) {
178 FILTER_DEFINITION *defi;
179
180 if (!(defi = tmalloc(sizeof(*defi))))
181 SDDS_Bomb("memory allocation failure (process_new_filter_definition)");
182 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
183 case COLUMN_BASED:
184 defi->is_parameter = 0;
185 break;
186 case PARAMETER_BASED:
187 defi->is_parameter = 1;
188 break;
189 default:
190 fprintf(stderr, "error: column or parameter must be specified for filter\n");
191 return (NULL);
192 }
193 if (!(defi->filter_terms =
194 process_filter_request(&(defi->filter_term), argument + 1, arguments - 1)))
195 return (NULL);
196 return (defi);
197}
198
199TIME_FILTER_DEFINITION *process_new_time_filter_definition(char **argument, long arguments) {
201 char *before, *after, *year, *month = NULL, *day = NULL, *hour, *minute, *second;
202 short minute_n, second_n, hour_n;
203 double hour_n1;
204 minute_n = second_n = hour_n = 0;
205
206 before = after = NULL;
207 if (!(defi = tmalloc(sizeof(*defi))))
208 SDDS_Bomb("memory allocation failure (process_new_filter_definition)");
209 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
210 case COLUMN_BASED:
211 defi->is_parameter = 0;
212 break;
213 case PARAMETER_BASED:
214 defi->is_parameter = 1;
215 break;
216 default:
217 fprintf(stderr, "error: column or parameter must be specified for filter\n");
218 return (NULL);
219 }
220 defi->flags = 0;
221 defi->before = defi->after = 0;
222 hour = minute = second = 0;
223 defi->name = argument[1];
224 arguments -= 2;
225 argument += 2;
226 if (!scanItemList(&defi->flags, argument, &arguments, 0,
227 "before", SDDS_STRING, &before, 1, TIMEFILTER_BEFORE_GIVEN,
228 "after", SDDS_STRING, &after, 1, TIMEFILTER_AFTER_GIVEN,
229 "invert", -1, NULL, 0, TIMEFILTER_INVERT_GIVEN,
230 NULL))
231 SDDS_Bomb("invalid -timeFilter syntax");
232 if (before) {
233 minute_n = second_n = hour_n = 0;
234 if (!(year = get_token_tq(before, "", "/", "", "")) ||
235 !(month = get_token_tq(before, "/", "/", "", "")) ||
236 !(day = get_token_tq(before, "/", "@", "", "")))
237 SDDS_Bomb("invalid \"before\" date given, the specified data should be YYYY/MM/DD@HH:MM:SS");
238 if ((hour = get_token_tq(before, "@", ":", "", "")))
239 hour_n = atol(hour);
240 if ((minute = get_token_tq(before, ":", ":", "", "")))
241 minute_n = atol(minute);
242 if ((second = get_token_tq(before, ":", "", "", "")))
243 second_n = atol(second);
244 hour_n1 = hour_n * 1.0 + minute_n / 60.0 + second_n / 3600.0;
245 if (!TimeBreakdownToEpoch(atol(year), 0, atol(month), atol(day), hour_n1, &defi->before))
246 SDDS_Bomb("invalid -timeFilter before syntax (something wrong with time convert)");
247 /*fprintf(stderr,"before: hour=%d,minute=%d,second=%d, time=%f\n",hour_n,minute_n,second_n,defi->before);*/
248 }
249 if (after) {
250 minute_n = second_n = hour_n = 0;
251 if (!(year = get_token_tq(after, "", "/", "", "")) ||
252 !(month = get_token_tq(after, "/", "/", "", "")) ||
253 !(day = get_token_tq(after, "/", "@", "", "")))
254 SDDS_Bomb("invalid \"after\" date given, the specified data should be YYYY/MM/DD@HH:MM:SS");
255 if ((hour = get_token_tq(after, "@", ":", "", "")))
256 hour_n = atol(hour);
257 if ((minute = get_token_tq(after, ":", ":", "", "")))
258 minute_n = atol(minute);
259 if ((second = get_token_tq(after, ":", "", "", "")))
260 second_n = atol(second);
261 hour_n1 = hour_n * 1.0 + minute_n / 60.0 + second_n / 3600.0;
262 if (!TimeBreakdownToEpoch(atol(year), 0, atol(month), atol(day), hour_n1, &defi->after))
263 SDDS_Bomb("invalid -timeFilter after syntax (something wrong with time convert)");
264 /* fprintf(stderr,"after: hour=%d,minute=%d,second=%d, time=%f\n",hour_n,minute_n,second_n,defi->after); */
265 }
266 if (before && after && defi->before < defi->after)
267 SDDS_Bomb("Invalid -timeFilter syntx, before date is earlier than the after date!");
268 if (!before)
269 defi->before = getTimeInSecs() + 3600.0;
270 /*no before time is given, accept all the time from the after date to now+3600*/
271 if (!after)
272 defi->after = -1; /*no after time is given, accept all the time before the before date */
273 /*fprintf(stderr,"before=%f, after=%f\n",defi->before,defi->after); */
274 return (defi);
275}
276
277MATCH_DEFINITION *process_new_match_definition(char **argument, long arguments) {
278 MATCH_DEFINITION *defi;
279
280 if (!(defi = tmalloc(sizeof(*defi))))
281 SDDS_Bomb("memory allocation failure (process_new_match_definition)");
282 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
283 case COLUMN_BASED:
284 defi->is_parameter = 0;
285 break;
286 case PARAMETER_BASED:
287 defi->is_parameter = 1;
288 break;
289 default:
290 fprintf(stderr, "error: column or parameter must be specified for match\n");
291 return (NULL);
292 }
293 if (!(defi->match_terms =
294 process_match_request(&(defi->match_term), argument + 1, arguments - 1)))
295 return (NULL);
296 return (defi);
297}
298
299long process_filter_request(FILTER_TERM **filter, char **argument, long arguments) {
300 long i, filters, max_filters;
301 long need_name, need_operation;
302
303 filters = 0;
304 i = 0;
305 max_filters = (arguments + 1) / 3 + 1;
306 *filter = tmalloc(sizeof(**filter) * max_filters);
307
308 need_name = 1;
309 need_operation = -1;
310 do {
311 if (is_logic_character(argument[i][0])) {
312 if (need_name)
313 return (0);
314 do {
315 /* will come here only for &, |, or ! applying to expressions */
316 if (need_name)
317 return (0);
318 switch (argument[i][0]) {
319 case '&':
320 if ((*filter)[filters].logic & SDDS_AND || (*filter)[filters].logic & SDDS_OR ||
321 (*filter)[filters].logic & SDDS_NEGATE_EXPRESSION)
322 return (0);
323 (*filter)[filters].logic |= SDDS_AND;
324 break;
325 case '|':
326 if ((*filter)[filters].logic & SDDS_AND || (*filter)[filters].logic & SDDS_OR ||
327 (*filter)[filters].logic & SDDS_NEGATE_EXPRESSION)
328 return (0);
329 (*filter)[filters].logic |= SDDS_OR;
330 break;
331 case '!':
332 if (!((*filter)[filters].logic & SDDS_AND || (*filter)[filters].logic & SDDS_OR) ||
333 (*filter)[filters].logic & SDDS_NEGATE_EXPRESSION)
334 return (0);
335 (*filter)[filters].logic |= SDDS_NEGATE_EXPRESSION;
336 }
337 } while (++i < arguments && is_logic_character(argument[i][0]));
338 filters++;
339 if (i >= arguments)
340 break;
341 need_name = 1;
342 } else if (need_operation > 0)
343 return (0);
344
345 /* should have a triplet (name, lower, upper) in argument list now */
346 if (is_logic_character(argument[i][0]))
347 return (0);
348 if (arguments - i < 3)
349 return (0);
350 if (filters + 1 >= max_filters)
351 *filter = trealloc(*filter, sizeof(**filter) * (max_filters += 2));
352 (*filter)[filters].name = argument[i++];
353 if (sscanf(argument[i], "%lf", &(*filter)[filters].lower) != 1)
354 (*filter)[filters].lowerPar = argument[i];
355 else
356 (*filter)[filters].lowerPar = NULL;
357 i++;
358 if (sscanf(argument[i], "%lf", &(*filter)[filters].upper) != 1)
359 (*filter)[filters].upperPar = argument[i];
360 else
361 (*filter)[filters].upperPar = NULL;
362 i++;
363 if ((*filter)[filters].lowerPar == NULL && (*filter)[filters].upperPar == NULL && (*filter)[filters].upper < (*filter)[filters].lower)
364 return (0);
365 (*filter)[filters].logic = 0;
366 if (arguments - i > 0 && argument[i][0] == '!') {
367 (*filter)[filters].logic = SDDS_NEGATE_MATCH;
368 i++;
369 }
370 if (++need_operation > 0)
371 need_name = 0;
372 else
373 filters++;
374 } while (arguments > i);
375 (*filter)[0].logic |= SDDS_AND;
376 return (filters);
377}
378
379long process_match_request(MATCH_TERM **match, char **argument, long arguments) {
380 long i, matches, max_matches;
381 long need_name, need_operation;
382 char *ptr;
383
384 matches = 0;
385 i = 0;
386 max_matches = (arguments + 1) / 3 + 1;
387 *match = tmalloc(sizeof(**match) * max_matches);
388
389 need_name = 1;
390 need_operation = -1;
391 do {
392 if (is_logic_character(argument[i][0])) {
393 if (need_name)
394 return (0);
395 do {
396 /* will come here only for &, |, or ! applying to expressions */
397 if (need_name)
398 return (0);
399 switch (argument[i][0]) {
400 case '&':
401 if ((*match)[matches].logic & SDDS_AND || (*match)[matches].logic & SDDS_OR ||
402 (*match)[matches].logic & SDDS_NEGATE_EXPRESSION)
403 return (0);
404 (*match)[matches].logic |= SDDS_AND;
405 break;
406 case '|':
407 if ((*match)[matches].logic & SDDS_AND || (*match)[matches].logic & SDDS_OR ||
408 (*match)[matches].logic & SDDS_NEGATE_EXPRESSION)
409 return (0);
410 (*match)[matches].logic |= SDDS_OR;
411 break;
412 case '!':
413 if (!((*match)[matches].logic & SDDS_AND || (*match)[matches].logic & SDDS_OR) ||
414 (*match)[matches].logic & SDDS_NEGATE_EXPRESSION)
415 return (0);
416 (*match)[matches].logic |= SDDS_NEGATE_EXPRESSION;
417 }
418 } while (++i < arguments && is_logic_character(argument[i][0]));
419 matches++;
420 if (i >= arguments)
421 break;
422 need_name = 1;
423 } else if (need_operation > 0)
424 return (0);
425
426 /* should have a name=string object now */
427 if (is_logic_character(argument[i][0]))
428 return (0);
429 if (arguments - i < 1)
430 return (0);
431 if (matches + 1 >= max_matches)
432 *match = trealloc(*match, sizeof(**match) * (max_matches += 2));
433 if (!(ptr = strchr(argument[i], '=')))
434 return (0);
435 *ptr = 0;
436 (*match)[matches].logic = 0;
437 if (*(ptr + 1) == '+') {
438 (*match)[matches].logic |= SDDS_NOCASE_COMPARE;
439 ptr++;
440 }
441 if (*(ptr + 1) == '@') {
442 (*match)[matches].logic |= SDDS_INDIRECT_MATCH;
443 ptr++;
444 }
445 (*match)[matches].name = argument[i++];
446 (*match)[matches].string = ptr + 1;
447 if (arguments - i > 0 && argument[i][0] == '!') {
448 (*match)[matches].logic |= SDDS_NEGATE_MATCH;
449 i++;
450 }
451 if (++need_operation > 0)
452 need_name = 0;
453 else
454 matches++;
455 } while (arguments > i);
456 (*match)[0].logic |= SDDS_AND;
457 return (matches);
458}
459
460void scan_label_parameter(LABEL_PARAMETER *label, char *string) {
461 char *ptr;
462 label->format = NULL;
463 if ((ptr = strchr(string, '='))) {
464 *ptr = 0;
465 label->format = ptr + 1;
466 }
467 label->name = string;
468}
469
470void show_matches(char *type, MATCH_TERM *match, long matches) {
471 long i;
472 fprintf(stderr, "\n %s matching logic:\n", type);
473 for (i = 0; i < matches; i++) {
474 if (match[i].logic & SDDS_NEGATE_MATCH)
475 fprintf(stderr, " <%s> != ", match[i].name);
476 else
477 fprintf(stderr, " <%s> == ", match[i].name);
478 if (match[i].logic & SDDS_INDIRECT_MATCH)
479 fprintf(stderr, "<%s>", match[i].string);
480 else
481 fprintf(stderr, "\"%s\"", match[i].string);
482 if (match[i].logic & SDDS_NOCASE_COMPARE)
483 fprintf(stderr, " (case insensitive)\n");
484 else
485 fprintf(stderr, " (case sensitive)\n");
486 if (i != 0) {
487 if (match[i].logic & SDDS_AND)
488 fprintf(stderr, "&& ");
489 if (match[i].logic & SDDS_OR)
490 fprintf(stderr, "|| ");
491 }
492 if (match[i].logic & SDDS_NEGATE_EXPRESSION)
493 fputc('!', stderr);
494 fputc('\n', stderr);
495 }
496}
497
498void show_filters(char *type, FILTER_TERM *filter, long filters) {
499 long i;
500 fprintf(stderr, "\n %s filtering logic:\n", type);
501 for (i = 0; i < filters; i++) {
502 if (filter[i].logic & SDDS_NEGATE_MATCH)
503 fprintf(stderr, " !( <%s>:[%22.15e, %22.15e] ) ", filter[i].name, filter[i].lower, filter[i].upper);
504 else
505 fprintf(stderr, " <%s>:[%22.15e, %22.15e] ", filter[i].name, filter[i].lower, filter[i].upper);
506 if (i != 0) {
507 if (filter[i].logic & SDDS_AND)
508 fprintf(stderr, "&& ");
509 if (filter[i].logic & SDDS_OR)
510 fprintf(stderr, "|| ");
511 }
512 if (filter[i].logic & SDDS_NEGATE_EXPRESSION)
513 fputc('!', stderr);
514 fputc('\n', stderr);
515 }
516}
517
518EQUATION_DEFINITION *process_new_equation_definition(char **argument, long arguments) {
519 static char s[SDDS_MAXLINE];
520 char *ptr, *equation;
521 long i, code, algebraic = 0;
523 char pfix[IFPF_BUF_SIZE];
524
525 if (!(defi = tmalloc(sizeof(*defi))))
526 SDDS_Bomb("memory allocation failure (process_new_equation_definition)");
527 defi->name = defi->text = defi->equation = defi->udf_name =
528 defi->editSelection = defi->select = defi->exclude = NULL;
529 defi->argv = NULL;
530 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
531 case COLUMN_BASED:
532 defi->is_parameter = 0;
533 sprintf(s, "&column name=\"%s\", ", argument[1]);
534 break;
535 case PARAMETER_BASED:
536 defi->is_parameter = 1;
537 sprintf(s, "&parameter name=\"%s\", ", argument[1]);
538 break;
539 default:
540 fprintf(stderr, "error: column or parameter must be specified for definition\n");
541 return (NULL);
542 }
543 SDDS_CopyString(&defi->name, argument[1]);
544
545 for (i = 3; i < arguments; i++) {
546 if (strncmp(argument[i], "algebraic", strlen(argument[i])) == 0) {
547 algebraic = 1;
548 break;
549 }
550 }
551
552 defi->argc = 0;
553
554 if (algebraic) {
555 if (argument[2][0] == '@') {
556 /*Add second @ symbol to signify that the parameter contains algebraic notation*/
557 equation = malloc(sizeof(char) * strlen(argument[2]) + 1);
558 sprintf(equation, "@%s", argument[2]);
559 } else {
560 ptr = addOuterParentheses(argument[2]);
561 if2pf(pfix, ptr, sizeof pfix);
562 free(ptr);
563
564 if (!SDDS_CopyString(&equation, pfix)) {
565 fprintf(stderr, "error: problem copying argument string\n");
566 return NULL;
567 }
568 }
569 if (arguments > 4) {
570 defi->argv = tmalloc(sizeof(*defi->argv) * (arguments - 3));
571 } else {
572 defi->argv = tmalloc(sizeof(*defi->argv) * 1);
573 }
574 } else {
575 equation = argument[2];
576 if (arguments > 3) {
577 defi->argv = tmalloc(sizeof(*defi->argv) * (arguments - 2));
578 } else {
579 defi->argv = tmalloc(sizeof(*defi->argv) * 1);
580 }
581 }
582 for (i = 3; i < arguments; i++) {
583 if (!(ptr = strchr(argument[i], '='))) {
584 if (strncmp(argument[i], "algebraic", strlen(argument[i])) == 0)
585 continue;
586 fprintf(stderr, "error: invalid definition-entry: %s\n", argument[i]);
587 return (NULL);
588 }
589 *ptr = 0;
590 switch (code = match_string(argument[i], selectQualifier, SELECT_QUALIFIERS, 0)) {
591 case SELECT_QUALIFIER:
592 SDDS_CopyString(&defi->select, ptr + 1);
593 break;
594 case EDITSELECTION_QUALIFIER:
595 SDDS_CopyString(&defi->editSelection, ptr + 1);
596 break;
597 case EXCLUDE_QUALIFIER:
598 SDDS_CopyString(&defi->exclude, ptr + 1);
599 break;
600 default:
601 break;
602 }
603 *ptr = '=';
604 if (code >= 0)
605 continue;
606 if (!SDDS_CopyString(defi->argv + defi->argc, argument[i])) {
607 fprintf(stderr, "error: problem copying argument string\n");
608 return NULL;
609 }
610 defi->argc += 1;
611 *ptr = 0;
612 strcat(s, argument[i]);
613 strcat(s, "=\"");
614 strcat(s, ptr + 1);
615 strcat(s, "\", ");
616 *ptr = '=';
617 }
618 if (!strstr(s, ", type=")) {
619 strcat(s, " type=\"double\", ");
620 SDDS_CopyString(defi->argv + defi->argc, "type=double");
621 defi->argc += 1;
622 }
623 strcat(s, "&end");
624 if (!SDDS_CopyString(&defi->text, s) || !SDDS_CopyString(&defi->equation, equation))
625 SDDS_Bomb("string copying failed (process_new_equation_definition)");
626 return (defi);
627}
628
629EVALUATE_DEFINITION *process_new_evaluate_definition(char **argument, long arguments) {
630 static char s[SDDS_MAXLINE];
631 long i;
633
634 if (!(defi = tmalloc(sizeof(*defi))))
635 SDDS_Bomb("memory allocation failure (process_new_evaluate_definition)");
636 defi->name = defi->text = defi->source = NULL;
637 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
638 case COLUMN_BASED:
639 defi->is_parameter = 0;
640 sprintf(s, "&column name=\"%s\", ", argument[1]);
641 break;
642 case PARAMETER_BASED:
643 defi->is_parameter = 1;
644 sprintf(s, "&parameter name=\"%s\", ", argument[1]);
645 break;
646 default:
647 fprintf(stderr, "error: column or parameter must be specified for definition\n");
648 return (NULL);
649 }
650 SDDS_CopyString(&defi->name, argument[1]);
651
652 defi->name = argument[1];
653 defi->source = argument[2];
654
655 for (i = 3; i < arguments; i++) {
656 strcat(s, ", ");
657 strcat(s, argument[i]);
658 }
659 if (!strstr(s, ", type=")) {
660 strcat(s, " type=double, ");
661 }
662 strcat(s, " &end");
663 if (!SDDS_CopyString(&defi->text, s))
664 SDDS_Bomb("string copying failed (process_new_evaluate_definition)");
665 return (defi);
666}
667
668SCAN_DEFINITION *process_new_scan_definition(char **argument, long arguments) {
669 static char s[SDDS_MAXLINE];
670 char *ptr;
671 long i;
672 SCAN_DEFINITION *defi;
673
674 if (!(defi = tmalloc(sizeof(*defi))))
675 SDDS_Bomb("memory allocation failure (process_new_scan_definition)");
676 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
677 case COLUMN_BASED:
678 defi->is_parameter = 0;
679 sprintf(s, "&column name=\"%s\", ", argument[1]);
680 break;
681 case PARAMETER_BASED:
682 defi->is_parameter = 1;
683 sprintf(s, "&parameter name=\"%s\", ", argument[1]);
684 break;
685 default:
686 fprintf(stderr, "error: column or parameter must be specified for scan\n");
687 return (NULL);
688 }
689 defi->new_name = argument[1];
690 defi->source = argument[2];
691 defi->sscanf_string = argument[3];
692 defi->edit = NULL;
693 for (i = 4; i < arguments; i++) {
694 if (!(ptr = strchr(argument[i], '=')))
695 return (NULL);
696 *ptr = 0;
697 if (strncasecmp(argument[i], "edit", strlen(argument[i])) == 0) {
698 /* pre-edit option */
699 SDDS_CopyString(&defi->edit, ptr + 1);
700 } else {
701 strcat(s, argument[i]);
702 strcat(s, "=\"");
703 strcat(s, ptr + 1);
704 strcat(s, "\", ");
705 }
706 }
707 if (!strstr(s, ", type="))
708 strcat(s, " type=\"double\", ");
709 strcat(s, "&end");
710 if (!SDDS_CopyString(&defi->text, s))
711 SDDS_Bomb("unable to copy text of scan definition (process_new_scan_definition)");
712 return (defi);
713}
714
715CAST_DEFINITION *process_new_cast_definition(char **argument, long arguments) {
716 CAST_DEFINITION *defi;
717
718 if (!(defi = tmalloc(sizeof(*defi))))
719 SDDS_Bomb("memory allocation failure (process_new_cast_definition)");
720 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
721 case COLUMN_BASED:
722 defi->isParameter = 0;
723 break;
724 case PARAMETER_BASED:
725 defi->isParameter = 1;
726 break;
727 default:
728 fprintf(stderr, "error: column or parameter must be specified for cast\n");
729 return (NULL);
730 }
731 defi->newName = argument[1];
732 defi->source = argument[2];
733 defi->newTypeName = argument[3];
734 if (strcmp(defi->newName, defi->source) == 0) {
735 fprintf(stderr, "error: can't cast something to the same name (sddsprocess)\n");
736 return NULL;
737 }
738 return (defi);
739}
740
741long complete_cast_definition(SDDS_DATASET *SDDSout, CAST_DEFINITION *defi,
742 SDDS_DATASET *SDDSin) {
743 char s[1024];
744
745 if (!(defi->newType = SDDS_IdentifyType(defi->newTypeName))) {
746 sprintf(s, "Unable to cast parameter %s to unknown type %s from column %s",
747 defi->newName, defi->newTypeName, defi->source);
748 SDDS_SetError(s);
749 return 0;
750 }
751 if (defi->isParameter) {
752 if (!SDDS_TransferParameterDefinition(SDDSout, SDDSout,
753 defi->source, defi->newName) ||
754 !SDDS_ChangeParameterInformation(SDDSout, "type", &defi->newType,
755 SDDS_BY_NAME, defi->newName)) {
756 sprintf(s, "Unable to cast parameter %s to type %s from column %s",
757 defi->newName, defi->newTypeName, defi->source);
758 SDDS_SetError(s);
759 return 0;
760 }
761 } else {
762 if (!SDDS_TransferColumnDefinition(SDDSout, SDDSout,
763 defi->source, defi->newName) ||
764 !SDDS_ChangeColumnInformation(SDDSout, "type", &defi->newType,
765 SDDS_BY_NAME, defi->newName)) {
766 sprintf(s, "Unable to cast column %s to type %s from column %s",
767 defi->newName, defi->newTypeName, defi->source);
768 SDDS_SetError(s);
769 return 0;
770 }
771 }
772 return 1;
773}
774
775NUMBERTEST_DEFINITION *process_new_numbertest_definition(char **argument, long arguments) {
776 static char s[SDDS_MAXLINE];
777 long i, j;
778
780#define NUMBERTEST_QUALIFIERS 2
781 static char *numbertestQualifier[NUMBERTEST_QUALIFIERS] = {
782 "invert",
783 "strict",
784 };
785 static unsigned long numbertestFlag[NUMBERTEST_QUALIFIERS] = {
786 NUMSCANFILTER_INVERT,
787 NUMSCANFILTER_STRICT,
788 };
789
790 if (!(defi = tmalloc(sizeof(*defi))))
791 SDDS_Bomb("memory allocation failure (process_new_numbertest_definition)");
792 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
793 case COLUMN_BASED:
794 defi->is_parameter = 0;
795 sprintf(s, "&column name=\"%s\", ", argument[1]);
796 break;
797 case PARAMETER_BASED:
798 defi->is_parameter = 1;
799 sprintf(s, "&parameter name=\"%s\", ", argument[1]);
800 break;
801 default:
802 fprintf(stderr, "error: column or parameter must be specified for numbertest\n");
803 return (NULL);
804 }
805 defi->name = argument[1];
806 defi->flags = 0;
807 for (i = 2; i < arguments; i++) {
808 switch (j = match_string(argument[i], numbertestQualifier, NUMBERTEST_QUALIFIERS, 0)) {
809 case -1:
810 fprintf(stderr, "error: unknown qualifer to -numberTest: %s\n", argument[i]);
811 exit(1);
812 break;
813 default:
814 defi->flags |= numbertestFlag[j];
815 break;
816 }
817 }
818 return (defi);
819}
820
821EDIT_DEFINITION *process_new_edit_definition(char **argument, long arguments, short reedit) {
822 static char s[SDDS_MAXLINE];
823 char *ptr;
824 long i, offset, hasType;
825 EDIT_DEFINITION *defi;
826
827 if (!(defi = tmalloc(sizeof(*defi))))
828 SDDS_Bomb("memory allocation failure (process_new_edit_definition)");
829 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
830 case COLUMN_BASED:
831 defi->is_parameter = 0;
832 sprintf(s, "&column name=\"%s\", ", argument[1]);
833 break;
834 case PARAMETER_BASED:
835 defi->is_parameter = 1;
836 sprintf(s, "&parameter name=\"%s\", ", argument[1]);
837 break;
838 default:
839 fprintf(stderr, "error: column or parameter must be specified for edit\n");
840 return (NULL);
841 }
842 defi->new_name = argument[1];
843 if (!reedit) {
844 defi->source = argument[2];
845 defi->edit_command = argument[3];
846 offset = 4;
847 } else {
848 defi->source = defi->new_name;
849 defi->edit_command = argument[2];
850 offset = 3;
851 }
852 if (arguments > offset) {
853 defi->argv = tmalloc(sizeof(*defi->argv) * (arguments - offset));
854 if (!SDDS_CopyStringArray(defi->argv, argument + offset, arguments - offset))
855 SDDS_Bomb("string array copy failed (process_new_edit_definition)");
856 defi->argc = arguments - offset;
857 } else {
858 defi->argc = 0;
859 defi->argv = NULL;
860 }
861 hasType = 0;
862 for (i = offset; i < arguments; i++) {
863 if (!(ptr = strchr(argument[i], '=')))
864 return (NULL);
865 *ptr = 0;
866 if (strcmp(argument[i], "type") == 0)
867 hasType = 1;
868 strcat(s, argument[i]);
869 strcat(s, "=\"");
870 strcat(s, ptr + 1);
871 strcat(s, "\", ");
872 }
873 if (!hasType)
874 strcat(s, " type=string &end");
875 else
876 strcat(s, " &end");
877 if (!SDDS_CopyString(&defi->text, s))
878 SDDS_Bomb("unable to copy text of edit definition (process_new_edit_definition)");
879 return (defi);
880}
881
882long edit_column_value(SDDS_DATASET *SDDS_dataset, char *target, char *source, char *edit_command) {
883 char **source_value;
884 long target_type, target_index, source_index;
885 int64_t i, rows;
886 static char s[SDDS_MAXLINE];
887
888 if ((source_index = SDDS_GetColumnIndex(SDDS_dataset, source)) < 0 ||
889 (target_index = SDDS_GetColumnIndex(SDDS_dataset, target)) < 0) {
890 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
891 return (0);
892 }
893 if (SDDS_GetColumnType(SDDS_dataset, source_index) != SDDS_STRING) {
894 fprintf(stderr, "error: source column %s has wrong type for editing--must be string\n", source);
895 return (0);
896 }
897 if ((target_type = SDDS_GetColumnType(SDDS_dataset, target_index)) != SDDS_STRING &&
898 target_type != SDDS_CHARACTER) {
899 fprintf(stderr, "error: target column %s has wrong type for editing--must be string or character\n", target);
900 return (0);
901 }
902
903 if ((rows = SDDS_CountRowsOfInterest(SDDS_dataset)) < 0) {
904 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
905 return (0);
906 }
907
908 if (!(source_value = SDDS_GetInternalColumn(SDDS_dataset, source))) {
909 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
910 return (0);
911 }
912
913 for (i = 0; i < rows; i++) {
914 if (!source_value[i])
915 s[0] = 0;
916 else
917 strcpy(s, source_value[i]);
918 if (!edit_string(s, edit_command)) {
919 fprintf(stderr, "error: unable to edit source string \"%s\" to make %s\n", source_value[i], target);
920 return (0);
921 }
922 if ((target_type == SDDS_STRING &&
923 !SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, i, target_index, s, -1)) ||
924 (target_type == SDDS_CHARACTER &&
925 !SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, i, target_index, s[0], -1))) {
926 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
927 return (0);
928 }
929 /*
930 if (source_value[i])
931 free(source_value[i]);
932 */
933 }
934 /*
935 free(source_value);
936 */
937 return (1);
938}
939
940long edit_parameter_value(SDDS_DATASET *SDDS_dataset, char *target, char *source, char *edit_command) {
941 char *source_value, **ptr;
942 long target_type, target_index, source_index;
943 static char s[SDDS_MAXLINE];
944
945 if ((source_index = SDDS_GetParameterIndex(SDDS_dataset, source)) < 0 ||
946 (target_index = SDDS_GetParameterIndex(SDDS_dataset, target)) < 0) {
947 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
948 return (0);
949 }
950 if (SDDS_GetParameterType(SDDS_dataset, source_index) != SDDS_STRING) {
951 fprintf(stderr, "error: source parameter %s has wrong type for editing--must be string\n", source);
952 return (0);
953 }
954 if ((target_type = SDDS_GetParameterType(SDDS_dataset, target_index)) != SDDS_STRING &&
955 target_type != SDDS_CHARACTER) {
956 fprintf(stderr, "error: target parameter %s has wrong type for editing--must be string or character\n", target);
957 return (0);
958 }
959
960 if (!(ptr = SDDS_GetParameter(SDDS_dataset, source, NULL))) {
961 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
962 return (0);
963 }
964 if (!(source_value = *ptr))
965 s[0] = 0;
966 else
967 strcpy(s, source_value);
968 if (!edit_string(s, edit_command)) {
969 fprintf(stderr, "error: unable to edit source string \"%s\" to make %s\n", source_value, target);
970 return (0);
971 }
972 if ((target_type == SDDS_STRING &&
973 !SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, s, -1)) ||
974 (target_type == SDDS_CHARACTER &&
975 !SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, s[0], -1))) {
976 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
977 return (0);
978 }
979 if (source_value)
980 free(source_value);
981 free(ptr);
982 return (1);
983}
984
985OUTPUT_REQUEST *process_output_request(char **argument, long arguments, OUTPUT_REQUEST *last_request) {
986 OUTPUT_REQUEST *request;
987 request = tmalloc(sizeof(*request));
988 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
989 case COLUMN_BASED:
990 request->parameter_output = 0;
991 break;
992 case PARAMETER_BASED:
993 request->parameter_output = 1;
994 break;
995 default:
996 fprintf(stderr, "error: column or parameter must be specified for output\n");
997 return (NULL);
998 }
999 argument++;
1000 arguments--;
1001
1002 request->fp = NULL;
1003 request->points = 0;
1004 request->counter = 0;
1005
1006 if (!(request->item[0] = determine_item_name(argument, last_request, 0)))
1007 return (NULL);
1008
1009 if (!(request->item[1] = determine_item_name(argument, last_request, 1)))
1010 return (NULL);
1011
1012 request->item[2] = request->item[3] = NULL;
1013 request->columns = 2;
1014
1015 if (arguments < 3)
1016 return (request);
1017
1018 request->columns = 3;
1019 if (!(request->item[2] = determine_item_name(argument, last_request, 2)))
1020 return (NULL);
1021
1022 if (arguments < 4)
1023 return (request);
1024
1025 request->columns = 4;
1026 if (!(request->item[3] = determine_item_name(argument, last_request, 3)))
1027 return (NULL);
1028
1029 return (request);
1030}
1031
1032char *determine_item_name(char **argument, OUTPUT_REQUEST *last_request, long index) {
1033 if (strcmp(argument[index], ".") == 0) {
1034 if (!last_request)
1035 return (NULL);
1036 return (last_request->item[index]);
1037 }
1038 return (argument[index]);
1039}
1040
1041void set_up_output(char *filename, OUTPUT_REQUEST *output, LABEL_PARAMETER *label_parameter, long label_parameters,
1042 long separate_pages, long announce_openings, SDDS_DATASET *SDDS_dataset) {
1043 COLUMN_DEFINITION **coldef;
1044 PARAMETER_DEFINITION **pardef, *pardefptr;
1045 long j;
1046 double param;
1047 char *mplTitle, *mplTopline;
1048
1049 output->fp = fopen_e(filename, "w", 0);
1050 if (announce_openings)
1051 fprintf(stderr, "file opened: %s\n", filename);
1052 if (!output->parameter_output) {
1053 coldef = (COLUMN_DEFINITION **)(output->definitions = tmalloc(sizeof(*coldef) * 4));
1054 coldef[0] = coldef[1] = coldef[2] = coldef[3] = NULL;
1055 if (!(coldef[0] = SDDS_GetColumnDefinition(SDDS_dataset, output->item[0])) ||
1056 !(coldef[1] = SDDS_GetColumnDefinition(SDDS_dataset, output->item[1])) ||
1057 (output->item[2] && !(coldef[2] = SDDS_GetColumnDefinition(SDDS_dataset, output->item[2]))) ||
1058 (output->item[3] && !(coldef[3] = SDDS_GetColumnDefinition(SDDS_dataset, output->item[3])))) {
1059 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
1060 exit(1);
1061 }
1062 fputs(coldef[0]->symbol ? coldef[0]->symbol : output->item[0], output->fp);
1063 if (coldef[0]->units && !is_blank(coldef[0]->units))
1064 fprintf(output->fp, " (%s)", coldef[0]->units);
1065 fprintf(output->fp, "\n%s", coldef[1]->symbol ? coldef[1]->symbol : output->item[1]);
1066 if (coldef[1]->units && !is_blank(coldef[1]->units))
1067 fprintf(output->fp, " (%s)", coldef[1]->units);
1068 if (label_parameters) {
1069 fputc('\n', output->fp);
1070 for (j = 0; j < label_parameters; j++) {
1071 if (!(pardefptr = SDDS_GetParameterDefinition(SDDS_dataset, label_parameter[j].name))) {
1072 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
1073 exit(1);
1074 }
1075 if (!SDDS_GetParameter(SDDS_dataset, label_parameter[j].name, &param)) {
1076 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
1077 exit(1);
1078 }
1079 fprintf(output->fp, "%s=", pardefptr->symbol ? pardefptr->symbol : label_parameter[j].name);
1080 SDDS_PrintTypedValue((void *)&param, 0, pardefptr->type,
1081 (label_parameter[j].format ? label_parameter[j].format : pardefptr->format_string), output->fp,
1082 0);
1083 if (pardefptr->units) {
1084 if (isdigit(pardefptr->units[0]))
1085 fputc(' ', output->fp);
1086 fprintf(output->fp, "%s%s", pardefptr->units, j == label_parameters - 1 ? "\n" : " ");
1087 } else
1088 fprintf(output->fp, "%s", j == label_parameters - 1 ? "\n" : " ");
1089 }
1090 } else {
1091 if (SDDS_GetParameterIndex(SDDS_dataset, "mplTitle") < 0)
1092 fprintf(output->fp, "\n%s vs %s\n",
1093 coldef[1]->description ? coldef[1]->description : (coldef[1]->symbol ? coldef[1]->symbol : output->item[1]),
1094 coldef[0]->description ? coldef[0]->description : (coldef[0]->symbol ? coldef[0]->symbol : output->item[0]));
1095 else {
1096 if (!SDDS_GetParameter(SDDS_dataset, "mplTitle", &mplTitle)) {
1097 SDDS_SetError("Unable to get value of parameter mplTitle");
1098 SDDS_PrintErrors(stderr, SDDS_EXIT_PrintErrors | SDDS_VERBOSE_PrintErrors);
1099 }
1100 fprintf(output->fp, "\n%s\n", mplTitle);
1101 free(mplTitle);
1102 }
1103 }
1104 } else {
1105 pardef = (PARAMETER_DEFINITION **)(output->definitions = tmalloc(sizeof(*pardef) * 4));
1106 pardef[0] = pardef[1] = pardef[2] = pardef[3] = NULL;
1107 if (!(pardef[0] = SDDS_GetParameterDefinition(SDDS_dataset, output->item[0])) ||
1108 !(pardef[1] = SDDS_GetParameterDefinition(SDDS_dataset, output->item[1])) ||
1109 (output->item[2] && !(pardef[2] = SDDS_GetParameterDefinition(SDDS_dataset, output->item[2]))) ||
1110 (output->item[3] && !(pardef[3] = SDDS_GetParameterDefinition(SDDS_dataset, output->item[3])))) {
1111 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
1112 exit(1);
1113 }
1114 fputs(pardef[0]->symbol ? pardef[0]->symbol : output->item[0], output->fp);
1115 if (pardef[0]->units && !is_blank(pardef[0]->units))
1116 fprintf(output->fp, " (%s)", pardef[0]->units);
1117 fprintf(output->fp, "\n%s", pardef[1]->symbol ? pardef[1]->symbol : output->item[1]);
1118 if (pardef[1]->units && !is_blank(pardef[1]->units))
1119 fprintf(output->fp, " (%s)", pardef[1]->units);
1120 if (label_parameters) {
1121 fputc('\n', output->fp);
1122 for (j = 0; j < label_parameters; j++) {
1123 if (!(pardefptr = SDDS_GetParameterDefinition(SDDS_dataset, label_parameter[j].name))) {
1124 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
1125 exit(1);
1126 }
1127 if (!SDDS_GetParameter(SDDS_dataset, label_parameter[j].name, &param)) {
1128 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
1129 exit(1);
1130 }
1131 fprintf(output->fp, "%s=", pardefptr->symbol ? pardefptr->symbol : label_parameter[j].name);
1132 SDDS_PrintTypedValue((void *)&param, 0, pardefptr->type,
1133 (label_parameter[j].format ? label_parameter[j].format : pardefptr->format_string), output->fp,
1134 0);
1135 if (pardefptr->units) {
1136 if (isdigit(pardefptr->units[0]))
1137 fputc(' ', output->fp);
1138 fprintf(output->fp, "%s%s", pardefptr->units, j == label_parameters - 1 ? "\n" : " ");
1139 } else
1140 fprintf(output->fp, "%s", j == label_parameters - 1 ? "\n" : " ");
1141 }
1142 } else {
1143 if (SDDS_GetParameterIndex(SDDS_dataset, "mplTitle") < 0)
1144 fprintf(output->fp, "\n%s vs %s\n",
1145 pardef[1]->description ? pardef[1]->description : (pardef[1]->symbol ? pardef[1]->symbol : output->item[1]),
1146 pardef[0]->description ? pardef[0]->description : (pardef[0]->symbol ? pardef[0]->symbol : output->item[0]));
1147 else {
1148 if (!SDDS_GetParameter(SDDS_dataset, "mplTitle", &mplTitle)) {
1149 SDDS_SetError("Unable to get value of parameter mplTitle");
1150 SDDS_PrintErrors(stderr, SDDS_EXIT_PrintErrors | SDDS_VERBOSE_PrintErrors);
1151 }
1152 fprintf(output->fp, "\n%s\n", mplTitle);
1153 free(mplTitle);
1154 }
1155 }
1156 }
1157 if (SDDS_GetParameterIndex(SDDS_dataset, "mplTopline") < 0) {
1158 fprintf(output->fp, "Data extracted from SDDS file %s", SDDS_dataset->layout.filename);
1159 if (separate_pages)
1160 fprintf(output->fp, ", page %" PRId32, SDDS_dataset->page_number);
1161 } else {
1162 if (!SDDS_GetParameter(SDDS_dataset, "mplTopline", &mplTopline)) {
1163 SDDS_SetError("Unable to get value of parameter mplTopline");
1164 SDDS_PrintErrors(stderr, SDDS_EXIT_PrintErrors | SDDS_VERBOSE_PrintErrors);
1165 }
1166 fprintf(output->fp, "%s", mplTopline);
1167 free(mplTopline);
1168 }
1169 fprintf(output->fp, "\n%-10" PRId64 "\n", SDDS_dataset->n_rows);
1170}
1171
1172#define DEBUG 0
1173
1174long process_column(SDDS_DATASET *Dataset, PROCESSING_DEFINITION *processing_ptr,
1175 double *result, char **stringResult, long warnings, int threads) {
1176 double *data, *indepData, *weightData;
1177 long i1, i2 = 0, i2save, mode;
1178 int64_t imin, imax;
1179 int64_t i, n_data, count;
1180 double min, max, top, base, point1, point2;
1181 double slope, intercept, variance;
1182 long returnValue, matchfound;
1183 char **stringData, **matchData;
1184 short *keep;
1185 double quartilePoint[2] = {25.0, 75.0}, quartileResult[2];
1186 double decilePoint[2] = {10.0, 90.0}, decileResult[2];
1187 double percentilePoint[2], percentileResult[2];
1188 char temp_str[256];
1189
1190 i1 = i2save = 0;
1191 matchfound = 0;
1192 mode = processing_ptr->mode;
1193#if DEBUG
1194 fprintf(stderr, "process_column: column=%s, mode=%s\n", processing_ptr->column_name,
1195 process_column_data[mode].name);
1196#endif
1197
1198 *stringResult = NULL;
1199 if ((n_data = SDDS_CountRowsOfInterest(Dataset)) <= 0) {
1200 if (mode != PROCESS_COLUMN_COUNT)
1201 *result = processing_ptr->defaultValue;
1202 else
1203 *result = n_data;
1204 return 1;
1205 }
1206 if (processing_ptr->lower_par && !SDDS_GetParameterAsDouble(Dataset, processing_ptr->lower_par,
1207 &processing_ptr->lowerLimit))
1208 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1209 if (processing_ptr->upper_par && !SDDS_GetParameterAsDouble(Dataset, processing_ptr->upper_par,
1210 &processing_ptr->upperLimit))
1211 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1212
1213 if (processing_ptr->head_par && !SDDS_GetParameterAsLong(Dataset, processing_ptr->head_par,
1214 &processing_ptr->head))
1215 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1216 if (processing_ptr->tail_par && !SDDS_GetParameterAsLong(Dataset, processing_ptr->tail_par,
1217 &processing_ptr->tail))
1218 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1219 if (processing_ptr->fhead_par && !SDDS_GetParameterAsDouble(Dataset, processing_ptr->fhead_par,
1220 &processing_ptr->fhead))
1221 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1222 if (processing_ptr->ftail_par && !SDDS_GetParameterAsDouble(Dataset, processing_ptr->ftail_par,
1223 &processing_ptr->ftail))
1224 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1225 if (processing_ptr->offset_par) {
1226 if (wild_match(processing_ptr->offset_par, "%s*")) {
1227 sprintf(temp_str, processing_ptr->offset_par, processing_ptr->column_name);
1228 if (!SDDS_GetParameterAsDouble(Dataset, temp_str,
1229 &processing_ptr->offset))
1230 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1231 } else if (!SDDS_GetParameterAsDouble(Dataset, processing_ptr->offset_par,
1232 &processing_ptr->offset))
1233 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1234 }
1235 if (processing_ptr->factor_par) {
1236 if (wild_match(processing_ptr->factor_par, "%s*")) {
1237 sprintf(temp_str, processing_ptr->factor_par, processing_ptr->column_name);
1238 if (!SDDS_GetParameterAsDouble(Dataset, temp_str,
1239 &processing_ptr->factor))
1240 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1241 } else if (!SDDS_GetParameterAsDouble(Dataset, processing_ptr->factor_par,
1242 &processing_ptr->factor))
1243 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1244 }
1245 if ((processing_ptr->flags & PROCESSING_INVERT_OFFSET) && (processing_ptr->flags & PROCESSING_OFFSET_GIVEN))
1246 processing_ptr->offset *=-1;
1247 if ((processing_ptr->flags & PROCESSING_FACTOR_GIVEN) && (processing_ptr->flags & PROCESSING_INVERT_FACTOR))
1248 processing_ptr->factor = 1/processing_ptr->factor;
1249
1250 if (!(data = SDDS_GetColumnInDoubles(Dataset, processing_ptr->column_name)))
1251 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1252 indepData = weightData = NULL;
1253 stringData = matchData = NULL;
1254
1255 if (processing_ptr->weightBy && !(weightData = SDDS_GetColumnInDoubles(Dataset, processing_ptr->weightBy)))
1256 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1257 if (processing_ptr->functionOf &&
1258 processing_ptr->outputType != SDDS_STRING &&
1259 !(indepData = SDDS_GetColumnInDoubles(Dataset, processing_ptr->functionOf)))
1260 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1261 if (processing_ptr->functionOf &&
1262 processing_ptr->outputType == SDDS_STRING &&
1263 !(stringData = SDDS_GetColumn(Dataset, processing_ptr->functionOf)))
1264 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1265
1266 keep = NULL;
1267 if (processing_ptr->flags & (PROCESSING_LOLIM_GIVEN | PROCESSING_UPLIM_GIVEN | PROCESSING_TAIL_GIVEN | PROCESSING_HEAD_GIVEN | PROCESSING_FTAIL_GIVEN | PROCESSING_FHEAD_GIVEN | PROCESSING_MATCHCOLUMN_GIVEN | PROCESSING_TOPLIM_GIVEN | PROCESSING_BOTLIM_GIVEN)) {
1268 keep = tmalloc(sizeof(*keep) * n_data);
1269 for (i = 0; i < n_data; i++)
1270 keep[i] = 1;
1271 }
1272 if (processing_ptr->flags & PROCESSING_MATCHCOLUMN_GIVEN) {
1273 if (!(matchData = SDDS_GetColumn(Dataset, processing_ptr->match_column)))
1274 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1275 for (i = 0; i < n_data; i++)
1276 keep[i] = 0;
1277 for (i = 0; i < n_data; i++) {
1278 if (wild_match(matchData[i], processing_ptr->match_value)) {
1279 matchfound = 1;
1280 keep[i] = 1;
1281 }
1282 }
1283 for (i = 0; i < n_data; i++)
1284 free(matchData[i]);
1285 free(matchData);
1286 if (!matchfound) {
1287 if (warnings)
1288 fprintf(stderr, "Warning: no values in column %s match %s.\n",
1289 processing_ptr->match_column, processing_ptr->match_value);
1290 free(keep);
1291 free(data);
1292 *result = processing_ptr->defaultValue;
1293 return 1;
1294 }
1295 }
1296 if (processing_ptr->flags & PROCESSING_LOLIM_GIVEN && indepData) {
1297#if DEBUG
1298 fprintf(stderr, "lower limit processing: value %e\n", processing_ptr->lowerLimit);
1299#endif
1300 for (i = 0; i < n_data; i++)
1301 if (processing_ptr->lowerLimit > indepData[i])
1302 keep[i] = 0;
1303 }
1304
1305 if (processing_ptr->flags & PROCESSING_UPLIM_GIVEN && indepData) {
1306#if DEBUG
1307 fprintf(stderr, "upper limit processing: value %e\n", processing_ptr->upperLimit);
1308#endif
1309 for (i = 0; i < n_data; i++) {
1310 if (processing_ptr->upperLimit < indepData[i])
1311 keep[i] = 0;
1312 if (isinf(indepData[i]) || isnan(indepData[i]))
1313 keep[i] = 0;
1314 }
1315 }
1316
1317 if (processing_ptr->flags & PROCESSING_TOPLIM_GIVEN) {
1318 for (i = 0; i < n_data; i++) {
1319 if (processing_ptr->topLimit < data[i])
1320 keep[i] = 0;
1321 if (isinf(data[i]) || isnan(data[i]))
1322 keep[i] = 0;
1323 }
1324 }
1325
1326 if (processing_ptr->flags & PROCESSING_BOTLIM_GIVEN) {
1327 for (i = 0; i < n_data; i++)
1328 if (processing_ptr->bottomLimit > data[i])
1329 keep[i] = 0;
1330 }
1331
1332 if (processing_ptr->flags & PROCESSING_HEAD_GIVEN) {
1333 count = 0;
1334#if DEBUG
1335 fprintf(stderr, "head processing: %ld points\n", processing_ptr->head);
1336#endif
1337 if (processing_ptr->head > 0) {
1338 /* keep first head points */
1339 for (i = 0; i < n_data && count < processing_ptr->head; i++)
1340 if (keep[i])
1341 count++;
1342 for (; i < n_data; i++)
1343 keep[i] = 0;
1344 } else {
1345 /* kill first -head points */
1346 for (i = 0; i < n_data && count < -processing_ptr->head; i++)
1347 if (keep[i]) {
1348 count++;
1349 keep[i] = 0;
1350 }
1351 }
1352 }
1353
1354 if (processing_ptr->flags & PROCESSING_FHEAD_GIVEN) {
1355 long head;
1356 count = 0;
1357 head = fabs(n_data * processing_ptr->fhead + 0.5);
1358 if (processing_ptr->fhead > 0) {
1359 for (i = 0; i < n_data && count < head; i++)
1360 if (keep[i])
1361 count++;
1362 for (; i < n_data; i++)
1363 keep[i] = 0;
1364 } else
1365 for (i = 0; i < n_data && count < head; i++)
1366 if (keep[i]) {
1367 count++;
1368 keep[i] = 0;
1369 }
1370 }
1371
1372 if (processing_ptr->flags & PROCESSING_TAIL_GIVEN) {
1373 count = 0;
1374#if DEBUG
1375 fprintf(stderr, "tail processing: %ld points\n", processing_ptr->tail);
1376#endif
1377 if (processing_ptr->tail > 0) {
1378 for (i = n_data - 1; i >= 0 && count < processing_ptr->tail; i--)
1379 if (keep[i])
1380 count++;
1381 for (; i >= 0; i--)
1382 keep[i] = 0;
1383 } else
1384 for (i = n_data - 1; i >= 0 && count < -processing_ptr->tail; i--)
1385 if (keep[i]) {
1386 count++;
1387 keep[i] = 0;
1388 }
1389 }
1390
1391 if (processing_ptr->flags & PROCESSING_FTAIL_GIVEN) {
1392 long tail;
1393 count = 0;
1394 tail = fabs(processing_ptr->ftail * n_data + 0.5);
1395 if (processing_ptr->ftail > 0) {
1396 for (i = n_data - 1; i >= 0 && count < tail; i--)
1397 if (keep[i])
1398 count++;
1399 for (; i >= 0; i--)
1400 keep[i] = 0;
1401 } else
1402 for (i = n_data - 1; i >= 0 && count < tail; i--)
1403 if (keep[i]) {
1404 count++;
1405 keep[i] = 0;
1406 }
1407 }
1408
1409 if (keep) {
1410 int64_t j;
1411 for (i = j = 0; i < n_data; i++) {
1412 if (keep[i]) {
1413 if (i != j) {
1414 data[j] = data[i];
1415 if (indepData)
1416 indepData[j] = indepData[i];
1417 if (stringData) {
1418 free(stringData[j]);
1419 stringData[j] = stringData[i];
1420 stringData[i] = NULL;
1421 }
1422 if (weightData)
1423 weightData[j] = weightData[i];
1424 }
1425 j++;
1426 }
1427 }
1428 n_data = j;
1429#if DEBUG
1430 fprintf(stderr, "%" PRId64 " points kept\n", n_data);
1431#endif
1432 }
1433 if (n_data == 0) {
1434 free(data);
1435 if (indepData)
1436 free(indepData);
1437 if (weightData)
1438 free(weightData);
1439 if (keep)
1440 free(keep);
1441 if (warnings)
1442 fprintf(stderr, "warning: no matches found");
1443 if (mode != PROCESS_COLUMN_COUNT) {
1444 *result = processing_ptr->defaultValue;
1445 *stringResult = NULL;
1446 return 1;
1447 } else {
1448 *result = 0;
1449 *stringResult = NULL;
1450 return 1;
1451 }
1452 }
1453
1454 if (processing_ptr->flags & PROCESSING_OFFSET_GIVEN) {
1455#if DEBUG
1456 fprintf(stderr, "offsetting by %f\n", processing_ptr->offset);
1457#endif
1458 for (i = 0; i < n_data; i++)
1459 data[i] += processing_ptr->offset;
1460 }
1461
1462 if (processing_ptr->flags & PROCESSING_FACTOR_GIVEN) {
1463#if DEBUG
1464 fprintf(stderr, "multiplying by %f\n", processing_ptr->factor);
1465#endif
1466 for (i = 0; i < n_data; i++)
1467 data[i] *= processing_ptr->factor;
1468 }
1469
1470#if DEBUG
1471 fprintf(stderr, "data points:\n");
1472 for (i = 0; i < n_data; i++)
1473 fprintf(stderr, "%e%c", data[i], (i + 1) % 8 == 0 ? '\n' : ' ');
1474 fputc('\n', stderr);
1475#endif
1476
1477 *result = 0;
1478 returnValue = 1;
1479 switch (mode) {
1480 case PROCESS_COLUMN_ZEROCROSSING:
1481 for (i = 0; i < n_data - 1; i++) {
1482 if (data[i] == 0)
1483 break;
1484 if ((data[i] < 0 && data[i + 1] >= 0) || (data[i] > 0 && data[i + 1] <= 0))
1485 break;
1486 }
1487 if (i != n_data - 1) {
1488 if (indepData) {
1489 if (data[i] == 0)
1490 *result = indepData[i];
1491 else
1492 *result = indepData[i] + (indepData[i + 1] - indepData[i]) / (data[i + 1] - data[i]) * (-data[i]);
1493 }
1494 if (stringData) {
1495 *stringResult = stringData[i];
1496 stringData[i] = NULL;
1497 }
1498 } else
1499 returnValue = 0;
1500 break;
1501 case PROCESS_COLUMN_MEAN:
1502 if (weightData)
1503 *result = weightedAverageThreaded(data, weightData, n_data, threads);
1504 else
1505 *result = arithmeticAverageThreaded(data, n_data, threads);
1506 break;
1507 case PROCESS_COLUMN_RMS:
1508 if (weightData)
1509 *result = weightedRMSThreaded(data, weightData, n_data, threads);
1510 else
1511 *result = rmsValueThreaded(data, n_data, threads);
1512 break;
1513 case PROCESS_COLUMN_SUM:
1514 if (weightData) {
1515 double sum;
1516 for (i = sum = 0; i < n_data; i++)
1517 sum += data[i] * weightData[i];
1518 *result = sum;
1519 } else
1520 *result = arithmeticAverageThreaded(data, n_data, threads) * n_data;
1521 break;
1522 case PROCESS_COLUMN_PRODUCT:
1523 if (weightData) {
1524 double product = 1;
1525 for (i = 0; i < n_data; i++)
1526 product *= data[i] * weightData[i];
1527 *result = product;
1528 } else {
1529 double product = 1;
1530 for (i = 0; i < n_data; i++)
1531 product *= data[i];
1532 *result = product;
1533 }
1534 break;
1535 case PROCESS_COLUMN_STAND_DEV:
1536 if (weightData)
1537 *result = weightedStDevThreaded(data, weightData, n_data, threads);
1538 else
1539 *result = standardDeviationThreaded(data, n_data, threads);
1540 break;
1541 case PROCESS_COLUMN_SIGMA:
1542 if (weightData)
1543 *result = weightedStDevThreaded(data, weightData, n_data, threads);
1544 else
1545 *result = standardDeviationThreaded(data, n_data, threads);
1546 *result /= sqrt(1.0 * n_data);
1547 break;
1548 case PROCESS_COLUMN_MAD:
1549 if (weightData)
1550 *result = weightedMADThreaded(data, weightData, n_data, threads);
1551 else
1552 *result = meanAbsoluteDeviationThreaded(data, n_data, threads);
1553 break;
1554 case PROCESS_COLUMN_SIGNEDSMALLEST:
1555 imin = 0;
1556 for (i = 1; i < n_data; i++)
1557 if (fabs(data[imin]) > fabs(data[i]))
1558 imin = i;
1559 *result = data[imin];
1560 if (processing_ptr->flags & PROCESSING_POSITION_GIVEN) {
1561 if (indepData)
1562 *result = indepData[imin];
1563 if (stringData) {
1564 *stringResult = stringData[imin];
1565 stringData[imin] = NULL;
1566 }
1567 }
1568 break;
1569 case PROCESS_COLUMN_SIGNEDLARGEST:
1570 imax = 0;
1571 for (i = 1; i < n_data; i++)
1572 if (fabs(data[imax]) < fabs(data[i]))
1573 imax = i;
1574 *result = data[imax];
1575 if (processing_ptr->flags & PROCESSING_POSITION_GIVEN) {
1576 if (indepData)
1577 *result = indepData[imax];
1578 if (stringData) {
1579 *stringResult = stringData[imax];
1580 stringData[imax] = NULL;
1581 }
1582 }
1583 break;
1584 case PROCESS_COLUMN_SMALLEST:
1585 case PROCESS_COLUMN_LARGEST:
1586 for (i = 0; i < n_data; i++)
1587 data[i] = fabs(data[i]);
1588 if (!index_min_max(&imin, &imax, data, n_data))
1589 returnValue = 0;
1590 else {
1591 switch (mode) {
1592 case PROCESS_COLUMN_SMALLEST:
1593 *result = data[i1 = imin];
1594 break;
1595 case PROCESS_COLUMN_LARGEST:
1596 *result = data[i1 = imax];
1597 break;
1598 }
1599 if (processing_ptr->flags & PROCESSING_POSITION_GIVEN) {
1600 if (indepData)
1601 *result = indepData[i1];
1602 if (stringData) {
1603 *stringResult = stringData[i1];
1604 stringData[i1] = NULL;
1605 }
1606 }
1607 }
1608 break;
1609 case PROCESS_COLUMN_MINIMUM:
1610 case PROCESS_COLUMN_MAXIMUM:
1611 case PROCESS_COLUMN_SPREAD:
1612 if (!index_min_max(&imin, &imax, data, n_data))
1613 returnValue = 0;
1614 else {
1615 min = data[imin];
1616 max = data[imax];
1617 switch (mode) {
1618 case PROCESS_COLUMN_MINIMUM:
1619 i1 = imin;
1620 *result = min;
1621 break;
1622 case PROCESS_COLUMN_MAXIMUM:
1623 i1 = imax;
1624 *result = max;
1625 break;
1626 case PROCESS_COLUMN_SMALLEST:
1627 if (fabs(min) < fabs(max)) {
1628 i1 = imin;
1629 *result = fabs(min);
1630 } else {
1631 i1 = imax;
1632 *result = fabs(max);
1633 }
1634 break;
1635 case PROCESS_COLUMN_LARGEST:
1636 if (fabs(min) > fabs(max)) {
1637 i1 = imin;
1638 *result = fabs(min);
1639 } else {
1640 i1 = imax;
1641 *result = fabs(max);
1642 }
1643 break;
1644 case PROCESS_COLUMN_SPREAD:
1645 *result = max - min;
1646 break;
1647 }
1648 if (processing_ptr->flags & PROCESSING_POSITION_GIVEN) {
1649 if (indepData)
1650 *result = indepData[i1];
1651 if (stringData) {
1652 *stringResult = stringData[i1];
1653 stringData[i1] = NULL;
1654 }
1655 }
1656 }
1657 break;
1658 case PROCESS_COLUMN_FIRST:
1659 *result = data[0];
1660 break;
1661 case PROCESS_COLUMN_LAST:
1662 *result = data[n_data - 1];
1663 break;
1664 case PROCESS_COLUMN_COUNT:
1665 *result = n_data;
1666 break;
1667 case PROCESS_COLUMN_MEDIAN:
1668 if (compute_median(result, data, n_data) <= 0)
1669 returnValue = 0;
1670 break;
1671 case PROCESS_COLUMN_MODE:
1672 if (processing_ptr->flags & PROCESSING_BINSIZE_GIVEN) {
1673 if (computeMode(result, data, n_data, processing_ptr->binSize, 0) <= 0)
1674 returnValue = 0;
1675 } else if (computeMode(result, data, n_data, 0, 100) <= 0)
1676 returnValue = 0;
1677 break;
1678 case PROCESS_COLUMN_BASELEVEL:
1679 case PROCESS_COLUMN_TOPLEVEL:
1680 case PROCESS_COLUMN_AMPLITUDE:
1681 case PROCESS_COLUMN_RISETIME:
1682 case PROCESS_COLUMN_FALLTIME:
1683 case PROCESS_COLUMN_FWHA:
1684 case PROCESS_COLUMN_FWTA:
1685 case PROCESS_COLUMN_CENTER:
1686 case PROCESS_COLUMN_FWHM:
1687 case PROCESS_COLUMN_FWTM:
1688 if (!findTopBaseLevels(&top, &base, data, n_data, 50, 2.0) ||
1689 !index_min_max(&imin, &imax, data, n_data))
1690 returnValue = 0;
1691 else {
1692 if ((top - base) < 0.75 * (data[imax] - base))
1693 top = data[imax];
1694 switch (mode) {
1695 case PROCESS_COLUMN_BASELEVEL:
1696 *result = base;
1697 break;
1698 case PROCESS_COLUMN_TOPLEVEL:
1699 *result = top;
1700 break;
1701 case PROCESS_COLUMN_AMPLITUDE:
1702 *result = top - base;
1703 break;
1704 case PROCESS_COLUMN_RISETIME:
1705 if ((i1 = findCrossingPoint(0, data, n_data, base + (top - base) * 0.1, 1, indepData, &point1)) < 0 ||
1706 (i2 = findCrossingPoint(i1, data, n_data, base + (top - base) * 0.9, 1, indepData, &point2)) < 0)
1707 returnValue = 0;
1708 else
1709 *result = point2 - point1;
1710 break;
1711 case PROCESS_COLUMN_FALLTIME:
1712 if ((i1 = findCrossingPoint(0, data, n_data, base + (top - base) * 0.9, -1, indepData, &point1)) < 0 ||
1713 (i2 = findCrossingPoint(i1, data, n_data, base + (top - base) * 0.1, -1, indepData, &point2)) < 0)
1714 returnValue = 0;
1715 else
1716 *result = point2 - point1;
1717 break;
1718 case PROCESS_COLUMN_FWHA:
1719 if ((i1 = findCrossingPoint(0, data, n_data, base + (top - base) * 0.5, 1, indepData, &point1)) < 0 ||
1720 (i2 = i2save = findCrossingPoint(i1, data, n_data, base + (top - base) * 0.9, -1, NULL, NULL)) < 0 ||
1721 (i2 = findCrossingPoint(i2, data, n_data, base + (top - base) * 0.5, -1, indepData, &point2)) < 0) {
1722 if (warnings) {
1723 fprintf(stderr, "warning: couldn't find crossing point for FWHA of %s\n",
1724 processing_ptr->column_name);
1725 fprintf(stderr, "top, base = %e, %e min, max = %e, %e\n", top, base,
1726 data[imin], data[imax]);
1727 if (i1 > 0)
1728 fprintf(stderr, "#1: %ld, (%e, %e)\n",
1729 i1, indepData[i1], data[i1]);
1730 if (i2save > 0)
1731 fprintf(stderr, "#2: %ld, (%e, %e)\n",
1732 i2save, indepData[i2save], data[i2save]);
1733 if (i2 > 0)
1734 fprintf(stderr, "#2a: %ld, (%e, %e)\n",
1735 i2, indepData[i2], data[i2]);
1736 }
1737 if ((i1 = findCrossingPoint(0, data, n_data, base + (top - base) * 0.5, 1, indepData, &point1)) < 0 ||
1738 (i2 = i2save = findCrossingPoint(i1, data, n_data, base + (top - base) * 0.9, 1, NULL, NULL)) < 0 ||
1739 (i2 = findCrossingPoint(i2, data, n_data, base + (top - base) * 0.5, -1, indepData, &point2)) < 0) {
1740 returnValue = 0;
1741 } else {
1742 *result = point2 - point1;
1743 }
1744 } else
1745 *result = point2 - point1;
1746 break;
1747 case PROCESS_COLUMN_FWTA:
1748 if ((i1 = findCrossingPoint(0, data, n_data, base + (top - base) * 0.1, 1, indepData, &point1)) < 0 ||
1749 (i2 = findCrossingPoint(i1, data, n_data, base + (top - base) * 0.9, -1, NULL, NULL)) < 0 ||
1750 (i2 = findCrossingPoint(i2, data, n_data, base + (top - base) * 0.1, -1, indepData, &point2)) < 0) {
1751 if ((i1 = findCrossingPoint(0, data, n_data, base + (top - base) * 0.1, 1, indepData, &point1)) < 0 ||
1752 (i2 = findCrossingPoint(i1, data, n_data, base + (top - base) * 0.9, 1, NULL, NULL)) < 0 ||
1753 (i2 = findCrossingPoint(i2, data, n_data, base + (top - base) * 0.1, -1, indepData, &point2)) < 0) {
1754 returnValue = 0;
1755 } else {
1756 *result = point2 - point1;
1757 }
1758 } else
1759 *result = point2 - point1;
1760 break;
1761 case PROCESS_COLUMN_FWHM:
1762 if ((i1 = findCrossingPoint(0, data, n_data, top * 0.5, 1, indepData, &point1)) < 0 ||
1763 (i2 = i2save = findCrossingPoint(i1, data, n_data, top * 0.9, -1, NULL, NULL)) < 0 ||
1764 (i2 = findCrossingPoint(i2, data, n_data, top * 0.5, -1, indepData, &point2)) < 0) {
1765 if (warnings) {
1766 fprintf(stderr, "warning: couldn't find crossing point for FWHM of %s\n",
1767 processing_ptr->column_name);
1768 fprintf(stderr, "top, base = %e, %e\n", top, base);
1769 if (i1 > 0)
1770 fprintf(stderr, "#1: %ld, (%e, %e)\n",
1771 i1, indepData[i1], data[i1]);
1772 if (i2save > 0)
1773 fprintf(stderr, "#2: %ld, (%e, %e)\n",
1774 i2save, indepData[i2save], data[i2save]);
1775 }
1776 if ((i1 = findCrossingPoint(0, data, n_data, top * 0.5, 1, indepData, &point1)) < 0 ||
1777 (i2 = i2save = findCrossingPoint(i1, data, n_data, top * 0.9, 1, NULL, NULL)) < 0 ||
1778 (i2 = findCrossingPoint(i2, data, n_data, top * 0.5, -1, indepData, &point2)) < 0) {
1779 returnValue = 0;
1780 } else {
1781 *result = point2 - point1;
1782 }
1783 } else
1784 *result = point2 - point1;
1785 break;
1786 case PROCESS_COLUMN_FWTM:
1787 if ((i1 = findCrossingPoint(0, data, n_data, top * 0.1, 1, indepData, &point1)) < 0 ||
1788 (i2 = findCrossingPoint(i1, data, n_data, top * 0.9, -1, NULL, NULL)) < 0 ||
1789 (i2 = findCrossingPoint(i2, data, n_data, top * 0.1, -1, indepData, &point2)) < 0) {
1790 if ((i1 = findCrossingPoint(0, data, n_data, top * 0.1, 1, indepData, &point1)) < 0 ||
1791 (i2 = findCrossingPoint(i1, data, n_data, top * 0.9, 1, NULL, NULL)) < 0 ||
1792 (i2 = findCrossingPoint(i2, data, n_data, top * 0.1, -1, indepData, &point2)) < 0) {
1793 returnValue = 0;
1794 } else {
1795 *result = point2 - point1;
1796 }
1797 } else
1798 *result = point2 - point1;
1799 break;
1800 case PROCESS_COLUMN_CENTER:
1801 if ((i1 = findCrossingPoint(0, data, n_data, base + (top - base) * 0.5, 1, indepData, &point1)) < 0 ||
1802 (i2 = findCrossingPoint(i1, data, n_data, base + (top - base) * 0.9, -1, NULL, NULL)) < 0 ||
1803 (i2 = findCrossingPoint(i2, data, n_data, base + (top - base) * 0.5, -1, indepData, &point2)) < 0) {
1804 if ((i1 = findCrossingPoint(0, data, n_data, base + (top - base) * 0.5, 1, indepData, &point1)) < 0 ||
1805 (i2 = findCrossingPoint(i1, data, n_data, base + (top - base) * 0.9, 1, NULL, NULL)) < 0 ||
1806 (i2 = findCrossingPoint(i2, data, n_data, base + (top - base) * 0.5, -1, indepData, &point2)) < 0) {
1807 returnValue = 0;
1808 } else {
1809 *result = (point1 + point2) / 2;
1810 }
1811 } else
1812 *result = (point1 + point2) / 2;
1813 break;
1814 }
1815 }
1816 break;
1817 case PROCESS_COLUMN_SLOPE:
1818 case PROCESS_COLUMN_INTERCEPT:
1819 case PROCESS_COLUMN_LFSD:
1820 if (!unweightedLinearFit(indepData, data, n_data, &slope, &intercept, &variance))
1821 returnValue = 0;
1822 else
1823 switch (mode) {
1824 case PROCESS_COLUMN_SLOPE:
1825 *result = slope;
1826 break;
1827 case PROCESS_COLUMN_INTERCEPT:
1828 *result = intercept;
1829 break;
1830 case PROCESS_COLUMN_LFSD:
1831 *result = sqrt(variance);
1832 break;
1833 }
1834 break;
1835 case PROCESS_COLUMN_INTEGRAL:
1836 trapazoidIntegration(indepData, data, n_data, result);
1837 break;
1838 case PROCESS_COLUMN_GMINTEGRAL:
1839 GillMillerIntegration1(indepData, data, n_data, result);
1840 break;
1841 case PROCESS_COLUMN_QRANGE:
1842 if (!compute_percentiles(quartileResult, quartilePoint, 2, data, n_data))
1843 returnValue = 0;
1844 else
1845 *result = quartileResult[1] - quartileResult[0];
1846 break;
1847 case PROCESS_COLUMN_DRANGE:
1848 if (!compute_percentiles(decileResult, decilePoint, 2, data, n_data))
1849 returnValue = 0;
1850 else
1851 *result = decileResult[1] - decileResult[0];
1852 break;
1853 case PROCESS_COLUMN_PERCENTILE:
1854 if (!compute_percentiles(percentileResult, &processing_ptr->percentileLevel, 1, data, n_data))
1855 returnValue = 0;
1856 else {
1857 *result = percentileResult[0];
1858 returnValue = 1;
1859 }
1860 break;
1861 case PROCESS_COLUMN_PRANGE:
1862 percentilePoint[1] = 50 + processing_ptr->percentileLevel / 2.0;
1863 percentilePoint[0] = 50 - processing_ptr->percentileLevel / 2.0;
1864 if (!compute_percentiles(percentileResult, percentilePoint, 2, data, n_data))
1865 returnValue = 0;
1866 else {
1867 *result = percentileResult[1] - percentileResult[0];
1868 returnValue = 1;
1869 }
1870 break;
1871 case PROCESS_COLUMN_CORRELATION:
1872 *result = linearCorrelationCoefficient(data, indepData, NULL, NULL, n_data, NULL);
1873 returnValue = 1;
1874 break;
1875 default:
1876 returnValue = 0;
1877 break;
1878 }
1879
1880 free(data);
1881 if (indepData)
1882 free(indepData);
1883 if (weightData)
1884 free(weightData);
1885 if (keep)
1886 free(keep);
1887 if (stringData) {
1888 for (i = 0; i < n_data; i++)
1889 if (stringData[i])
1890 free(stringData[i]);
1891 free(stringData);
1892 }
1893 if (!returnValue) {
1894 if (warnings)
1895 fprintf(stderr, "warning: processing of %s with mode %s failed--value %e returned\n",
1896 processing_ptr->column_name,
1897 process_column_name[processing_ptr->mode],
1898 processing_ptr->defaultValue);
1899 *result = processing_ptr->defaultValue;
1900 *stringResult = NULL;
1901 }
1902 return 1;
1903}
1904
1905char *process_string_column(SDDS_DATASET *Dataset, PROCESSING_DEFINITION *processing_ptr, long warnings) {
1906 char **data, *result, **matchData;
1907 long mode, matchfound;
1908 int64_t i, n_data, count;
1909 short *keep;
1910
1911 mode = processing_ptr->mode;
1912 matchData = NULL;
1913 matchfound = 0;
1914
1915 if ((n_data = SDDS_CountRowsOfInterest(Dataset)) <= 0 && mode != PROCESS_COLUMN_COUNT)
1916 return NULL;
1917
1918 if (!(data = SDDS_GetColumn(Dataset, processing_ptr->column_name)))
1919 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1920
1921 keep = NULL;
1922 if (processing_ptr->flags & (PROCESSING_TAIL_GIVEN | PROCESSING_HEAD_GIVEN |
1923 PROCESSING_FTAIL_GIVEN | PROCESSING_FHEAD_GIVEN |
1924 PROCESSING_MATCHCOLUMN_GIVEN)) {
1925 keep = tmalloc(sizeof(*keep) * n_data);
1926 for (i = 0; i < n_data; i++)
1927 keep[i] = 1;
1928 }
1929
1930 if (processing_ptr->flags & PROCESSING_MATCHCOLUMN_GIVEN) {
1931 if (!(matchData = SDDS_GetColumn(Dataset, processing_ptr->match_column)))
1932 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
1933 for (i = 0; i < n_data; i++)
1934 keep[i] = 0;
1935 for (i = 0; i < n_data; i++) {
1936 if (wild_match(matchData[i], processing_ptr->match_value)) {
1937 matchfound = 1;
1938 keep[i] = 1;
1939 }
1940 }
1941 for (i = 0; i < n_data; i++)
1942 free(matchData[i]);
1943 free(matchData);
1944 if (!matchfound) {
1945 if (warnings)
1946 fprintf(stderr, "Warning: no values in column %s match %s.\n",
1947 processing_ptr->match_column, processing_ptr->match_value);
1948 free(keep);
1949 for (i = 0; i < n_data; i++)
1950 free(data[i]);
1951 free(data);
1952 SDDS_CopyString(&result, "_NoResultFound_");
1953 return result;
1954 }
1955 }
1956 if (processing_ptr->flags & PROCESSING_HEAD_GIVEN) {
1957 count = 0;
1958 for (i = 0; i < n_data && count < processing_ptr->head; i++)
1959 if (keep[i])
1960 count++;
1961 for (; i < n_data; i++)
1962 keep[i] = 0;
1963 }
1964
1965 if (processing_ptr->flags & PROCESSING_FHEAD_GIVEN) {
1966 long head;
1967 count = 0;
1968 head = n_data * processing_ptr->fhead + 0.5;
1969 for (i = 0; i < n_data && count < head; i++)
1970 if (keep[i])
1971 count++;
1972 for (; i < n_data; i++)
1973 keep[i] = 0;
1974 }
1975
1976 if (processing_ptr->flags & PROCESSING_TAIL_GIVEN) {
1977 count = 0;
1978 for (i = n_data - 1; i >= 0 && count < processing_ptr->tail; i--)
1979 if (keep[i])
1980 count++;
1981 for (; i >= 0; i--)
1982 keep[i] = 0;
1983 }
1984
1985 if (processing_ptr->flags & PROCESSING_FTAIL_GIVEN) {
1986 long tail;
1987 count = 0;
1988 tail = processing_ptr->ftail * n_data + 0.5;
1989 for (i = n_data - 1; i >= 0 && count < tail; i--)
1990 if (keep[i])
1991 count++;
1992 for (; i >= 0; i--)
1993 keep[i] = 0;
1994 }
1995
1996 if (keep) {
1997 int64_t j;
1998 for (i = j = 0; i < n_data; i++) {
1999 if (keep[i]) {
2000 if (i != j)
2001 data[j] = data[i];
2002 j++;
2003 } else
2004 free(data[i]);
2005 }
2006 n_data = j;
2007 }
2008 if (n_data > 0) {
2009 switch (mode) {
2010 case PROCESS_COLUMN_FIRST:
2011 SDDS_CopyString(&result, data[0]);
2012 break;
2013 case PROCESS_COLUMN_LAST:
2014 SDDS_CopyString(&result, data[n_data - 1]);
2015 break;
2016 default:
2017 SDDS_Bomb("invalid processing mode for string data (sddsprocess)");
2018 exit(1);
2019 break;
2020 }
2021 } else {
2022 if (warnings)
2023 fprintf(stderr, "warning, no matches found.");
2024 SDDS_CopyString(&result, "_NoResultFound_");
2025 }
2026 for (i = 0; i < n_data; i++)
2027 free(data[i]);
2028 free(data);
2029 if (keep)
2030 free(keep);
2031 return result;
2032}
2033
2034static char *PROCESSING_USAGE =
2035 " [-process=<column-name>,<analysis-name>,<result-name>[,description=<string>][,symbol=<string>][,weightBy=<column-name>]\n\
2036 [,match=<column-name>,value=<match-string>]\n\
2037 [,head=<number>][,tail=<number>][fhead=<fraction>][ftail=<fraction>][,topLimit=<value>][,bottomLimit=<value>]\n\
2038 [,functionOf=<column-name>[,lowerLimit=<value>|@parameter_name][,upperLimit=<value>|@<parameter_name>][,position]]\n\
2039 [,offset=<value>][,factor=<value>][match=<column-name>,value=<string>][,overwrite],[default=<value>]]\n\
2040 [,binSize=<value>]\n";
2041
2042PROCESSING_DEFINITION *record_processing_definition(char **argument, long arguments) {
2044 char *lower_str = NULL, *upper_str = NULL;
2045 char *head_str=NULL, *tail_str=NULL, *fhead_str=NULL, *ftail_str=NULL, *offset_str=NULL, *factor_str=NULL;
2046 char *invert_str=NULL;
2047 pd = tmalloc(sizeof(*pd));
2048 if (arguments < 3)
2049 bomb("invalid -process syntax--wrong number of arguments", PROCESSING_USAGE);
2050 SDDS_CopyString(&pd->column_name, argument[0]);
2051 if (process_column_name[0] == NULL) {
2052 long i;
2053 for (i = 0; i < N_PROCESS_COLUMN_MODES; i++)
2054 process_column_name[i] = process_column_data[i].name;
2055 }
2056 pd->lower_par = pd->upper_par = pd->head_par = pd->tail_par = pd->fhead_par = pd->ftail_par = pd->offset_par=pd->factor_par=NULL;
2057 if ((pd->mode = match_string(argument[1], process_column_name, N_PROCESS_COLUMN_MODES, 0)) < 0) {
2058 fprintf(stderr, "invalid -process mode: %s\n", argument[1]);
2059 show_process_modes(stderr);
2060 exit(1);
2061 }
2062
2063 SDDS_CopyString(&pd->parameter_name, argument[2]);
2064 argument += 3;
2065 arguments -= 3;
2066 pd->defaultValue = DBL_MAX;
2067 if (!scanItemList(&pd->flags, argument, &arguments, 0,
2068 "functionof", SDDS_STRING, &pd->functionOf, 1, PROCESSING_FUNCOF_GIVEN,
2069 "weightby", SDDS_STRING, &pd->weightBy, 1, PROCESSING_WEIGHT_GIVEN,
2070 "description", SDDS_STRING, &pd->description, 1, PROCESSING_DESCRIP_GIVEN,
2071 "symbol", SDDS_STRING, &pd->symbol, 1, PROCESSING_SYMBOL_GIVEN,
2072 "toplimit", SDDS_DOUBLE, &pd->topLimit, 1, PROCESSING_TOPLIM_GIVEN,
2073 "bottomlimit", SDDS_DOUBLE, &pd->bottomLimit, 1, PROCESSING_BOTLIM_GIVEN,
2074 "lowerlimit", SDDS_STRING, &lower_str, 1, PROCESSING_LOLIM_GIVEN,
2075 "upperlimit", SDDS_STRING, &upper_str, 1, PROCESSING_UPLIM_GIVEN,
2076 "head", SDDS_STRING, &head_str, 1, PROCESSING_HEAD_GIVEN,
2077 "tail", SDDS_STRING, &tail_str, 1, PROCESSING_TAIL_GIVEN,
2078 "fhead", SDDS_STRING, &fhead_str, 1, PROCESSING_FHEAD_GIVEN,
2079 "ftail", SDDS_STRING, &ftail_str, 1, PROCESSING_FTAIL_GIVEN,
2080 "position", -1, NULL, 0, PROCESSING_POSITION_GIVEN,
2081 "offset", SDDS_STRING, &offset_str, 1, PROCESSING_OFFSET_GIVEN,
2082 "factor", SDDS_STRING, &factor_str, 1, PROCESSING_FACTOR_GIVEN,
2083 "percentlevel", SDDS_DOUBLE, &pd->percentileLevel, 1, PROCESSING_PERCLEVEL_GIVEN,
2084 "binsize", SDDS_DOUBLE, &pd->binSize, 1, PROCESSING_BINSIZE_GIVEN,
2085 "match", SDDS_STRING, &pd->match_column, 1, PROCESSING_MATCHCOLUMN_GIVEN,
2086 "value", SDDS_STRING, &pd->match_value, 1, PROCESSING_MATCHVALUE_GIVEN,
2087 "overwrite", -1, NULL, 0, PROCESSING_OVERWRITE_GIVEN,
2088 "invert", SDDS_STRING, &invert_str, 1, 0,
2089 "default", SDDS_DOUBLE, &pd->defaultValue, 1, PROCESSING_DEFAULTVALUE_GIVEN,
2090 NULL))
2091 bomb("invalid -process syntax", PROCESSING_USAGE);
2092 if (invert_str) {
2093 if (strncmp_case_insensitive(invert_str, "offset", strlen(invert_str))==0)
2094 pd->flags |= PROCESSING_INVERT_OFFSET;
2095 else if (strncmp_case_insensitive(invert_str, "factor", strlen(invert_str))==0)
2096 pd->flags |= PROCESSING_INVERT_FACTOR;
2097 else if (strncmp_case_insensitive(invert_str, "both", strlen(invert_str))==0) {
2098 pd->flags |= PROCESSING_INVERT_OFFSET;
2099 pd->flags |= PROCESSING_INVERT_FACTOR;
2100 } else {
2101 fprintf(stdout, "Warning, invalid invert %s provided for process.\n", invert_str);
2102 }
2103 free(invert_str);
2104 }
2105 if (lower_str) {
2106 if (wild_match(lower_str, "@*")) {
2107 SDDS_CopyString(&pd->lower_par, lower_str + 1);
2108 free(lower_str);
2109 } else if (!get_double(&pd->lowerLimit, lower_str)) {
2110 bomb("invalid lower limit provided for -process option", PROCESSING_USAGE);
2111 }
2112 }
2113 if (upper_str) {
2114 if (wild_match(upper_str, "@*")) {
2115 SDDS_CopyString(&pd->upper_par, upper_str + 1);
2116 free(upper_str);
2117 } else if (!get_double(&pd->upperLimit, upper_str)) {
2118 bomb("invalid upper limit provided for -process option", PROCESSING_USAGE);
2119 }
2120 }
2121 if (head_str) {
2122 if (wild_match(head_str, "@*")) {
2123 SDDS_CopyString(&pd->head_par, head_str + 1);
2124 free(head_str);
2125 } else if (!get_int(&pd->head, head_str)) {
2126 bomb("invalid head provided for -process option", PROCESSING_USAGE);
2127 }
2128 }
2129 if (tail_str) {
2130 if (wild_match(tail_str, "@*")) {
2131 SDDS_CopyString(&pd->tail_par, tail_str + 1);
2132 free(tail_str);
2133 } else if (!get_int(&pd->tail, tail_str)) {
2134 bomb("invalid tail provided for -process option", PROCESSING_USAGE);
2135 }
2136 }
2137 if (fhead_str) {
2138 if (wild_match(fhead_str, "@*")) {
2139 SDDS_CopyString(&pd->fhead_par, fhead_str + 1);
2140 free(fhead_str);
2141 } else if (!get_double(&pd->fhead, fhead_str)) {
2142 bomb("invalid fhead provided for -process option", PROCESSING_USAGE);
2143 }
2144 }
2145 if (ftail_str) {
2146 if (wild_match(ftail_str, "@*")) {
2147 SDDS_CopyString(&pd->ftail_par, ftail_str + 1);
2148 free(ftail_str);
2149 } else if (!get_double(&pd->ftail, ftail_str)) {
2150 bomb("invalid ftail provided for -process option", PROCESSING_USAGE);
2151 }
2152 }
2153 if (offset_str) {
2154 if (wild_match(offset_str, "@*")) {
2155 SDDS_CopyString(&pd->offset_par, offset_str + 1);
2156 free(offset_str);
2157 } else if (wild_match(offset_str, "%s*")) {
2158 SDDS_CopyString(&pd->offset_par, offset_str);
2159 free(ftail_str);
2160 } else if (!get_double(&pd->offset, offset_str)) {
2161 bomb("invalid offset provided for -process option", PROCESSING_USAGE);
2162 }
2163 }
2164 if (factor_str) {
2165 if (wild_match(factor_str, "@*")) {
2166 SDDS_CopyString(&pd->factor_par, factor_str + 1);
2167 free(factor_str);
2168 } else if (wild_match(factor_str, "%s*")) {
2169 SDDS_CopyString(&pd->factor_par, factor_str);
2170 free(factor_str);
2171 } else if (!get_double(&pd->factor, factor_str)) {
2172 bomb("invalid factor provided for -process option", PROCESSING_USAGE);
2173 }
2174 }
2175
2176 if (pd->flags & PROCESSING_BINSIZE_GIVEN && pd->binSize <= 0)
2177 SDDS_Bomb("invalid -process syntax---bin size is zero");
2178 if (pd->flags & PROCESSING_FACTOR_GIVEN && pd->factor == 0)
2179 SDDS_Bomb("invalid -process syntax---factor field is zero");
2180 if ((process_column_data[pd->mode].flags & PROCMODE_FUNCOF_REQUIRED) &&
2181 !(pd->flags & PROCESSING_FUNCOF_GIVEN))
2182 SDDS_Bomb("invalid -process syntax---functionOf option required for given mode");
2183 if (pd->flags & PROCESSING_WEIGHT_GIVEN &&
2184 !(process_column_data[pd->mode].flags & PROCMODE_WEIGHT_OK))
2185 SDDS_Bomb("invalid -process specification---weightBy option not available for given mode");
2186 if (pd->flags & PROCESSING_POSITION_GIVEN) {
2187 if (!(pd->flags & PROCESSING_FUNCOF_GIVEN))
2188 SDDS_Bomb("invalid -process syntax---functionOf required with position option");
2189 if (!(process_column_data[pd->mode].flags & PROCMODE_POSITION_OK))
2190 SDDS_Bomb("invalid -process syntax---position option not permitted for given mode");
2191 }
2192 if (pd->flags & PROCESSING_LOLIM_GIVEN && pd->flags & PROCESSING_UPLIM_GIVEN &&
2193 pd->lowerLimit > pd->upperLimit)
2194 SDDS_Bomb("invalid -process syntax---lowerLimit>upperLimit");
2195 if (pd->flags & PROCESSING_TOPLIM_GIVEN && pd->flags & PROCESSING_BOTLIM_GIVEN && pd->topLimit < pd->bottomLimit)
2196 SDDS_Bomb("invalid -process syntax---bottomLimit>topLimit");
2197 if (pd->flags & PROCESSING_HEAD_GIVEN && !pd->head_par && pd->head == 0)
2198 SDDS_Bomb("invalid -process syntax---head=0");
2199 if (pd->flags & PROCESSING_FHEAD_GIVEN && !pd->fhead_par && pd->fhead == 0)
2200 SDDS_Bomb("invalid -process syntax---fhead=0");
2201 if (pd->flags & PROCESSING_TAIL_GIVEN && !pd->tail_par && pd->tail == 0)
2202 SDDS_Bomb("invalid -process syntax---tail=0");
2203 if (pd->flags & PROCESSING_FTAIL_GIVEN && !pd->ftail_par && pd->ftail == 0)
2204 SDDS_Bomb("invalid -process syntax---ftail=0");
2205 if (pd->flags & (PROCESSING_LOLIM_GIVEN | PROCESSING_UPLIM_GIVEN) && !(pd->flags & PROCESSING_FUNCOF_GIVEN))
2206 SDDS_Bomb("invalid -process syntax---must give -functionOf with limit options");
2207 if (pd->mode == PROCESS_COLUMN_PERCENTILE && !(pd->flags & PROCESSING_PERCLEVEL_GIVEN))
2208 SDDS_Bomb("invalid -process syntax---must give percentLevel with percentile processing");
2209 if (pd->flags & PROCESSING_MATCHCOLUMN_GIVEN && !(pd->flags & PROCESSING_MATCHVALUE_GIVEN))
2210 SDDS_Bomb("invalid -process syntax---must give value for match column");
2211 return (pd);
2212}
2213
2214SDDS_ENUM_PAIR typeEnumPair_local[SDDS_NUM_TYPES + 1] = {
2215 {"longdouble", SDDS_LONGDOUBLE},
2216 {"double", SDDS_DOUBLE},
2217 {"float", SDDS_FLOAT},
2218 {"short", SDDS_SHORT},
2219 {"ushort", SDDS_USHORT},
2220 {"long", SDDS_LONG},
2221 {"ulong", SDDS_ULONG},
2222 {"long64", SDDS_LONG64},
2223 {"ulong64", SDDS_ULONG64},
2224 {"character", SDDS_CHARACTER},
2225 {"string", SDDS_STRING},
2226 {NULL, 0}};
2227
2228long complete_processing_definitions(PROCESSING_DEFINITION **processing_definition,
2229 long processing_definitions,
2230 SDDS_DATASET *SDDS_dataset) {
2231 static char s[SDDS_MAXLINE], t[SDDS_MAXLINE];
2232 long i, index, index1;
2233 PARAMETER_DEFINITION *pardef = NULL, pardef1;
2234 SDDS_FIELD_INFORMATION SDDS_ParameterFieldInformation_local[SDDS_PARAMETER_FIELDS] = {
2235 {"name", offsetof(PARAMETER_DEFINITION, name), SDDS_STRING},
2236 {"symbol", offsetof(PARAMETER_DEFINITION, symbol), SDDS_STRING},
2237 {"units", offsetof(PARAMETER_DEFINITION, units), SDDS_STRING},
2238 {"description", offsetof(PARAMETER_DEFINITION, description), SDDS_STRING},
2239 {"format_string", offsetof(PARAMETER_DEFINITION, format_string), SDDS_STRING},
2240 {"type", offsetof(PARAMETER_DEFINITION, type), SDDS_LONG, typeEnumPair_local},
2241 {"fixed_value", offsetof(PARAMETER_DEFINITION, fixed_value), SDDS_STRING},
2242 };
2243
2244 index1 = 0;
2245
2246 for (i = 0; i < processing_definitions; i++) {
2247 if ((index = SDDS_GetColumnIndex(SDDS_dataset, processing_definition[i]->column_name)) < 0) {
2248 sprintf(s, "column %s does not exist", processing_definition[i]->column_name);
2249 SDDS_SetError(s);
2250 return (0);
2251 }
2252 switch (processing_definition[i]->type =
2253 processing_definition[i]->outputType =
2254 SDDS_GetColumnType(SDDS_dataset, index)) {
2255 case SDDS_STRING:
2256 if (!(process_column_data[processing_definition[i]->mode].flags & PROCMODE_STRING_OK)) {
2257 fprintf(stderr, "column %s has the wrong type for processing (sddsprocess)\n",
2258 processing_definition[i]->column_name);
2259 exit(1);
2260 }
2261 break;
2262 case SDDS_LONG:
2263 case SDDS_SHORT:
2264 case SDDS_FLOAT:
2265 case SDDS_DOUBLE:
2266 case SDDS_LONG64:
2267 case SDDS_CHARACTER:
2268 case SDDS_ULONG64:
2269 case SDDS_ULONG:
2270 case SDDS_USHORT:
2271 case SDDS_LONGDOUBLE:
2272 break;
2273 default:
2274 fprintf(stderr, "column %s has the wrong type for processing (sddsprocess)\n",
2275 processing_definition[i]->column_name);
2276 exit(1);
2277 break;
2278 }
2279 if (processing_definition[i]->flags & PROCESSING_DESCRIP_GIVEN) {
2280 if (strstr(processing_definition[i]->description, "%s")) {
2281 sprintf(s, processing_definition[i]->description,
2282 processing_definition[i]->column_name);
2283 free(processing_definition[i]->description);
2284 SDDS_CopyString(&processing_definition[i]->description, s);
2285 }
2286 } else {
2287 sprintf(s, "%s%s", process_column_data[processing_definition[i]->mode].description,
2288 processing_definition[i]->column_name);
2289 SDDS_CopyString(&processing_definition[i]->description, s);
2290 }
2291 if (strstr(processing_definition[i]->parameter_name, "%s")) {
2292 sprintf(s, processing_definition[i]->parameter_name, processing_definition[i]->column_name);
2293 free(processing_definition[i]->parameter_name);
2294 SDDS_CopyString(&processing_definition[i]->parameter_name, s);
2295 }
2296 if (processing_definition[i]->flags & PROCESSING_WEIGHT_GIVEN &&
2297 SDDS_GetColumnIndex(SDDS_dataset, processing_definition[i]->weightBy) < 0) {
2298 sprintf(s, "column %s does not exist", processing_definition[i]->weightBy);
2299 SDDS_SetError(s);
2300 return 0;
2301 }
2302 if (processing_definition[i]->flags & PROCESSING_MATCHCOLUMN_GIVEN &&
2303 SDDS_GetColumnIndex(SDDS_dataset, processing_definition[i]->match_column) < 0) {
2304 sprintf(s, "column %s does not exist", processing_definition[i]->match_column);
2305 SDDS_SetError(s);
2306 return 0;
2307 }
2308 if (processing_definition[i]->flags & PROCESSING_FUNCOF_GIVEN) {
2309 if ((index1 = SDDS_GetColumnIndex(SDDS_dataset, processing_definition[i]->functionOf)) < 0) {
2310 sprintf(s, "column %s does not exist", processing_definition[i]->functionOf);
2311 SDDS_SetError(s);
2312 return 0;
2313 }
2314 if (processing_definition[i]->flags & PROCESSING_POSITION_GIVEN &&
2315 (processing_definition[i]->outputType = SDDS_GetColumnType(SDDS_dataset, index1)) == SDDS_STRING &&
2316 !(process_column_data[processing_definition[i]->mode].flags & PROCMODE_STRINGPOS_OK)) {
2317 sprintf(s, "Can't have string column for position data with %s processing",
2318 process_column_data[processing_definition[i]->mode].name);
2319 SDDS_SetError(s);
2320 return 0;
2321 }
2322 }
2323 if (processing_definition[i]->outputType != SDDS_STRING)
2324 sprintf(s, "&parameter name=\"%s\", type=double, description=\"%s\", ",
2325 processing_definition[i]->parameter_name, processing_definition[i]->description);
2326 else
2327 sprintf(s, "&parameter name=\"%s\", type=string, description=\"%s\", ",
2328 processing_definition[i]->parameter_name, processing_definition[i]->description);
2329 if (process_column_data[processing_definition[i]->mode].flags & PROCMODE_FUNCOF_UNITS ||
2330 (processing_definition[i]->flags & PROCESSING_FUNCOF_GIVEN &&
2331 processing_definition[i]->flags & PROCESSING_POSITION_GIVEN)) {
2332 if (SDDS_dataset->layout.column_definition[index1].units) {
2333 sprintf(t, "units=\"%s\", ", SDDS_dataset->layout.column_definition[index1].units);
2334 strcat(s, t);
2335 }
2336 } else if (process_column_data[processing_definition[i]->mode].flags & PROCMODE_YoX_UNITS) {
2337 t[0] = 0;
2338 if (!SDDS_StringIsBlank(SDDS_dataset->layout.column_definition[index].units) &&
2339 !SDDS_StringIsBlank(SDDS_dataset->layout.column_definition[index1].units))
2340 sprintf(t, "units=\"(%s)/(%s)\", ",
2341 SDDS_dataset->layout.column_definition[index].units,
2342 SDDS_dataset->layout.column_definition[index1].units);
2343 else if (!SDDS_StringIsBlank(SDDS_dataset->layout.column_definition[index].units))
2344 sprintf(t, "units=\"%s\", ",
2345 SDDS_dataset->layout.column_definition[index].units);
2346 else if (!SDDS_StringIsBlank(SDDS_dataset->layout.column_definition[index1].units))
2347 sprintf(t, "units=\"1/(%s)\", ",
2348 SDDS_dataset->layout.column_definition[index1].units);
2349 strcat(s, t);
2350 } else if (process_column_data[processing_definition[i]->mode].flags & PROCMODE_YtX_UNITS) {
2351 t[0] = 0;
2352 if (!SDDS_StringIsBlank(SDDS_dataset->layout.column_definition[index].units) &&
2353 !SDDS_StringIsBlank(SDDS_dataset->layout.column_definition[index1].units))
2354 sprintf(t, "units=\"%s*%s\", ",
2355 SDDS_dataset->layout.column_definition[index].units,
2356 SDDS_dataset->layout.column_definition[index1].units);
2357 else if (!SDDS_StringIsBlank(SDDS_dataset->layout.column_definition[index].units))
2358 sprintf(t, "units=\"%s\", ",
2359 SDDS_dataset->layout.column_definition[index].units);
2360 else if (!SDDS_StringIsBlank(SDDS_dataset->layout.column_definition[index1].units))
2361 sprintf(t, "units=\"%s\", ",
2362 SDDS_dataset->layout.column_definition[index1].units);
2363 strcat(s, t);
2364 } else if (process_column_data[processing_definition[i]->mode].flags & PROCMODE_Y_UNITS) {
2365 if (SDDS_dataset->layout.column_definition[index].units) {
2366 sprintf(t, "units=\"%s\", ", SDDS_dataset->layout.column_definition[index].units);
2367 strcat(s, t);
2368 }
2369 }
2370 if (processing_definition[i]->symbol) {
2371 sprintf(t, "symbol=\"%s\", ", processing_definition[i]->symbol);
2372 strcat(s, t);
2373 }
2374 strcat(s, "&end");
2375 if ((index = SDDS_GetParameterIndex(SDDS_dataset, processing_definition[i]->parameter_name)) >= 0 &&
2376 processing_definition[i]->flags & PROCESSING_OVERWRITE_GIVEN) {
2377 pardef1.name = pardef1.symbol = pardef1.units = pardef1.description =
2378 pardef1.format_string = pardef1.fixed_value = NULL;
2379 pardef1.type = -1;
2380 if (!SDDS_ParseNamelist((void *)&pardef1, SDDS_ParameterFieldInformation_local,
2381 SDDS_PARAMETER_FIELDS, s)) {
2382 SDDS_SetError("Problem parsing parameter namelist");
2383 return 0;
2384 }
2385 if ((pardef1.symbol && !SDDS_ChangeParameterInformation(SDDS_dataset, "symbol", &pardef1.symbol, SDDS_BY_INDEX, index)) ||
2386 (pardef1.units && !SDDS_ChangeParameterInformation(SDDS_dataset, "units", &pardef1.units, SDDS_BY_INDEX, index)) ||
2387 (pardef1.description && !SDDS_ChangeParameterInformation(SDDS_dataset, "description", &pardef1.description, SDDS_BY_INDEX, index)) ||
2388 (pardef1.format_string && !SDDS_ChangeParameterInformation(SDDS_dataset, "format_string", &pardef1.format_string, SDDS_BY_INDEX, index)) ||
2389 (pardef1.fixed_value && !SDDS_ChangeParameterInformation(SDDS_dataset, "fixed_value", &pardef1.fixed_value, SDDS_BY_INDEX, index)) ||
2390 (pardef1.type >= 0 && !SDDS_ChangeParameterInformation(SDDS_dataset, "type", &pardef1.type, SDDS_BY_INDEX, index))) {
2391 SDDS_SetError("Problem changing parameter definitions");
2392 return 0;
2393 }
2394 } else {
2395 if (!SDDS_ProcessParameterString(SDDS_dataset, s, SDDS_WRITEONLY_DEFINITION) ||
2396 !(pardef = SDDS_GetParameterDefinition(SDDS_dataset, processing_definition[i]->parameter_name)))
2397 return (0);
2398 processing_definition[i]->memory_number = pardef->memory_number;
2400 }
2401 }
2402 return (1);
2403}
2404
2405CONVERSION_DEFINITION *process_conversion_definition(char **argument, long arguments) {
2406 CONVERSION_DEFINITION *request;
2407 request = tmalloc(sizeof(*request));
2408 if (arguments != 5)
2409 return (NULL);
2410 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
2411 case COLUMN_BASED:
2412 request->is_parameter = 0;
2413 break;
2414 case PARAMETER_BASED:
2415 request->is_parameter = 1;
2416 break;
2417 default:
2418 return (NULL);
2419 }
2420 argument++;
2421 arguments--;
2422
2423 request->name = argument[0];
2424 request->new_units = argument[1];
2425 request->old_units = argument[2];
2426 if (sscanf(argument[3], "%lf", &request->factor) != 1)
2427 return (NULL);
2428
2429 return (request);
2430}
2431
2432#include <stddef.h>
2433
2434char *substituteString(char *template, char *pattern, char *replacement) {
2435 char *ptr, *ptr0, *buffer, c;
2436 long count = 0, patternLength, newLength;
2437
2438 if (!(patternLength = strlen(pattern)))
2439 return NULL;
2440 if (!(ptr = template))
2441 return NULL;
2442 while ((ptr = strstr(ptr, pattern))) {
2443 count++;
2444 ptr += patternLength;
2445 }
2446 if ((newLength = strlen(template) - count * patternLength + count * strlen(replacement) + 1) <= 0 ||
2447 !(buffer = malloc(newLength * sizeof(*buffer))))
2448 return NULL;
2449
2450 ptr0 = template;
2451 *buffer = 0;
2452 while (ptr0 && *ptr0 && (ptr = strstr(ptr0, pattern))) {
2453 c = *ptr;
2454 *ptr = 0;
2455 strcat(buffer, ptr0);
2456 strcat(buffer, replacement);
2457 *ptr = c;
2458 ptr0 = ptr = ptr + patternLength;
2459 }
2460 if (ptr0 && *ptr0)
2461 strcat(buffer, ptr0);
2462 return buffer;
2463}
2464
2465void expandDefinitions(DEFINITION **definition, long *definitions, SDDS_DATASET *SDDS_dataset) {
2466 long names, idef, jdef, is_parameter, templates, itemplate, definitionType, i, j;
2467 char **name, **wildcardName, *editSelection, **target, **excludeWildcardName = NULL;
2468 size_t structSize;
2469 void *defStruct;
2470 char editBuffer[SDDS_MAXLINE];
2471 long maxTemplates = 10, requireWildcard;
2472 struct {
2473 long offset;
2474 short isPointer, isBase;
2475 size_t arraySize;
2476 long index;
2477 char *template;
2478 } * targetData;
2479
2480 is_parameter = 0;
2481 structSize = 0;
2482
2483 if (!(targetData = SDDS_Malloc(sizeof(*targetData) * maxTemplates)))
2484 SDDS_Bomb("Memory allocation failure");
2485
2486 for (idef = 0; idef < *definitions; idef++) {
2487 editSelection = NULL;
2488 requireWildcard = 0; /* If nonzero, don't try to process an expansion unless the
2489 * name being expanded has wildcards.
2490 */
2491 for (i = 0; i < maxTemplates; i++) {
2492 targetData[i].isPointer = 0;
2493 }
2494 switch (definitionType = (*definition)[idef].type) {
2495 case IS_EQUATION_DEFINITION:
2496 /* e.g., -define=column,%sDiff,"%sSet %sRead -",select=Current*Set,edit=%/Set// */
2497 wildcardName = &((EQUATION_DEFINITION *)(*definition)[idef].structure)->select;
2498 excludeWildcardName = &((EQUATION_DEFINITION *)(*definition)[idef].structure)->exclude;
2499 is_parameter = ((EQUATION_DEFINITION *)(*definition)[idef].structure)->is_parameter;
2500 editSelection = ((EQUATION_DEFINITION *)(*definition)[idef].structure)->editSelection;
2501 structSize = sizeof(EQUATION_DEFINITION);
2502 targetData[0].offset = offsetof(EQUATION_DEFINITION, name);
2503 targetData[1].offset = offsetof(EQUATION_DEFINITION, equation);
2504 targetData[2].offset = offsetof(EQUATION_DEFINITION, text);
2505 SDDS_CopyString(&targetData[0].template,
2506 ((EQUATION_DEFINITION *)(*definition)[idef].structure)->name);
2507 SDDS_CopyString(&targetData[1].template,
2508 ((EQUATION_DEFINITION *)(*definition)[idef].structure)->equation);
2509 SDDS_CopyString(&targetData[2].template,
2510 ((EQUATION_DEFINITION *)(*definition)[idef].structure)->text);
2511 templates = 3;
2512 break;
2513 case IS_PRINT_DEFINITION:
2514 /* e.g., -print=column,%sLabel,"%s = %f%s",%s.name,%s,%s.units,select=Current* */
2515 wildcardName = &((PRINT_DEFINITION *)(*definition)[idef].structure)->select;
2516 excludeWildcardName = &((PRINT_DEFINITION *)(*definition)[idef].structure)->exclude;
2517 is_parameter = ((PRINT_DEFINITION *)(*definition)[idef].structure)->is_parameter;
2518 editSelection = ((PRINT_DEFINITION *)(*definition)[idef].structure)->editSelection;
2519 structSize = sizeof(PRINT_DEFINITION);
2520 targetData[0].offset = offsetof(PRINT_DEFINITION, new_name);
2521 targetData[1].offset = offsetof(PRINT_DEFINITION, text);
2522 SDDS_CopyString(&targetData[0].template,
2523 ((PRINT_DEFINITION *)(*definition)[idef].structure)->new_name);
2524 SDDS_CopyString(&targetData[1].template,
2525 ((PRINT_DEFINITION *)(*definition)[idef].structure)->text);
2526 if (((PRINT_DEFINITION *)(*definition)[idef].structure)->sources + 2 > maxTemplates) {
2527 maxTemplates = 2 * ((PRINT_DEFINITION *)(*definition)[idef].structure)->sources + 2;
2528 if (!(targetData = SDDS_Realloc(targetData, sizeof(*targetData) * maxTemplates)))
2529 SDDS_Bomb("Memory allocation failure");
2530 }
2531 for (i = 0; i < ((PRINT_DEFINITION *)(*definition)[idef].structure)->sources; i++) {
2532 targetData[i + 2].isPointer = 1;
2533 if (i == 0) {
2534 targetData[i + 2].isBase = 1;
2535 targetData[i + 2].arraySize = sizeof(*(((PRINT_DEFINITION *)(*definition)[idef].structure)->source)) *
2536 ((PRINT_DEFINITION *)(*definition)[idef].structure)->sources;
2537 } else
2538 targetData[i + 2].isBase = 0;
2539 targetData[i + 2].index = i;
2540 targetData[i + 2].offset = offsetof(PRINT_DEFINITION, source);
2541 SDDS_CopyString(&targetData[i + 2].template,
2542 ((PRINT_DEFINITION *)(*definition)[idef].structure)->source[i]);
2543 }
2544 templates = ((PRINT_DEFINITION *)(*definition)[idef].structure)->sources + 2;
2545 break;
2546 case IS_SCAN_DEFINITION:
2547 /* e.g., -scan=column,%sNum,Current*,"%f" */
2548 wildcardName = &((SCAN_DEFINITION *)(*definition)[idef].structure)->source;
2549 requireWildcard = 1;
2550 is_parameter = ((SCAN_DEFINITION *)(*definition)[idef].structure)->is_parameter;
2551 structSize = sizeof(SCAN_DEFINITION);
2552 targetData[0].offset = offsetof(SCAN_DEFINITION, new_name);
2553 targetData[1].offset = offsetof(SCAN_DEFINITION, text);
2554 targetData[2].offset = offsetof(SCAN_DEFINITION, source);
2555 SDDS_CopyString(&targetData[0].template,
2556 ((SCAN_DEFINITION *)(*definition)[idef].structure)->new_name);
2557 SDDS_CopyString(&targetData[1].template,
2558 ((SCAN_DEFINITION *)(*definition)[idef].structure)->text);
2559 SDDS_CopyString(&targetData[2].template, "%s");
2560 templates = 3;
2561 break;
2562 case IS_EDIT_DEFINITION:
2563 /* e.g., -edit=column,%sEdited,String*,%/Fred/Sally/ */
2564 wildcardName = &((EDIT_DEFINITION *)(*definition)[idef].structure)->source;
2565 requireWildcard = 1;
2566 is_parameter = ((EDIT_DEFINITION *)(*definition)[idef].structure)->is_parameter;
2567 structSize = sizeof(EDIT_DEFINITION);
2568 targetData[0].offset = offsetof(EDIT_DEFINITION, new_name);
2569 targetData[1].offset = offsetof(EDIT_DEFINITION, text);
2570 targetData[2].offset = offsetof(EDIT_DEFINITION, source);
2571 SDDS_CopyString(&targetData[0].template,
2572 ((EDIT_DEFINITION *)(*definition)[idef].structure)->new_name);
2573 SDDS_CopyString(&targetData[1].template,
2574 ((EDIT_DEFINITION *)(*definition)[idef].structure)->text);
2575 SDDS_CopyString(&targetData[2].template, "%s");
2576 templates = 3;
2577 break;
2578 case IS_PROCESSING_DEFINITION:
2579 /* e.g., -process=Current*,average,%sMean */
2580 wildcardName = &((PROCESSING_DEFINITION *)(*definition)[idef].structure)->column_name;
2581 requireWildcard = 1;
2582 is_parameter = 0;
2583 structSize = sizeof(PROCESSING_DEFINITION);
2584 targetData[0].offset = offsetof(PROCESSING_DEFINITION, parameter_name);
2585 targetData[1].offset = offsetof(PROCESSING_DEFINITION, column_name);
2586 targetData[2].offset = offsetof(PROCESSING_DEFINITION, functionOf);
2587 targetData[3].offset = offsetof(PROCESSING_DEFINITION, weightBy);
2588 targetData[4].offset = offsetof(PROCESSING_DEFINITION, description);
2589 targetData[5].offset = offsetof(PROCESSING_DEFINITION, symbol);
2590 SDDS_CopyString(&targetData[0].template,
2591 ((PROCESSING_DEFINITION *)(*definition)[idef].structure)->parameter_name);
2592 SDDS_CopyString(&targetData[1].template, "%s");
2593 SDDS_CopyString(&targetData[2].template,
2594 ((PROCESSING_DEFINITION *)(*definition)[idef].structure)->functionOf);
2595 SDDS_CopyString(&targetData[3].template,
2596 ((PROCESSING_DEFINITION *)(*definition)[idef].structure)->weightBy);
2597 SDDS_CopyString(&targetData[4].template,
2598 ((PROCESSING_DEFINITION *)(*definition)[idef].structure)->description);
2599 SDDS_CopyString(&targetData[5].template,
2600 ((PROCESSING_DEFINITION *)(*definition)[idef].structure)->symbol);
2601 templates = 6;
2602 break;
2603 case IS_CONVERSION_DEFINITION:
2604 /* e.g., -convert=column,Current*,mA,A,1000 */
2605 wildcardName = &((CONVERSION_DEFINITION *)(*definition)[idef].structure)->name;
2606 requireWildcard = 1;
2607 is_parameter = ((CONVERSION_DEFINITION *)(*definition)[idef].structure)->is_parameter;
2608 structSize = sizeof(CONVERSION_DEFINITION);
2609 targetData[0].offset = offsetof(CONVERSION_DEFINITION, name);
2610 SDDS_CopyString(&targetData[0].template, "%s");
2611 templates = 1;
2612 break;
2613 case IS_SYSTEM_DEFINITION:
2614 /* e.g., -system=column,SysResult%s,Command* */
2615 wildcardName = &((SYSTEM_DEFINITION *)(*definition)[idef].structure)->source;
2616 requireWildcard = 1;
2617 is_parameter = ((SYSTEM_DEFINITION *)(*definition)[idef].structure)->is_parameter;
2618 structSize = sizeof(SYSTEM_DEFINITION);
2619 targetData[0].offset = offsetof(SYSTEM_DEFINITION, new_name);
2620 targetData[1].offset = offsetof(SYSTEM_DEFINITION, text);
2621 targetData[2].offset = offsetof(SYSTEM_DEFINITION, source);
2622 SDDS_CopyString(&targetData[0].template,
2623 ((SYSTEM_DEFINITION *)(*definition)[idef].structure)->new_name);
2624 SDDS_CopyString(&targetData[1].template,
2625 ((SYSTEM_DEFINITION *)(*definition)[idef].structure)->text);
2626 SDDS_CopyString(&targetData[2].template, "%s");
2627 templates = 3;
2628 break;
2629 case IS_CAST_DEFINITION:
2630 /* e.g., -cast=column,%sLong,Current*,long */
2631 wildcardName = &((CAST_DEFINITION *)(*definition)[idef].structure)->source;
2632 requireWildcard = 1;
2633 is_parameter = ((CAST_DEFINITION *)(*definition)[idef].structure)->isParameter;
2634 structSize = sizeof(CAST_DEFINITION);
2635 targetData[0].offset = offsetof(CAST_DEFINITION, newName);
2636 targetData[1].offset = offsetof(CAST_DEFINITION, source);
2637 SDDS_CopyString(&targetData[0].template,
2638 ((CAST_DEFINITION *)(*definition)[idef].structure)->newName);
2639 SDDS_CopyString(&targetData[1].template, "%s");
2640 templates = 2;
2641 break;
2642 default:
2643 wildcardName = NULL;
2644 templates = 0;
2645 break;
2646 }
2647 if ((!wildcardName || !*wildcardName) || (requireWildcard && !has_wildcards(*wildcardName))) {
2648 if (wildcardName && *wildcardName)
2649 unescape_wildcards(*wildcardName);
2650 continue;
2651 }
2652
2653 if (is_parameter) {
2654 if ((excludeWildcardName == NULL) || (*excludeWildcardName == NULL)) {
2655 if ((names = SDDS_MatchParameters(SDDS_dataset, &name, SDDS_MATCH_STRING, FIND_ANY_TYPE,
2656 *wildcardName, SDDS_AND | SDDS_1_PREVIOUS)) <= 0) {
2657 fprintf(stderr, "Error (expandDefinitions): unable to find match to parameter name %s\n", *wildcardName);
2658 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2659 exit(1);
2660 }
2661 } else {
2662 if ((names = SDDS_MatchParameters(SDDS_dataset, &name, SDDS_MATCH_EXCLUDE_STRING, FIND_ANY_TYPE,
2663 *wildcardName, *excludeWildcardName,
2664 SDDS_AND | SDDS_1_PREVIOUS)) <= 0) {
2665 fprintf(stderr, "Error (expandDefinitions): unable to find match to parameter name %s\n", *wildcardName);
2666 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2667 exit(1);
2668 }
2669 }
2670 } else {
2671 if ((excludeWildcardName == NULL) || (*excludeWildcardName == NULL)) {
2672 if ((names = SDDS_MatchColumns(SDDS_dataset, &name, SDDS_MATCH_STRING, FIND_ANY_TYPE,
2673 *wildcardName, SDDS_AND | SDDS_1_PREVIOUS)) <= 0) {
2674 fprintf(stderr, "Error (expandDefinitions): unable to find match to column name %s\n", *wildcardName);
2675 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2676 exit(1);
2677 }
2678 } else {
2679 if ((names = SDDS_MatchColumns(SDDS_dataset, &name, SDDS_MATCH_EXCLUDE_STRING, FIND_ANY_TYPE,
2680 *wildcardName, *excludeWildcardName,
2681 SDDS_AND | SDDS_1_PREVIOUS)) <= 0) {
2682 fprintf(stderr, "Error (expandDefinitions): unable to find match to column name %s\n", *wildcardName);
2683 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2684 exit(1);
2685 }
2686 }
2687 }
2688 if (editSelection)
2689 edit_strings(name, names, editBuffer, editSelection);
2690 *definition = SDDS_Realloc(*definition, sizeof(**definition) * (*definitions - 1 + names));
2691 for (jdef = *definitions - 1; jdef > idef; jdef--) {
2692 (*definition)[jdef + names - 1].structure = (*definition)[jdef].structure;
2693 (*definition)[jdef + names - 1].type = (*definition)[jdef].type;
2694 }
2695 for (jdef = names - 1; jdef >= 0; jdef--) {
2696 if (jdef) {
2697 if (!(defStruct = (*definition)[idef + jdef].structure = calloc(1, structSize)))
2698 SDDS_Bomb("memory allocation failure (expandDefinitions)");
2699 memcpy((char *)defStruct, (char *)(*definition)[idef].structure, structSize);
2700 } else
2701 defStruct = (*definition)[idef + jdef].structure;
2702 (*definition)[idef + jdef].type = definitionType;
2703 for (itemplate = 0; itemplate < templates; itemplate++) {
2704 if (targetData[itemplate].isPointer) {
2705 char **ptr;
2706 if (targetData[itemplate].isBase) {
2707 *(char ***)((char *)defStruct + targetData[itemplate].offset) =
2708 SDDS_Malloc(targetData[itemplate].arraySize);
2709 }
2710 ptr = *(char ***)((char *)defStruct + targetData[itemplate].offset);
2711 target = ptr + targetData[itemplate].index;
2712 } else
2713 target = (char **)((char *)defStruct + targetData[itemplate].offset);
2714 if (!(*target =
2715 substituteString(targetData[itemplate].template, "%s", name[jdef])) &&
2716 targetData[itemplate].template) {
2717 fputs("Error: problem doing pattern substitution (expandDefinitions)\n", stderr);
2718 fprintf(stderr, "template is \"%s\", instance is \"%s\"\n",
2719 targetData[itemplate].template, name[jdef]);
2720 exit(1);
2721 }
2722 }
2723 }
2724 *definitions += names - 1;
2725 idef += names - 1;
2726 for (j = 0; j < names; j++)
2727 free(name[j]);
2728 free(name);
2729 }
2730 free(targetData);
2731}
2732
2733long scan_column_value(SDDS_DATASET *SDDS_dataset, char *target, char *source, char *format,
2734 char *edit_command) {
2735 char **source_value, char_value, *sourcePtr;
2736 long target_type, target_index, source_index;
2737 int64_t i, rows;
2738 float float_value;
2739 double double_value;
2740 int64_t long64_value;
2741 int32_t long_value;
2742 short short_value;
2743 static char s[SDDS_MAXLINE];
2744
2745 if ((source_index = SDDS_GetColumnIndex(SDDS_dataset, source)) < 0 ||
2746 (target_index = SDDS_GetColumnIndex(SDDS_dataset, target)) < 0) {
2747 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2748 return (0);
2749 }
2750 if (SDDS_GetColumnType(SDDS_dataset, source_index) != SDDS_STRING) {
2751 fprintf(stderr, "error: source column %s has wrong type for scanning--must be string\n", source);
2752 return (0);
2753 }
2754 target_type = SDDS_GetColumnType(SDDS_dataset, target_index);
2755
2756 if ((rows = SDDS_CountRowsOfInterest(SDDS_dataset)) < 0) {
2757 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2758 return (0);
2759 }
2760
2761 if (!(source_value = SDDS_GetInternalColumn(SDDS_dataset, source))) {
2762 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2763 return (0);
2764 }
2765
2766 for (i = 0; i < rows; i++) {
2767 sourcePtr = source_value[i];
2768 if (!source_value[i]) {
2769 if (SDDS_NUMERIC_TYPE(target_type))
2770 strcpy(s, "NaN");
2771 else
2772 strcpy(s, "\0");
2773 sourcePtr = s;
2774 } else if (edit_command && strlen(edit_command)) {
2775 strncpy(s, source_value[i], SDDS_MAXLINE - 1);
2776 sourcePtr = s;
2777 if (!edit_string(s, edit_command)) {
2778 fprintf(stderr, "error: unable to preedit source string \"%s\" to scan into %s\n", source_value[i], target);
2779 return (0);
2780 }
2781 }
2782 switch (target_type) {
2783 case SDDS_DOUBLE:
2784 if (sscanf(sourcePtr, format, &double_value) != 1) {
2785 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\n", sourcePtr, target);
2786 return (0);
2787 }
2788 if (!SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, i, target_index, double_value, -1)) {
2789 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2790 return (0);
2791 }
2792 break;
2793 case SDDS_FLOAT:
2794 if (sscanf(sourcePtr, format, &float_value) != 1) {
2795 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\n", sourcePtr, target);
2796 return (0);
2797 }
2798 if (!SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, i, target_index, float_value, -1)) {
2799 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2800 return (0);
2801 }
2802 break;
2803 case SDDS_LONG64:
2804 if (sscanf(sourcePtr, format, &long64_value) != 1) {
2805 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\n", sourcePtr, target);
2806 return (0);
2807 }
2808 if (!SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, i, target_index, long64_value, -1)) {
2809 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2810 return (0);
2811 }
2812 break;
2813 case SDDS_LONG:
2814 if (sscanf(sourcePtr, format, &long_value) != 1) {
2815 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\n", sourcePtr, target);
2816 return (0);
2817 }
2818 if (!SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, i, target_index, long_value, -1)) {
2819 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2820 return (0);
2821 }
2822 break;
2823 case SDDS_SHORT:
2824 if (sscanf(sourcePtr, format, &short_value) != 1) {
2825 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\n", sourcePtr, target);
2826 return (0);
2827 }
2828 if (!SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, i, target_index, short_value, -1)) {
2829 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2830 return (0);
2831 }
2832 break;
2833 case SDDS_CHARACTER:
2834 if (sscanf(sourcePtr, format, &char_value) != 1) {
2835 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\n", sourcePtr, target);
2836 return (0);
2837 }
2838 if (!SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, i, target_index, char_value, -1)) {
2839 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2840 return (0);
2841 }
2842 break;
2843 case SDDS_STRING:
2844 if (sscanf(sourcePtr, format, s) != 1) {
2845 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\n", sourcePtr, target);
2846 return (0);
2847 }
2848 if (!SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, i, target_index, s, -1)) {
2849 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2850 return (0);
2851 }
2852 break;
2853 default:
2854 SDDS_Bomb("error: unknown type encountered--this shouldn't happen (scan_column_value)");
2855 break;
2856 }
2857 }
2858 return (1);
2859}
2860
2861long scan_parameter_value(SDDS_DATASET *SDDS_dataset, char *target, char *source, char *format,
2862 char *edit_command) {
2863 char *source_value, **ptr, char_value;
2864 long target_type, target_index, source_index;
2865 float float_value;
2866 double double_value;
2867 int64_t long64_value;
2868 int32_t long_value;
2869 short short_value;
2870 static char s[SDDS_MAXLINE];
2871
2872 if ((source_index = SDDS_GetParameterIndex(SDDS_dataset, source)) < 0 ||
2873 (target_index = SDDS_GetParameterIndex(SDDS_dataset, target)) < 0) {
2874 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2875 return (0);
2876 }
2877 if (SDDS_GetParameterType(SDDS_dataset, source_index) != SDDS_STRING) {
2878 fprintf(stderr, "error: source parameter %s has wrong type for scanning--must be string\n", source);
2879 return (0);
2880 }
2881 target_type = SDDS_GetParameterType(SDDS_dataset, target_index);
2882
2883 if (!(ptr = SDDS_GetParameter(SDDS_dataset, source, NULL))) {
2884 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2885 return (0);
2886 }
2887 source_value = *ptr;
2888 if (!source_value) {
2889 if (SDDS_NUMERIC_TYPE(target_type))
2890 SDDS_CopyString(&source_value, "NaN");
2891 else
2892 SDDS_CopyString(&source_value, "\0");
2893 } else if (edit_command) {
2894 strncpy(s, source_value, SDDS_MAXLINE - 1);
2895 if (!edit_string(s, edit_command)) {
2896 fprintf(stderr, "error: unable to preedit source string \"%s\" for scanning into %s\n", source_value, target);
2897 return (0);
2898 }
2899 free(source_value);
2900 SDDS_CopyString(&source_value, s);
2901 }
2902 switch (target_type) {
2903 case SDDS_DOUBLE:
2904 if (sscanf(source_value, format, &double_value) != 1) {
2905 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\nsscanf string was:", source_value, target);
2906 fputs(format, stderr);
2907 fputc('\n', stderr);
2908 return (0);
2909 }
2910 if (!SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, double_value, -1)) {
2911 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2912 return (0);
2913 }
2914 break;
2915 case SDDS_FLOAT:
2916 if (sscanf(source_value, format, &float_value) != 1) {
2917 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\nsscanf string was:", source_value, target);
2918 fputs(format, stderr);
2919 fputc('\n', stderr);
2920 return (0);
2921 }
2922 if (!SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, float_value, -1)) {
2923 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2924 return (0);
2925 }
2926 break;
2927 case SDDS_LONG64:
2928 if (sscanf(source_value, format, &long64_value) != 1) {
2929 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\nsscanf string was:", source_value, target);
2930 fputs(format, stderr);
2931 fputc('\n', stderr);
2932 return (0);
2933 }
2934 if (!SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, long64_value, -1)) {
2935 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2936 return (0);
2937 }
2938 break;
2939 case SDDS_LONG:
2940 if (sscanf(source_value, format, &long_value) != 1) {
2941 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\nsscanf string was:", source_value, target);
2942 fputs(format, stderr);
2943 fputc('\n', stderr);
2944 return (0);
2945 }
2946 if (!SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, long_value, -1)) {
2947 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2948 return (0);
2949 }
2950 break;
2951 case SDDS_SHORT:
2952 if (sscanf(source_value, format, &short_value) != 1) {
2953 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\nsscanf string was:", source_value, target);
2954 fputs(format, stderr);
2955 fputc('\n', stderr);
2956 return (0);
2957 }
2958 if (!SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, short_value, -1)) {
2959 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2960 return (0);
2961 }
2962 break;
2963 case SDDS_CHARACTER:
2964 if (sscanf(source_value, format, &char_value) != 1) {
2965 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\nsscanf string was:", source_value, target);
2966 fputs(format, stderr);
2967 fputc('\n', stderr);
2968 return (0);
2969 }
2970 if (!SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, char_value, -1)) {
2971 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2972 return (0);
2973 }
2974 break;
2975 case SDDS_STRING:
2976 if (sscanf(source_value, format, s) != 1) {
2977 fprintf(stderr, "error: unable to scan source string \"%s\" to make %s\nsscanf string was:", source_value, target);
2978 fputs(format, stderr);
2979 fputc('\n', stderr);
2980 return (0);
2981 }
2982 if (!SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, s, -1)) {
2983 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
2984 return (0);
2985 }
2986 break;
2987 default:
2988 SDDS_Bomb("error: unknown type encountered--this shouldn't happen (scan_parameter_value)");
2989 break;
2990 }
2991 free(source_value);
2992 return (1);
2993}
2994
2995PRINT_DEFINITION *process_new_print_definition(char **argument, long arguments) {
2996 static char s[SDDS_MAXLINE];
2997 char *ptr;
2998 long i, hasType, code;
2999 PRINT_DEFINITION *defi;
3000
3001 hasType = 0;
3002 if (!(defi = tmalloc(sizeof(*defi))))
3003 SDDS_Bomb("memory allocation failure (process_new_print_definition)");
3004 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
3005 case COLUMN_BASED:
3006 defi->is_parameter = 0;
3007 sprintf(s, "&column name=\"%s\", ", argument[1]);
3008 break;
3009 case PARAMETER_BASED:
3010 defi->is_parameter = 1;
3011 sprintf(s, "&parameter name=\"%s\", ", argument[1]);
3012 break;
3013 default:
3014 fprintf(stderr, "error: column or parameter must be specified for print\n");
3015 return (NULL);
3016 }
3017 defi->new_name = argument[1];
3018 defi->source = NULL;
3019 defi->sources = 0;
3020 defi->printf_string = argument[2];
3021
3022 for (i = 3; i < arguments; i++) {
3023 if (!(ptr = strchr(argument[i], '='))) {
3024 /* source entry */
3025 defi->source = trealloc(defi->source, sizeof(*defi->source) * (defi->sources + 1));
3026 defi->source[defi->sources++] = argument[i];
3027 } else
3028 break;
3029 }
3030 for (; i < arguments; i++) {
3031 /* should only have qualifiers from here on */
3032 if (!(ptr = strchr(argument[i], '='))) {
3033 fprintf(stderr, "error: invalid definition-entry: %s\n", argument[i]);
3034 return (NULL);
3035 }
3036 *ptr = 0;
3037 switch (code = match_string(argument[i], selectQualifier, SELECT_QUALIFIERS, 0)) {
3038 case SELECT_QUALIFIER:
3039 defi->select = ptr + 1;
3040 break;
3041 case EDITSELECTION_QUALIFIER:
3042 defi->editSelection = ptr + 1;
3043 break;
3044 case EXCLUDE_QUALIFIER:
3045 defi->exclude = ptr + 1;
3046 break;
3047 default:
3048 break;
3049 }
3050 *ptr = '=';
3051 if (code >= 0)
3052 continue;
3053 *ptr = 0;
3054 strcat(s, argument[i]);
3055 if (strcmp(argument[i], "type") == 0)
3056 hasType = 1;
3057 strcat(s, "=\"");
3058 strcat(s, ptr + 1);
3059 strcat(s, "\", ");
3060 *ptr = '=';
3061 }
3062 if (!hasType)
3063 strcat(s, " type=string &end");
3064 else
3065 strcat(s, " &end");
3066 if (!SDDS_CopyString(&defi->text, s))
3067 SDDS_Bomb("unable to copy text of print definition (process_new_print_definition)");
3068 return (defi);
3069}
3070
3071long print_parameter_value(SDDS_DATASET *SDDS_dataset, char *target, char **source, long sources, char *format) {
3072 char *print_pos, **ptr, *fptr1, *fptr2 = NULL, *fptr3, *cptr;
3073 long source_type, source_index, target_index, target_type;
3074 long i, use_info;
3075 static char s[SDDS_MAXLINE];
3076 static char *info = NULL;
3077
3078 if (!info && !(info = malloc(sizeof(double) * 2)))
3079 SDDS_Bomb("Allocation failure in print_parameter_value");
3080
3081 if ((target_index = SDDS_GetParameterIndex(SDDS_dataset, target)) < 0) {
3082 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3083 return (0);
3084 }
3085 if ((target_type = SDDS_GetParameterType(SDDS_dataset, target_index)) != SDDS_STRING &&
3086 target_type != SDDS_CHARACTER) {
3087 fprintf(stderr, "error: target parameter %s has wrong type for printing--must be string or character\n", target);
3088 return (0);
3089 }
3090 fptr1 = format;
3091 s[0] = 0;
3092 if (sources == 0)
3093 strcpy(s, format);
3094 for (i = 0; i < sources; i++) {
3095 print_pos = s + strlen(s);
3096 use_info = 0;
3097 if ((source_index = SDDS_GetParameterIndex(SDDS_dataset, source[i])) < 0 ||
3098 (source_type = SDDS_GetParameterType(SDDS_dataset, source_index)) < 0) {
3099 if ((cptr = strrchr(source[i], '.'))) {
3100 *cptr = 0;
3101 if (!(source_type = SDDS_GetParameterInformation(SDDS_dataset, cptr + 1, info, SDDS_GET_BY_NAME, source[i])) &&
3102 !(source_type = SDDS_GetColumnInformation(SDDS_dataset, cptr + 1, info, SDDS_GET_BY_NAME, source[i]))) {
3103 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3104 return (0);
3105 }
3106 if (strcmp(cptr + 1, "type") == 0) {
3107 if (source_type != SDDS_LONG)
3108 return bombre("internal error: type of data-type information is not long", NULL, 0);
3109 SDDS_CopyString((char **)info, SDDS_type_name[*(long *)info - 1]);
3110 source_type = SDDS_STRING;
3111 }
3112 *cptr = '.';
3113 use_info = 1;
3114 if (source_type == SDDS_STRING && *(char **)info == NULL)
3115 SDDS_CopyString((char **)info, "");
3116 } else {
3117 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3118 return (0);
3119 }
3120 }
3121 if (use_info)
3122 ptr = (char **)info;
3123 else if (!(ptr = SDDS_GetParameter(SDDS_dataset, source[i], NULL))) {
3124 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3125 return (0);
3126 }
3127
3128 fptr3 = fptr1;
3129 while (*fptr3) {
3130 if (!(fptr2 = strchr(fptr3, '%'))) {
3131 fprintf(stderr, "Error: invalid sprintf string\n");
3132 return (0);
3133 }
3134 if (*(fptr2 + 1) == '%')
3135 fptr3 = fptr2 + 2;
3136 else if (fptr2 != format && *(fptr2 - 1) == '\\')
3137 fptr3 = fptr2 + 1;
3138 else
3139 break;
3140 }
3141 if (*fptr3 == 0) {
3142 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3143 return (0);
3144 }
3145 if ((fptr2 = strchr(fptr2 + 1, '%')) && i != (sources - 1))
3146 *fptr2 = 0;
3147 else
3148 fptr2 = NULL;
3149 switch (source_type) {
3150 case SDDS_DOUBLE:
3151 sprintf(print_pos, fptr1, *(double *)ptr);
3152 break;
3153 case SDDS_FLOAT:
3154 sprintf(print_pos, fptr1, *(float *)ptr);
3155 break;
3156 case SDDS_LONG64:
3157 sprintf(print_pos, fptr1, *(int64_t *)ptr);
3158 break;
3159 case SDDS_ULONG64:
3160 sprintf(print_pos, fptr1, *(uint64_t *)ptr);
3161 break;
3162 case SDDS_LONG:
3163 sprintf(print_pos, fptr1, *(int32_t *)ptr);
3164 break;
3165 case SDDS_ULONG:
3166 sprintf(print_pos, fptr1, *(uint32_t *)ptr);
3167 break;
3168 case SDDS_SHORT:
3169 sprintf(print_pos, fptr1, *(short *)ptr);
3170 break;
3171 case SDDS_USHORT:
3172 sprintf(print_pos, fptr1, *(unsigned short *)ptr);
3173 break;
3174 case SDDS_CHARACTER:
3175 sprintf(print_pos, fptr1, *(char *)ptr);
3176 break;
3177 case SDDS_STRING:
3178 sprintf(print_pos, fptr1, *(char **)ptr);
3179 free(*ptr);
3180 break;
3181 default:
3182 SDDS_Bomb("error: unknown type encountered--this shouldn't happen (print_parameter_value)");
3183 break;
3184 }
3185 if (!(fptr1 = fptr2))
3186 break;
3187 *fptr1 = '%';
3188 if (!use_info)
3189 free(ptr);
3190 }
3191 if ((target_type == SDDS_STRING &&
3192 !SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, s, -1)) ||
3193 (target_type == SDDS_CHARACTER &&
3194 !SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, s[0], -1))) {
3195 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3196 return (0);
3197 }
3198 return (1);
3199}
3200
3201long print_column_value(SDDS_DATASET *SDDS_dataset, char *target, char **source, long sources, char *format) {
3202 char *print_pos, **ptr, *fptr1, *fptr2 = NULL, *fptr3, *cptr;
3203 long target_index, target_type;
3204 long i;
3205 int64_t j, rows;
3206 static char s[SDDS_MAXLINE];
3207 static long firstCall = 1;
3208 struct {
3209 long source_type, source_index;
3210 short is_parameter, is_column, use_info;
3211 char *info;
3212 } * sourceData;
3213
3214 ptr = NULL;
3215 if ((target_index = SDDS_GetColumnIndex(SDDS_dataset, target)) < 0) {
3216 SDDS_SetError("Unable to find print target");
3217 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3218 return (0);
3219 }
3220 if ((target_type = SDDS_GetColumnType(SDDS_dataset, target_index)) != SDDS_STRING &&
3221 target_type != SDDS_CHARACTER) {
3222 fprintf(stderr, "error: target column %s has wrong type for printing--must be string or character\n", target);
3223 return (0);
3224 }
3225 if ((rows = SDDS_CountRowsOfInterest(SDDS_dataset)) < 0) {
3226 SDDS_SetError("Error counting rows to print.");
3227 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3228 return (0);
3229 }
3230
3231 if (!(sourceData = SDDS_Malloc(sizeof(*sourceData) * sources)))
3232 SDDS_Bomb("Memory allocation failure doing printing.");
3233 for (i = 0; i < sources; i++) {
3234 print_pos = s + strlen(s);
3235 sourceData[i].is_column = sourceData[i].is_parameter =
3236 sourceData[i].use_info = 0;
3237 if (((sourceData[i].source_index = SDDS_GetColumnIndex(SDDS_dataset, source[i])) >= 0) &&
3238 ((sourceData[i].source_type = SDDS_GetColumnType(SDDS_dataset, sourceData[i].source_index)) >= 0))
3239 sourceData[i].is_column = 1;
3240 else if ((sourceData[i].source_index = SDDS_GetParameterIndex(SDDS_dataset, source[i])) >= 0 &&
3241 (sourceData[i].source_type = SDDS_GetParameterType(SDDS_dataset, sourceData[i].source_index)) >= 0)
3242 sourceData[i].is_parameter = 1;
3243 else if ((cptr = strrchr(source[i], '.'))) {
3244 *cptr = 0;
3245 if ((sourceData[i].source_type =
3246 SDDS_GetParameterInformation(SDDS_dataset, cptr + 1, &sourceData[i].info, SDDS_GET_BY_NAME, source[i])))
3247 sourceData[i].is_parameter = 1;
3248 else if ((sourceData[i].source_type =
3249 SDDS_GetColumnInformation(SDDS_dataset, cptr + 1, &sourceData[i].info, SDDS_GET_BY_NAME, source[i])))
3250 sourceData[i].is_column = 1;
3251 else {
3252 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3253 return (0);
3254 }
3255 if (strcmp(cptr + 1, "type") == 0) {
3256 if (sourceData[i].source_type != SDDS_LONG)
3257 return bombre("internal error: type of data-type information is not long", NULL, 0);
3258 SDDS_CopyString((char **)sourceData[i].info, SDDS_type_name[*(long *)sourceData[i].info - 1]);
3259 sourceData[i].source_type = SDDS_STRING;
3260 }
3261 *cptr = '.';
3262 sourceData[i].use_info = 1;
3263 if (sourceData[i].source_type == SDDS_STRING && sourceData[i].info == NULL)
3264 SDDS_CopyString(&sourceData[i].info, "");
3265 } else {
3266 sprintf(s, "Unable to find print source %s.", source[i]);
3267 SDDS_SetError(s);
3268 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3269 return (0);
3270 }
3271 }
3272
3273 for (j = 0; j < rows; j++) {
3274 fptr1 = format;
3275 s[0] = 0;
3276 if (sources == 0)
3277 strcpy(s, format);
3278 for (i = 0; i < sources; i++) {
3279 print_pos = s + strlen(s);
3280 if (sourceData[i].is_column && !sourceData[i].use_info) {
3281 if (!(ptr = SDDS_GetValue(SDDS_dataset, source[i], j, NULL))) {
3282 SDDS_SetError("Unable to get column value for printing");
3283 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3284 return (0);
3285 }
3286 if (!j && firstCall && SDDS_GetParameterIndex(SDDS_dataset, source[i]) >= 0) {
3287 if (*ptr == NULL) {
3288 fprintf(stderr, "error: -print option for column %s uses source %s which is defined\n",
3289 target, source[i]);
3290 fprintf(stderr, "as both a column and a parameter\n");
3291 return (0);
3292 } else {
3293 fprintf(stderr, "warning: -print option for column %s uses source %s which is defined\n",
3294 target, source[i]);
3295 fprintf(stderr, "as both a column and a parameter---column values are used!\n");
3296 }
3297 }
3298 }
3299 if (sourceData[i].is_parameter && !sourceData[i].use_info) {
3300 if (!(ptr = SDDS_GetParameter(SDDS_dataset, source[i], NULL))) {
3301 SDDS_SetError("Unable to get print source parameter value.");
3302 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3303 return (0);
3304 }
3305 }
3306 if (sourceData[i].use_info)
3307 ptr = &sourceData[i].info;
3308 fptr3 = fptr1;
3309 while (*fptr3) {
3310 if (!(fptr2 = strchr(fptr3, '%'))) {
3311 fprintf(stderr, "Error: invalid sprintf string\n");
3312 return (0);
3313 }
3314 if (*(fptr2 + 1) == '%')
3315 fptr3 = fptr2 + 2;
3316 else if (fptr2 != format && *(fptr2 - 1) == '\\')
3317 fptr3 = fptr2 + 1;
3318 else
3319 break;
3320 }
3321 if (*fptr3 == 0) {
3322 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3323 return (0);
3324 }
3325 if ((fptr2 = strchr(fptr2 + 1, '%')) && i != (sources - 1))
3326 *fptr2 = 0;
3327 else
3328 fptr2 = NULL;
3329 switch (sourceData[i].source_type) {
3330 case SDDS_DOUBLE:
3331 sprintf(print_pos, fptr1, *(double *)ptr);
3332 break;
3333 case SDDS_FLOAT:
3334 sprintf(print_pos, fptr1, *(float *)ptr);
3335 break;
3336 case SDDS_LONG64:
3337 sprintf(print_pos, fptr1, *(int64_t *)ptr);
3338 break;
3339 case SDDS_ULONG64:
3340 sprintf(print_pos, fptr1, *(uint64_t *)ptr);
3341 break;
3342 case SDDS_LONG:
3343 sprintf(print_pos, fptr1, *(int32_t *)ptr);
3344 break;
3345 case SDDS_ULONG:
3346 sprintf(print_pos, fptr1, *(uint32_t *)ptr);
3347 break;
3348 case SDDS_SHORT:
3349 sprintf(print_pos, fptr1, *(short *)ptr);
3350 break;
3351 case SDDS_USHORT:
3352 sprintf(print_pos, fptr1, *(unsigned short *)ptr);
3353 break;
3354 case SDDS_CHARACTER:
3355 sprintf(print_pos, fptr1, *(char *)ptr);
3356 break;
3357 case SDDS_STRING:
3358 sprintf(print_pos, fptr1, *(char **)ptr);
3359 if (!sourceData[i].use_info)
3360 free(*ptr);
3361 break;
3362 default:
3363 SDDS_Bomb("error: unknown type encountered--this shouldn't happen (print_column_value)");
3364 break;
3365 }
3366 if (!sourceData[i].use_info)
3367 free(ptr);
3368 if (!(fptr1 = fptr2))
3369 break;
3370 *fptr1 = '%';
3371 }
3372 if ((target_type == SDDS_STRING &&
3373 !SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, j, target_index, s, -1)) ||
3374 (target_type == SDDS_CHARACTER &&
3375 !SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, j, target_index, s[0],
3376 -1))) {
3377 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3378 return (0);
3379 }
3380 }
3381 firstCall = 0;
3382 SDDS_Free(sourceData);
3383 return (1);
3384}
3385
3386FORMAT_DEFINITION *process_new_format_definition(char **argument, long arguments) {
3387 FORMAT_DEFINITION *defi;
3388 unsigned long flags;
3389
3390 if (!(defi = tmalloc(sizeof(*defi))))
3391 SDDS_Bomb("memory allocation failure (process_new_format_definition)");
3392 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
3393 case COLUMN_BASED:
3394 defi->is_parameter = 0;
3395 break;
3396 case PARAMETER_BASED:
3397 defi->is_parameter = 1;
3398 break;
3399 default:
3400 fprintf(stderr, "error: column or parameter must be specified for format\n");
3401 return (NULL);
3402 }
3403 defi->target = argument[1];
3404 defi->source = argument[2];
3405 defi->stringFormat = NULL;
3406 defi->doubleFormat = NULL;
3407 defi->longFormat = NULL;
3408
3409 arguments -= 3;
3410 argument += 3;
3411 if (!scanItemList(&flags, argument, &arguments, 0,
3412 "stringformat", SDDS_STRING, &defi->stringFormat, 1, 0,
3413 "doubleformat", SDDS_STRING, &defi->doubleFormat, 1, 0,
3414 "longformat", SDDS_STRING, &defi->longFormat, 1, 0,
3415 NULL)) {
3416 bomb("invalid -format syntax", NULL);
3417 }
3418 return (defi);
3419}
3420
3421long format_parameter_value(SDDS_DATASET *SDDS_dataset, FORMAT_DEFINITION *definition) {
3422 static char *buffer = NULL;
3423 static long bufferSize = 0;
3424 char *ptr, *doubleFormat, *longFormat, *stringFormat;
3425 long target_index, source_index, bufferRequired;
3426
3427 if ((source_index = SDDS_GetParameterIndex(SDDS_dataset, definition->source)) < 0 || (target_index = SDDS_GetParameterIndex(SDDS_dataset, definition->target)) < 0) {
3428 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3429 return 0;
3430 }
3431 if (SDDS_GetParameterType(SDDS_dataset, source_index) != SDDS_STRING) {
3432 fprintf(stderr, "error: target parameter %s has wrong type for formatting--must be string\n", definition->source);
3433 return 0;
3434 }
3435 if (SDDS_GetParameterType(SDDS_dataset, target_index) != SDDS_STRING) {
3436 fprintf(stderr, "error: target parameter %s has wrong type for formatting--must be string\n", definition->target);
3437 return 0;
3438 }
3439 if (!(ptr = SDDS_GetParameter(SDDS_dataset, definition->source, NULL))) {
3440 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3441 return 0;
3442 }
3443 if ((bufferRequired = 2 * strlen(ptr) + 1024) > bufferSize) {
3444 /* guessing that string won't more than double in length */
3445 bufferSize = bufferRequired;
3446 if (!(buffer = SDDS_Realloc(buffer, sizeof(*buffer) * bufferRequired))) {
3447 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3448 return 0;
3449 }
3450 }
3451
3452 if (!(doubleFormat = definition->doubleFormat))
3453 doubleFormat = "%21.15e";
3454 if (!(longFormat = definition->longFormat))
3455 longFormat = "%ld";
3456 if (!(stringFormat = definition->stringFormat))
3457 stringFormat = "%s";
3458
3459 if (!reformatString(buffer, bufferSize, ptr, stringFormat, doubleFormat, longFormat))
3460 return 0;
3461
3462 if (!SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, buffer, -1)) {
3463 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3464 return 0;
3465 }
3466 return 1;
3467}
3468
3469long reformatString(char *buffer, long bufferSize, char *string, char *stringFormat,
3470 char *doubleFormat, char *longFormat) {
3471 long bufferUseLimit, length, lValue;
3472 double dValue;
3473 char *bufferPosition, *token0, *token1;
3474
3475 bufferPosition = buffer;
3476 *buffer = 0;
3477 bufferUseLimit = bufferSize * 0.9 + 1;
3478
3479 token1 = string;
3480 while ((token0 = strtok(token1, " "))) {
3481 token1 = NULL;
3482
3483 if (tokenIsInteger(token0)) {
3484 if (sscanf(token0, "%ld", &lValue) == 1)
3485 sprintf(bufferPosition, longFormat, lValue);
3486 else {
3487 fprintf(stderr, "Error: problem formatting token %s as long integer.\n", token0);
3488 return 0;
3489 }
3490 } else if (tokenIsNumber(token0)) {
3491 if (sscanf(token0, "%lf", &dValue) == 1)
3492 sprintf(bufferPosition, doubleFormat, dValue);
3493 else {
3494 fprintf(stderr, "Error: problem formatting token %s as double.\n", token0);
3495 return 0;
3496 }
3497 } else
3498 sprintf(bufferPosition, stringFormat, token0);
3499 if ((length = strlen(buffer)) > bufferUseLimit) {
3500 fprintf(stderr, "Error: format buffer overflow (sddsprocess).\n");
3501 return 0;
3502 }
3503 bufferPosition = buffer + length;
3504 *bufferPosition = ' ';
3505 *++bufferPosition = 0;
3506 }
3507 if ((--bufferPosition) >= buffer)
3508 *bufferPosition = 0;
3509 return 1;
3510}
3511
3512long format_column_value(SDDS_DATASET *SDDS_dataset, FORMAT_DEFINITION *definition) {
3513 static char *buffer = NULL;
3514 static long bufferSize = 0;
3515 char **ptr, *longFormat, *doubleFormat, *stringFormat;
3516 long source_index, target_index, bufferRequired;
3517 int64_t row, rows;
3518
3519 if ((source_index = SDDS_GetColumnIndex(SDDS_dataset, definition->source)) < 0 ||
3520 (target_index = SDDS_GetColumnIndex(SDDS_dataset, definition->target)) < 0) {
3521 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3522 return 0;
3523 }
3524 if (SDDS_GetColumnType(SDDS_dataset, source_index) != SDDS_STRING) {
3525 fprintf(stderr, "error: target column %s has wrong type for formatting--must be string\n", definition->source);
3526 return 0;
3527 }
3528 if (SDDS_GetColumnType(SDDS_dataset, target_index) != SDDS_STRING) {
3529 fprintf(stderr, "error: target column %s has wrong type for formatting--must be string\n", definition->target);
3530 return 0;
3531 }
3532 if ((rows = SDDS_CountRowsOfInterest(SDDS_dataset)) < 0) {
3533 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3534 return 0;
3535 }
3536 if (!(ptr = SDDS_GetColumn(SDDS_dataset, definition->source))) {
3537 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3538 return 0;
3539 }
3540
3541 if (!(doubleFormat = definition->doubleFormat))
3542 doubleFormat = "%21.15e";
3543 if (!(longFormat = definition->longFormat))
3544 longFormat = "%ld";
3545 if (!(stringFormat = definition->stringFormat))
3546 stringFormat = "%s";
3547
3548 for (row = 0; row < rows; row++) {
3549 if ((bufferRequired = 2 * strlen(ptr[row]) + 1024) > bufferSize) {
3550 bufferSize = bufferRequired;
3551 if (!(buffer = SDDS_Realloc(buffer, sizeof(*buffer) * bufferRequired))) {
3552 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3553 return 0;
3554 }
3555 }
3556 if (!reformatString(buffer, bufferSize, ptr[row], stringFormat, doubleFormat, longFormat)) {
3557 fprintf(stderr, "Error: problem formatting string >%s< (sddsprocess).\n",
3558 ptr[row]);
3559 return 0;
3560 }
3561 if (!SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, row, target_index, buffer, -1)) {
3562 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3563 return 0;
3564 }
3565 }
3566 return 1;
3567}
3568
3569void add_definition(DEFINITION **definition, long *definitions, void *structure, long type) {
3570 *definition = trealloc(*definition, sizeof(**definition) * (*definitions + 1));
3571 (*definition)[*definitions].structure = structure;
3572 (*definition)[*definitions].type = type;
3573 *definitions += 1;
3574}
3575
3576RPNTEST_DEFINITION *process_new_rpntest_definition(char **argument, long arguments) {
3577 RPNTEST_DEFINITION *defi;
3578 int i, algebraic = 0;
3579 char pfix[IFPF_BUF_SIZE];
3580
3581 if (!(defi = tmalloc(sizeof(*defi))))
3582 SDDS_Bomb("memory allocation failure (process_new_print_definition)");
3583 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
3584 case COLUMN_BASED:
3585 defi->is_parameter = 0;
3586 break;
3587 case PARAMETER_BASED:
3588 defi->is_parameter = 1;
3589 break;
3590 default:
3591 fprintf(stderr, "error: column or parameter must be specified for rpntest\n");
3592 return (NULL);
3593 }
3594 defi->autostop = 0;
3595
3596 for (i = 2; i < arguments; i++) {
3597 if (strncmp(argument[i], "autostop", strlen(argument[i])) == 0)
3598 defi->autostop = 1;
3599 else if (strncmp(argument[i], "algebraic", strlen(argument[i])) == 0)
3600 algebraic = 1;
3601 else
3602 return (NULL);
3603 }
3604 if (algebraic) {
3605 char *ptr;
3606 ptr = addOuterParentheses(argument[1]);
3607 if2pf(pfix, ptr, sizeof pfix);
3608 free(ptr);
3609 if (!SDDS_CopyString(&defi->expression, pfix)) {
3610 fprintf(stderr, "error: problem copying argument string\n");
3611 return NULL;
3612 }
3613 } else
3614 defi->expression = argument[1];
3615 return (defi);
3616}
3617
3618RPNEXPRESSION_DEFINITION *process_new_rpnexpression_definition(char **argument, long arguments) {
3620 int i, algebraic = 0;
3621 char pfix[IFPF_BUF_SIZE];
3622
3623 if (arguments > 2)
3624 return (NULL);
3625 if (!(defi = tmalloc(sizeof(*defi))))
3626 SDDS_Bomb("memory allocation failure (process_new_rpnexpression_definition)");
3627 defi->repeat = 0;
3628
3629 for (i = 1; i < arguments; i++) {
3630 if (strncmp(argument[i], "repeat", strlen(argument[i])) == 0)
3631 defi->repeat = 1;
3632 else if (strncmp(argument[i], "algebraic", strlen(argument[i])) == 0)
3633 algebraic = 1;
3634 else
3635 return NULL;
3636 }
3637 if (algebraic) {
3638 char *ptr;
3639 ptr = addOuterParentheses(argument[0]);
3640 if2pf(pfix, ptr, sizeof pfix);
3641 free(ptr);
3642 if (!SDDS_CopyString(&defi->expression, pfix)) {
3643 fprintf(stderr, "error: problem copying argument string\n");
3644 return NULL;
3645 }
3646 } else
3647 defi->expression = argument[0];
3648 return (defi);
3649}
3650
3651CLIP_DEFINITION *process_new_clip_definition(char **argument, long arguments) {
3652 CLIP_DEFINITION *defi;
3653
3654 if (arguments < 2 || arguments > 3)
3655 return (NULL);
3656 if (!(defi = tmalloc(sizeof(*defi))))
3657 SDDS_Bomb("memory allocation failure (process_new_clip_definition)");
3658 if (sscanf(argument[0], "%" SCNd64, &defi->head) != 1 ||
3659 sscanf(argument[1], "%" SCNd64, &defi->tail) != 1 ||
3660 defi->head < 0 || defi->tail < 0)
3661 return NULL;
3662
3663 defi->invert = 0;
3664 if (arguments == 3) {
3665 if (strncmp(argument[2], "invert", strlen(argument[2])) != 0)
3666 return NULL;
3667 defi->invert = 1;
3668 }
3669 return (defi);
3670}
3671FCLIP_DEFINITION *process_new_fclip_definition(char **argument, long arguments) {
3672 FCLIP_DEFINITION *defi;
3673
3674 if (arguments < 2 || arguments > 3)
3675 return (NULL);
3676 if (!(defi = tmalloc(sizeof(*defi))))
3677 SDDS_Bomb("memory allocation failure (process_new_clip_definition)");
3678 if (sscanf(argument[0], "%le", &defi->fhead) != 1 ||
3679 sscanf(argument[1], "%le", &defi->ftail) != 1 ||
3680 defi->fhead < 0 || defi->ftail < 0)
3681 return NULL;
3682
3683 defi->invert = 0;
3684 if (arguments == 3) {
3685 if (strncmp(argument[2], "invert", strlen(argument[2])) != 0)
3686 return NULL;
3687 defi->invert = 1;
3688 }
3689 return (defi);
3690}
3691SPARSE_DEFINITION *process_new_sparse_definition(char **argument, long arguments) {
3692 SPARSE_DEFINITION *defi;
3693
3694 if (arguments < 1 || arguments > 2)
3695 return (NULL);
3696 if (!(defi = tmalloc(sizeof(*defi))))
3697 SDDS_Bomb("memory allocation failure (process_new_sparse_definition)");
3698 if (sscanf(argument[0], "%" SCNd64, &defi->interval) != 1 || defi->interval <= 0 ||
3699 (arguments == 2 && (sscanf(argument[1], "%" SCNd64, &defi->offset) != 1 || defi->offset < 0)))
3700 return NULL;
3701 return defi;
3702}
3703
3704SAMPLE_DEFINITION *process_new_sample_definition(char **argument, long arguments) {
3705 SAMPLE_DEFINITION *defi;
3706
3707 if (arguments < 1)
3708 return (NULL);
3709 if (!(defi = tmalloc(sizeof(*defi))))
3710 SDDS_Bomb("memory allocation failure (process_new_sample_definition)");
3711 if (sscanf(argument[0], "%lf", &defi->fraction) != 1)
3712 return NULL;
3713 return defi;
3714}
3715
3716SYSTEM_DEFINITION *process_new_system_definition(char **argument, long arguments) {
3717 static char s[SDDS_MAXLINE];
3718 char *ptr;
3719 long i;
3720 SYSTEM_DEFINITION *defi;
3721
3722 if (!(defi = tmalloc(sizeof(*defi))))
3723 SDDS_Bomb("memory allocation failure (process_new_system_definition)");
3724 switch (match_string(argument[0], data_class_keyword, DATA_CLASS_KEYWORDS, 0)) {
3725 case COLUMN_BASED:
3726 defi->is_parameter = 0;
3727 sprintf(s, "&column name=\"%s\", ", argument[1]);
3728 break;
3729 case PARAMETER_BASED:
3730 defi->is_parameter = 1;
3731 sprintf(s, "&parameter name=\"%s\", ", argument[1]);
3732 break;
3733 default:
3734 fprintf(stderr, "error: column or parameter must be specified for system\n");
3735 return (NULL);
3736 }
3737 defi->new_name = argument[1];
3738 defi->source = argument[2];
3739 for (i = 3; i < arguments; i++) {
3740 if (!(ptr = strchr(argument[i], '=')))
3741 return (NULL);
3742 *ptr = 0;
3743 if (strcmp(argument[i], "type") == 0)
3744 continue;
3745 strcat(s, argument[i]);
3746 strcat(s, "=\"");
3747 strcat(s, ptr + 1);
3748 strcat(s, "\", ");
3749 }
3750 strcat(s, " type=string &end");
3751 if (!SDDS_CopyString(&defi->text, s))
3752 SDDS_Bomb("unable to copy text of system definition (process_new_system_definition)");
3753 return (defi);
3754}
3755
3756long system_column_value(SDDS_DATASET *SDDS_dataset, char *target, char *source) {
3757 char **source_value, *command;
3758 int64_t i, rows;
3759 long target_index, source_index;
3760 static char s[SDDS_MAXLINE];
3761
3762 if ((source_index = SDDS_GetColumnIndex(SDDS_dataset, source)) < 0 ||
3763 (target_index = SDDS_GetColumnIndex(SDDS_dataset, target)) < 0) {
3764 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3765 return (0);
3766 }
3767 if (SDDS_GetColumnType(SDDS_dataset, source_index) != SDDS_STRING) {
3768 fprintf(stderr, "error: source column %s has wrong type for system call--must be string\n", source);
3769 return (0);
3770 }
3771 if (SDDS_GetColumnType(SDDS_dataset, target_index) != SDDS_STRING) {
3772 fprintf(stderr, "error: target column %s has wrong type for system call--must be string\n", target);
3773 return (0);
3774 }
3775
3776 if ((rows = SDDS_CountRowsOfInterest(SDDS_dataset)) < 0) {
3777 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3778 return (0);
3779 }
3780
3781 if (!(source_value = SDDS_GetInternalColumn(SDDS_dataset, source))) {
3782 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3783 return (0);
3784 }
3785
3786 for (i = 0; i < rows; i++) {
3787 s[0] = 0;
3788 if ((command = source_value[i]) && !run_on_pipe(command, s, SDDS_MAXLINE)) {
3789 sprintf(s, "Problem with subprocess call (system_column_value)---command was\n%s\n",
3790 command);
3791 SDDS_SetError(s);
3792 return (0);
3793 }
3794 if (!SDDS_SetRowValues(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, i, target_index, s, -1)) {
3795 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3796 return (0);
3797 }
3798 }
3799 return (1);
3800}
3801
3802long system_parameter_value(SDDS_DATASET *SDDS_dataset, char *target, char *source) {
3803 char *command, **ptr;
3804 long target_index, source_index;
3805 static char s[SDDS_MAXLINE];
3806
3807 if ((source_index = SDDS_GetParameterIndex(SDDS_dataset, source)) < 0 ||
3808 (target_index = SDDS_GetParameterIndex(SDDS_dataset, target)) < 0) {
3809 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3810 return (0);
3811 }
3812 if (SDDS_GetParameterType(SDDS_dataset, source_index) != SDDS_STRING) {
3813 fprintf(stderr, "error: source parameter %s has wrong type for system call--must be string\n", source);
3814 return (0);
3815 }
3816 if (SDDS_GetParameterType(SDDS_dataset, target_index) != SDDS_STRING) {
3817 fprintf(stderr, "error: target parameter %s has wrong type for system call--must be string\n", target);
3818 return (0);
3819 }
3820
3821 if (!(ptr = SDDS_GetParameter(SDDS_dataset, source, NULL))) {
3822 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3823 return (0);
3824 }
3825 s[0] = 0;
3826 if ((command = *ptr) && !run_on_pipe(command, s, SDDS_MAXLINE)) {
3827 sprintf(s, "Problem with subprocess call (system_parameter_value)---command was\n%s\n",
3828 command);
3829 SDDS_SetError(s);
3830 return (0);
3831 }
3832 if (!SDDS_SetParameters(SDDS_dataset, SDDS_SET_BY_INDEX | SDDS_PASS_BY_VALUE, target_index, s, -1)) {
3833 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3834 return (0);
3835 }
3836 if (command)
3837 free(command);
3838 free(ptr);
3839 return (1);
3840}
3841
3842long run_on_pipe(char *command, char *buffer, long buffer_length) {
3843 FILE *fp;
3844 long length;
3845
3846 if (!(fp = popen(command, "r")))
3847 return (0);
3848 buffer[0] = 0;
3849 if (!fgets(buffer, buffer_length, fp)) {
3850 pclose(fp);
3851 return (0);
3852 }
3853 if (buffer[(length = strlen(buffer)) - 1] == '\n')
3854 buffer[length - 1] = 0;
3855 pclose(fp);
3856 return (1);
3857}
3858
3859/* used for redefining parameters using sddsprocess-style commandline arguments */
3860long SDDS_RedefineParameterCL(SDDS_DATASET *SDDS_dataset, char *parameter, char **argv, long argc) {
3861 char *value, *keyword;
3862 long i;
3863
3864 for (i = 0; i < argc; i++) {
3865 keyword = argv[i];
3866 if (!(value = strchr(argv[i], '='))) {
3867 fprintf(stderr, "error: missing = in qualifier string for redefine: %s\n", argv[i]);
3868 return (0);
3869 }
3870 *value++ = 0;
3871 if (!SDDS_ChangeParameterInformation(SDDS_dataset, keyword, value, SDDS_PASS_BY_STRING | SDDS_SET_BY_NAME,
3872 parameter)) {
3873 fprintf(stderr, "Problem redefining %s for %s\n",
3874 keyword, parameter);
3875 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3876 return (0);
3877 }
3878 *--value = '=';
3879 }
3880 return (1);
3881}
3882
3883/* used for redefining columns using sddsprocess-style commandline arguments */
3884long SDDS_RedefineColumnCL(SDDS_DATASET *SDDS_dataset, char *column, char **argv, long argc) {
3885 char *value, *keyword;
3886 long i;
3887
3888 for (i = 0; i < argc; i++) {
3889 keyword = argv[i];
3890 if (!(value = strchr(argv[i], '='))) {
3891 fprintf(stderr, "error: missing = in qualifier string for redefine: %s\n", argv[i]);
3892 return (0);
3893 }
3894 *value++ = 0;
3895 if (!SDDS_ChangeColumnInformation(SDDS_dataset, keyword, value, SDDS_PASS_BY_STRING | SDDS_SET_BY_NAME,
3896 column)) {
3897 fprintf(stderr, "Problem redefining %s for %s\n",
3898 keyword, column);
3899 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3900 return (0);
3901 }
3902 *--value = '=';
3903 }
3904 return (1);
3905}
3906
3907long add_sddsfile_arguments(SCANNED_ARG **scanned, int argc) {
3908 long iarg, datacode, index, argc_got;
3909 int64_t j;
3910 SDDS_DATASET dataset;
3911 static char *choice[2] = {"column", "parameter"};
3912 char *dataname, *filename, **argv_got;
3913 SCANNED_ARG *sa_got;
3914
3915 index = 0;
3916
3917 argv_got = NULL;
3918 for (iarg = 0; iarg < argc; iarg++) {
3919 if (!((*scanned)[iarg].arg_type == OPTION) ||
3920 strcmp((*scanned)[iarg].list[0], "getargs") != 0 ||
3921 (*scanned)[iarg].n_items != 3 ||
3922 !(dataname = strchr((*scanned)[iarg].list[2], '=')) || (*dataname++ = 0) ||
3923 ((datacode = match_string((*scanned)[iarg].list[2], choice, 2, 0)) < 0))
3924 continue;
3925 filename = (*scanned)[iarg].list[1];
3926 if (!SDDS_InitializeInput(&dataset, filename))
3927 continue;
3928 if ((datacode == 0 && (index = SDDS_GetColumnIndex(&dataset, dataname)) < 0) ||
3929 (datacode == 1 && (index = SDDS_GetParameterIndex(&dataset, dataname)) < 0)) {
3930 fprintf(stderr, "error: %s %s not found in file %s--can't process -getargs request\n",
3931 choice[datacode], dataname, filename);
3932 /* SDDS_Terminate(&dataset); */
3933 exit(1);
3934 }
3935 if ((datacode == 0 && SDDS_GetColumnType(&dataset, index) != SDDS_STRING) ||
3936 (datacode == 1 && SDDS_GetParameterType(&dataset, index) != SDDS_STRING)) {
3937 fprintf(stderr, "error: %s %s from file %s does not have string type--can't use for -getargs\n",
3938 choice[datacode], dataname, filename);
3939 /* SDDS_Terminate(&dataset); */
3940 exit(1);
3941 }
3942
3943 argc_got = 0;
3944 switch (datacode) {
3945 case 0:
3946 while (SDDS_ReadPage(&dataset) > 0) {
3947 char **column;
3948 int64_t rows;
3949 if ((rows = SDDS_CountRowsOfInterest(&dataset)) <= 0)
3950 continue;
3951 if (!(column = SDDS_GetColumn(&dataset, dataname)))
3952 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
3953 argv_got = trealloc(argv_got, sizeof(*argv_got) * (rows + argc_got));
3954 for (j = 0; j < rows; j++) {
3955 delete_chars(column[j], "\"");
3956 argv_got[argc_got + j] = column[j];
3957 }
3958 free(column);
3959 argc_got += j;
3960 }
3961 break;
3962 case 1:
3963 while (SDDS_ReadPage(&dataset) > 0) {
3964 char *parameter;
3965 if (!SDDS_GetParameter(&dataset, dataname, &parameter))
3966 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
3967 argv_got = trealloc(argv_got, sizeof(*argv_got) * (argc_got + 1));
3968 argv_got[argc_got] = parameter;
3969 argc_got += 1;
3970 }
3971 break;
3972 default:
3973 break;
3974 }
3975 SDDS_Terminate(&dataset);
3976 argc_got = scanargsg(&sa_got, argc_got, argv_got);
3977 *scanned = trealloc(*scanned, sizeof(**scanned) * (argc + argc_got));
3978 if (argc_got > 1)
3979 for (j = argc - 1; j > iarg; j--)
3980 (*scanned)[j + argc_got - 1] = (*scanned)[j];
3981 for (j = 0; j < argc_got; j++)
3982 (*scanned)[j + iarg] = sa_got[j];
3983 argc += argc_got - 1;
3984 iarg += argc_got - 1;
3985 }
3986 return argc;
3987}
3988
3989long ParameterScansAsNumber(SDDS_DATASET *dataset, char *name, short invert) {
3990 char **ptr;
3991 double value;
3992 if (SDDS_CheckParameter(dataset, name, NULL, SDDS_STRING, stderr) != SDDS_CHECK_OKAY) {
3993 fprintf(stderr, "Error: parameter %s nonexistent or not string type---can't use with -numberTest\n",
3994 name);
3995 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
3996 exit(1);
3997 }
3998 if (!(ptr = SDDS_GetParameter(dataset, name, NULL))) {
3999 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
4000 exit(1);
4001 }
4002 if (sscanf(*ptr, "%lf", &value) != 1) {
4003 free(*ptr);
4004 return invert;
4005 }
4006 free(*ptr);
4007 return !invert;
4008}
4009
4010long cast_column_value(SDDS_DATASET *SDDS_dataset, CAST_DEFINITION *cast) {
4011 char **source_value, **target_value;
4012 long target_index, source_index, size;
4013 int64_t i, rows;
4014 long source_type, target_type;
4015 char s[1024];
4016
4017 if ((source_index = SDDS_GetColumnIndex(SDDS_dataset, cast->source)) < 0 ||
4018 (target_index = SDDS_GetColumnIndex(SDDS_dataset, cast->newName)) < 0) {
4019 sprintf(s, "Unable to cast %s to %s--column not found", cast->source,
4020 cast->newName);
4021 SDDS_SetError(s);
4022 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
4023 return (0);
4024 }
4025 source_type = SDDS_GetColumnType(SDDS_dataset, source_index);
4026 if (!SDDS_NUMERIC_TYPE(source_type)) {
4027 sprintf(s, "source column %s has wrong type for casting--must be number\n",
4028 cast->source);
4029 SDDS_SetError(s);
4030 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
4031 return (0);
4032 }
4033
4034 target_type = SDDS_GetColumnType(SDDS_dataset, target_index);
4035 if (!SDDS_NUMERIC_TYPE(target_type)) {
4036 sprintf(s, "target column %s has wrong type for casting--must be number\n",
4037 cast->newName);
4038 SDDS_SetError(s);
4039 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
4040 return (0);
4041 }
4042
4043 if ((rows = SDDS_CountRowsOfInterest(SDDS_dataset)) < 0) {
4044 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
4045 return (0);
4046 }
4047
4048 if (!(source_value = SDDS_GetInternalColumn(SDDS_dataset, cast->source))) {
4049 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
4050 return (0);
4051 }
4052 if (!(target_value = SDDS_GetInternalColumn(SDDS_dataset, cast->newName))) {
4053 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
4054 return (0);
4055 }
4056 size = SDDS_GetTypeSize(target_type);
4057 for (i = 0; i < rows; i++) {
4058 if (!SDDS_CastValue(source_value, i, source_type, target_type,
4059 (void *)((char *)target_value + size * i))) {
4060 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
4061 return (0);
4062 }
4063 }
4064 return (1);
4065}
4066
4067long cast_parameter_value(SDDS_DATASET *SDDS_dataset, CAST_DEFINITION *cast) {
4068 double doubleValue;
4069 int32_t targetIndex, sourceIndex;
4070 static char s[SDDS_MAXLINE];
4071
4072 if ((sourceIndex = SDDS_GetParameterIndex(SDDS_dataset, cast->source)) < 0 ||
4073 (targetIndex = SDDS_GetParameterIndex(SDDS_dataset, cast->newName)) < 0) {
4074 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
4075 return (0);
4076 }
4077 if (!SDDS_NUMERIC_TYPE(SDDS_GetParameterType(SDDS_dataset, sourceIndex))) {
4078 sprintf(s, "error: source parameter %s has wrong type for casting--must be number\n",
4079 cast->source);
4080 SDDS_SetError(s);
4081 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
4082 return (0);
4083 }
4084 if (!SDDS_NUMERIC_TYPE(SDDS_GetParameterType(SDDS_dataset, targetIndex))) {
4085 fprintf(stderr, "error: target parameter %s has wrong type for casting--must be number\n",
4086 cast->newName);
4087 return (0);
4088 }
4089
4090 if (!SDDS_GetParameterAsDouble(SDDS_dataset, cast->source, &doubleValue)) {
4091 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
4092 return (0);
4093 }
4094
4095 if (!SDDS_SetParametersFromDoubles(SDDS_dataset,
4096 SDDS_BY_INDEX | SDDS_PASS_BY_VALUE,
4097 targetIndex, doubleValue, -1)) {
4098 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
4099 return (0);
4100 }
4101 return (1);
4102}
4103
4104char *addOuterParentheses(char *arg) {
4105 char *ptr;
4106 ptr = tmalloc(sizeof(*ptr) * (strlen(arg) + 2));
4107 sprintf(ptr, "(%s)", arg);
4108 return ptr;
4109}
4110
4111void GillMillerIntegration1(double *indepData, double *data, long n_data, double *result) {
4112 double *integral;
4113 integral = tmalloc(sizeof(*integral) * n_data);
4114 GillMillerIntegration(integral, NULL, data, indepData, n_data);
4115 *result = integral[n_data - 1];
4116 free(integral);
4117}
int GillMillerIntegration(double *integral, double *error, double *f, double *x, long n)
Performs numerical integration using the Gill-Miller method.
SDDS (Self Describing Data Set) Data Types Definitions and Function Prototypes.
char * SDDS_type_name[SDDS_NUM_TYPES]
Array of supported data type names.
Definition SDDS_data.c:43
int32_t SDDS_SetRowValues(SDDS_DATASET *SDDS_dataset, int32_t mode, int64_t row,...)
int32_t SDDS_SetParametersFromDoubles(SDDS_DATASET *SDDS_dataset, int32_t mode,...)
int32_t SDDS_SetParameters(SDDS_DATASET *SDDS_dataset, int32_t mode,...)
int32_t * SDDS_GetParameterAsLong(SDDS_DATASET *SDDS_dataset, char *parameter_name, int32_t *memory)
Retrieves the value of a specified parameter as a 32-bit integer from the current data table of a dat...
void * SDDS_GetColumn(SDDS_DATASET *SDDS_dataset, char *column_name)
Retrieves a copy of the data for a specified column, including only rows marked as "of interest".
double * SDDS_GetParameterAsDouble(SDDS_DATASET *SDDS_dataset, char *parameter_name, double *memory)
Retrieves the value of a specified parameter as a double from the current data table of an SDDS datas...
int64_t SDDS_CountRowsOfInterest(SDDS_DATASET *SDDS_dataset)
Counts the number of rows marked as "of interest" in the current data table.
void * SDDS_GetInternalColumn(SDDS_DATASET *SDDS_dataset, char *column_name)
Retrieves an internal pointer to the data of a specified column, including all rows.
void * SDDS_GetParameter(SDDS_DATASET *SDDS_dataset, char *parameter_name, void *memory)
Retrieves the value of a specified parameter from the current data table of a data set.
void * SDDS_GetValue(SDDS_DATASET *SDDS_dataset, char *column_name, int64_t srow_index, void *memory)
Retrieves the value from a specified column and selected row, optionally storing it in provided memor...
double * SDDS_GetColumnInDoubles(SDDS_DATASET *SDDS_dataset, char *column_name)
Retrieves the data of a specified numerical column as an array of doubles, considering only rows mark...
int32_t SDDS_ChangeParameterInformation(SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
Modifies a specific field in a parameter definition within the SDDS dataset.
Definition SDDS_info.c:485
int32_t SDDS_GetParameterInformation(SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
Retrieves information about a specified parameter in the SDDS dataset.
Definition SDDS_info.c:117
int32_t SDDS_ChangeColumnInformation(SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
Modifies a specific field in a column definition within the SDDS dataset.
Definition SDDS_info.c:364
int32_t SDDS_GetColumnInformation(SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
Retrieves information about a specified column in the SDDS dataset.
Definition SDDS_info.c:41
int32_t SDDS_InitializeInput(SDDS_DATASET *SDDS_dataset, char *filename)
Definition SDDS_input.c:49
int32_t SDDS_Terminate(SDDS_DATASET *SDDS_dataset)
int32_t SDDS_ReadPage(SDDS_DATASET *SDDS_dataset)
int32_t SDDS_ProcessParameterString(SDDS_DATASET *SDDS_dataset, char *string, int32_t mode)
Process a parameter definition string.
int32_t SDDS_ParseNamelist(void *data, SDDS_FIELD_INFORMATION *fieldInfo, int32_t fieldInfos, char *s)
Parse a namelist string and populate the corresponding data structure.
int32_t SDDS_TransferColumnDefinition(SDDS_DATASET *target, SDDS_DATASET *source, char *name, char *newName)
Transfers a column definition from a source dataset to a target dataset.
int32_t SDDS_TransferParameterDefinition(SDDS_DATASET *target, SDDS_DATASET *source, char *name, char *newName)
Transfers a parameter definition from a source dataset to a target dataset.
void SDDS_SetError(char *error_text)
Records an error message in the SDDS error stack.
Definition SDDS_utils.c:379
int32_t SDDS_GetParameterType(SDDS_DATASET *SDDS_dataset, int32_t index)
Retrieves the data type of a parameter in the SDDS dataset by its index.
int32_t SDDS_GetArrayIndex(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the index of a named array in the SDDS dataset.
PARAMETER_DEFINITION * SDDS_GetParameterDefinition(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the definition of a specified parameter from the SDDS dataset.
int32_t SDDS_FreeParameterDefinition(PARAMETER_DEFINITION *source)
Frees memory allocated for a parameter definition.
int32_t SDDS_GetParameterIndex(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the index of a named parameter in the SDDS dataset.
int32_t SDDS_GetColumnIndex(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the index of a named column in the SDDS dataset.
int32_t SDDS_MatchParameters(SDDS_DATASET *SDDS_dataset, char ***nameReturn, int32_t matchMode, int32_t typeMode,...)
Matches and retrieves parameter names from an SDDS dataset based on specified criteria.
void * SDDS_CastValue(void *data, int64_t index, int32_t data_type, int32_t desired_type, void *memory)
Casts a value from one SDDS data type to another.
void SDDS_PrintErrors(FILE *fp, int32_t mode)
Prints recorded error messages to a specified file stream.
Definition SDDS_utils.c:432
int32_t SDDS_CopyStringArray(char **target, char **source, int64_t n_strings)
Copies an array of strings from source to target.
void * SDDS_Malloc(size_t size)
Allocates memory of a specified size.
Definition SDDS_utils.c:639
int32_t SDDS_IdentifyType(char *typeName)
Identifies the SDDS data type based on its string name.
int32_t SDDS_GetTypeSize(int32_t type)
Retrieves the size in bytes of a specified SDDS data type.
int32_t SDDS_StringIsBlank(char *s)
Checks if a string is blank (contains only whitespace characters).
int32_t SDDS_MatchColumns(SDDS_DATASET *SDDS_dataset, char ***nameReturn, int32_t matchMode, int32_t typeMode,...)
Matches and retrieves column names from an SDDS dataset based on specified criteria.
int32_t SDDS_GetColumnType(SDDS_DATASET *SDDS_dataset, int32_t index)
Retrieves the data type of a column in the SDDS dataset by its index.
void SDDS_Bomb(char *message)
Terminates the program after printing an error message and recorded errors.
Definition SDDS_utils.c:342
int32_t SDDS_CheckParameter(SDDS_DATASET *SDDS_dataset, char *name, char *units, int32_t type, FILE *fp_message)
Checks if a parameter exists in the SDDS dataset with the specified name, units, and type.
int32_t SDDS_CopyString(char **target, const char *source)
Copies a source string to a target string with memory allocation.
Definition SDDS_utils.c:856
void * SDDS_Realloc(void *old_ptr, size_t new_size)
Reallocates memory to a new size.
Definition SDDS_utils.c:677
int32_t SDDS_PrintTypedValue(void *data, int64_t index, int32_t type, char *format, FILE *fp, uint32_t mode)
Prints a data value of a specified type using an optional printf format string.
Definition SDDS_utils.c:59
void SDDS_Free(void *mem)
Free memory previously allocated by SDDS_Malloc.
Definition SDDS_utils.c:655
COLUMN_DEFINITION * SDDS_GetColumnDefinition(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the definition of a specified column from the SDDS dataset.
Definition SDDS_utils.c:978
Header file for routines used by SDDS command-line applications.
long edit_string(char *text, char *edit)
Edits the provided text based on the specified edit commands.
Definition edit_string.c:75
#define SDDS_NUM_TYPES
Total number of defined SDDS data types.
Definition SDDStypes.h:97
#define SDDS_ULONG
Identifier for the unsigned 32-bit integer data type.
Definition SDDStypes.h:67
#define SDDS_FLOAT
Identifier for the float data type.
Definition SDDStypes.h:43
#define SDDS_STRING
Identifier for the string data type.
Definition SDDStypes.h:85
#define SDDS_ULONG64
Identifier for the unsigned 64-bit integer data type.
Definition SDDStypes.h:55
#define SDDS_LONG
Identifier for the signed 32-bit integer data type.
Definition SDDStypes.h:61
#define SDDS_SHORT
Identifier for the signed short integer data type.
Definition SDDStypes.h:73
#define SDDS_CHARACTER
Identifier for the character data type.
Definition SDDStypes.h:91
#define SDDS_USHORT
Identifier for the unsigned short integer data type.
Definition SDDStypes.h:79
#define SDDS_DOUBLE
Identifier for the double data type.
Definition SDDStypes.h:37
#define SDDS_NUMERIC_TYPE(type)
Checks if the given type identifier corresponds to any numeric type.
Definition SDDStypes.h:138
#define SDDS_LONGDOUBLE
Identifier for the long double data type.
Definition SDDStypes.h:31
#define SDDS_LONG64
Identifier for the signed 64-bit integer data type.
Definition SDDStypes.h:49
void * trealloc(void *old_ptr, uint64_t size_of_block)
Reallocates a memory block to a new size.
Definition array.c:181
void * tmalloc(uint64_t size_of_block)
Allocates a memory block of the specified size with zero initialization.
Definition array.c:59
void bomb(char *error, char *usage)
Reports error messages to the terminal and aborts the program.
Definition bomb.c:26
long bombre(char *error, char *usage, long return_value)
Reports error messages to the terminal and returns a specified value.
Definition bomb.c:44
int get_double(double *dptr, char *s)
Parses a double value from the given string.
Definition data_scan.c:40
long tokenIsNumber(char *token)
Checks if the given token represents a valid number.
Definition data_scan.c:530
int get_int(int *iptr, char *s)
Parses an integer value from the given string.
Definition data_scan.c:380
long tokenIsInteger(char *token)
Checks if the given token represents a valid integer.
Definition data_scan.c:509
char * delete_chars(char *s, char *t)
Removes all occurrences of characters found in string t from string s.
void edit_strings(char **string, long strings, char *buffer, char *edit)
Applies edit commands to an array of strings.
int index_min_max(int64_t *imin, int64_t *imax, double *list, int64_t n)
Finds the indices of the minimum and maximum values in a list of doubles.
Definition findMinMax.c:116
FILE * fopen_e(char *file, char *open_mode, long mode)
Opens a file with error checking, messages, and aborts.
Definition fopen_e.c:30
char * get_token_tq(char *s, char *ts, char *te, char *qs, char *qe)
Extracts a token from a string with support for multiple delimiter and quotation sets.
long is_blank(char *s)
Determine whether a string is composed entirely of whitespace characters.
Definition is_blank.c:27
double linearCorrelationCoefficient(double *data1, double *data2, short *accept1, short *accept2, long rows, long *count)
Compute the linear correlation coefficient for two data sets.
Definition lincorr.c:32
long unweightedLinearFit(double *xData, double *yData, long nData, double *slope, double *intercept, double *variance)
Performs an unweighted linear fit on the provided data.
Definition linfit.c:37
double getTimeInSecs()
Get the current time in seconds since the Epoch with high resolution.
long computeMode(double *result, double *data, long pts, double binSize, long bins)
Computes the mode of a dataset using histogram binning.
long match_string(char *string, char **option, long n_options, long mode)
Matches a given string against an array of option strings based on specified modes.
int strncmp_case_insensitive(char *s1, char *s2, long n)
Compares up to a specified number of characters of two strings in a case-insensitive manner.
long compute_percentiles(double *position, double *percent, long positions, double *x, long n)
Computes multiple percentiles of an array of doubles.
Definition median.c:84
long compute_median(double *value, double *x, long n)
Computes the median of an array of doubles.
Definition median.c:29
double weightedStDevThreaded(double *y, double *w, long n, long numThreads)
Calculates the weighted standard deviation of an array of doubles using multiple threads.
Definition moments.c:910
double standardDeviationThreaded(double *x, long n, long numThreads)
Calculates the standard deviation of an array of doubles using multiple threads.
Definition moments.c:51
double rmsValueThreaded(double *y, long n, long numThreads)
Calculates the RMS (Root Mean Square) value of an array of doubles using multiple threads.
Definition moments.c:597
double arithmeticAverageThreaded(double *y, long n, long numThreads)
Calculates the arithmetic average of an array of doubles using multiple threads.
Definition moments.c:547
double weightedRMSThreaded(double *y, double *w, long n, long numThreads)
Calculates the weighted RMS (Root Mean Square) value of an array of doubles using multiple threads.
Definition moments.c:774
double meanAbsoluteDeviationThreaded(double *y, long n, long numThreads)
Calculates the mean absolute deviation of an array of doubles using multiple threads.
Definition moments.c:647
double weightedMADThreaded(double *y, double *w, long n, long numThreads)
Calculates the weighted mean absolute deviation of an array of doubles using multiple threads.
Definition moments.c:833
double weightedAverageThreaded(double *y, double *w, long n, long numThreads)
Calculates the weighted average of an array of doubles using multiple threads.
Definition moments.c:715
int scanargsg(SCANNED_ARG **scanned, int argc, char **argv)
Definition scanargs.c:163
long scanItemList(unsigned long *flags, char **item, long *items, unsigned long mode,...)
Scans a list of items and assigns values based on provided keywords and types.
short TimeBreakdownToEpoch(short year, short jDay, short month, short day, double hour, double *epochTime)
Converts a broken-down time into epoch time.
long findTopBaseLevels(double *top, double *base, double *data, int64_t points, long bins, double sigmasRequired)
Finds the top-level and base-level of a dataset.
Definition topbase.c:36
int64_t findCrossingPoint(int64_t start, double *data, int64_t points, double level, long direction, double *indepData, double *location)
Finds the crossing point in the data where the data crosses a specified level.
Definition topbase.c:118
long trapazoidIntegration(double *x, double *y, long n, double *integral)
Computes the integral of a dataset using the trapezoidal rule.
Definition trapInteg.c:29
int has_wildcards(char *template)
Check if a template string contains any wildcard characters.
Definition wild_match.c:498
int wild_match(char *string, char *template)
Determine whether one string is a wildcard match for another.
Definition wild_match.c:49
char * unescape_wildcards(char *template)
Remove escape characters from wildcard characters in a template string.
Definition wild_match.c:534