ARB
adperl.cxx
Go to the documentation of this file.
1 // =============================================================== //
2 // //
3 // File : adperl.cxx //
4 // Purpose : helper functions used by perl interface //
5 // (see ../PERL2ARB) //
6 // //
7 // Institute of Microbiology (Technical University Munich) //
8 // http://www.arb-home.de/ //
9 // //
10 // =============================================================== //
11 
12 #include "gb_local.h"
13 #include "adperl.h"
14 
15 // used by perl interface, see ../PERL2ARB/ARB_ext.c@GBP_croak_function
16 void (*GBP_croak_function)(const char *message) = NULp;
17 
18 static void die(const char *with_last_words) {
19  // raise exception in caller (assuming caller is a perl script)
20 
21  if (GBP_croak_function) {
22  GBP_croak_function(with_last_words);
23  }
24  else {
25  fputs("Warning: GBP_croak_function undefined. terminating..\n", stderr);
26  GBK_terminate(with_last_words);
27  }
28 }
29 
30 // -------------------------------------------
31 // "generic" enum<->string-conversion
32 
33 union known_enum {
34  int as_int;
35 
41 };
42 
43 #define ILLEGAL_VALUE (-666)
44 
45 
46 typedef const char *(*enum2string)(known_enum enumValue);
47 
49  known_enum enumValue, lookupLimit;
50 
51  enumValue.as_int = greaterThan.as_int+1;
52  lookupLimit.as_int = enumValue.as_int+256;
53 
54  while (enumValue.as_int <= lookupLimit.as_int) {
55  const char *valueExists = lookup(enumValue);
56  if (valueExists) return enumValue;
57  enumValue.as_int++;
58  }
59 
60  enumValue.as_int = ILLEGAL_VALUE;
61  return enumValue;
62 }
63 
64 static known_enum first_known_enum_value(known_enum greaterEqualThan, enum2string lookup) {
65  return (lookup(greaterEqualThan))
66  ? greaterEqualThan
67  : next_known_enum_value(greaterEqualThan, lookup);
68 }
69 
70 static known_enum string2enum(const char *string, enum2string lookup, known_enum start) {
71 
72  for (start = first_known_enum_value(start, lookup);
73  start.as_int != ILLEGAL_VALUE;
74  start = next_known_enum_value(start, lookup))
75  {
76  const char *asString = lookup(start);
77  gb_assert(asString);
78  if (strcasecmp(asString, string) == 0) break; // found
79  }
80  return start;
81 }
82 
84  char *allowed = NULp;
85 
86  for (start = first_known_enum_value(start, lookup);
87  start.as_int != ILLEGAL_VALUE;
88  start = next_known_enum_value(start, lookup))
89  {
90  const char *asString = lookup(start);
91  gb_assert(asString);
92 
93  if (allowed) freeset(allowed, GBS_global_string_copy("%s, '%s'", allowed, asString));
94  else allowed = GBS_global_string_copy("'%s'", asString);
95  }
96 
97  if (!allowed) allowed = ARB_strdup("none (this is a bug)");
98 
99  return allowed;
100 }
101 
102 static known_enum string2enum_or_die(const char *enum_name, const char *string, enum2string lookup, known_enum start) {
103  known_enum found = string2enum(string, lookup, start);
104 
105  if (found.as_int == ILLEGAL_VALUE) {
106  char *allowed_values = buildAllowedValuesString(start, lookup);
107  char *usage = GBS_global_string_copy("Error: value '%s' is not a legal %s\n"
108  "Known %ss are: %s",
109  string, enum_name, enum_name, allowed_values);
110  free(allowed_values);
111  die(usage);
112  }
113 
114  return found;
115 }
116 
117 /* --------------------------------------------------------------------------------
118  * conversion declarations for different used enums
119  *
120  * To add a new enum type
121  * - write a function to convert your enum-values into a string (example: GBP_gb_search_types_to_string)
122  * - write a reverse-wrapper (example: GBP_string_to_gb_search_types)
123  *
124  * [Code-Tag: enum_conversion_functions]
125  * see also ../PERLTOOLS/arb_proto_2_xsub.cxx@enum_type_replacement
126  */
127 
128 // ------------------------
129 // GB_SEARCH_TYPE
130 
132  switch (search_type) {
133  case SEARCH_BROTHER: return "brother";
134  case SEARCH_CHILD: return "child";
135  case SEARCH_GRANDCHILD: return "grandchild";
136  case SEARCH_NEXT_BROTHER: return "next_brother";
137  case SEARCH_CHILD_OF_NEXT: return "child_of_next";
138  }
139 
140  return NULp;
141 }
142 
144  known_enum start; start.as_int = 0;
145  known_enum found = string2enum_or_die("search-type", search_mode, CASTSIG(enum2string, GBP_GB_SEARCH_TYPE_2_charPtr), start);
146  return found.search_type;
147 }
148 
149 // ------------------
150 // GB_TYPES
151 
153  switch (type) {
154  case GB_NONE: return "NONE";
155  case GB_BIT: return "BIT";
156  case GB_BYTE: return "BYTE";
157  case GB_INT: return "INT";
158  case GB_FLOAT: return "FLOAT";
159  case GB_BITS: return "BITS";
160  case GB_BYTES: return "BYTES";
161  case GB_INTS: return "INTS";
162  case GB_FLOATS: return "FLOATS";
163  case GB_STRING: return "STRING";
164  case GB_DB: return "CONTAINER";
165 
166  default: break;
167  }
168  return NULp;
169 }
170 
171 GB_TYPES GBP_charPtr_2_GB_TYPES(const char *type_name) {
172  known_enum start; start.as_int = 0;
173  known_enum found = string2enum_or_die("db-type", type_name, CASTSIG(enum2string, GBP_GB_TYPES_2_charPtr), start);
174  return found.db_type;
175 }
176 
177 
178 // ----------------------
179 // GB_UNDO_TYPE
180 
181 const char *GBP_GB_UNDO_TYPE_2_charPtr(GB_UNDO_TYPE undo_type) {
182  switch (undo_type) {
183  case GB_UNDO_UNDO: return "undo";
184  case GB_UNDO_REDO: return "redo";
185 
186  case GB_UNDO_NONE:
187  case GB_UNDO_KILL:
188  case GB_UNDO_UNDO_REDO:
189  break;
190  }
191  return NULp;
192 }
193 
194 GB_UNDO_TYPE GBP_charPtr_2_GB_UNDO_TYPE(const char *undo_type) {
195  known_enum start; start.as_int = 0;
196  known_enum found = string2enum_or_die("undo-type", undo_type, CASTSIG(enum2string, GBP_GB_UNDO_TYPE_2_charPtr), start);
197  return found.undo_type;
198 }
199 
200 
201 // -----------------
202 // GB_CASE
203 
204 const char *GBP_GB_CASE_2_charPtr(GB_CASE sensitivity) {
205  switch (sensitivity) {
206  case GB_IGNORE_CASE: return "ignore_case";
207  case GB_MIND_CASE: return "mind_case";
208  case GB_CASE_UNDEFINED: return "case_undef";
209  }
210  return NULp;
211 }
212 
213 GB_CASE GBP_charPtr_2_GB_CASE(const char *sensitivity) {
214  known_enum start; start.as_int = 0;
215  known_enum found = string2enum_or_die("sensitivity", sensitivity, CASTSIG(enum2string, GBP_GB_CASE_2_charPtr), start);
216  return found.case_sensitivity;
217 }
218 
219 // ---------------------------
220 // GB_alignment_type
221 
223  switch (ali_type) {
224  case GB_AT_RNA: return "RNA";
225  case GB_AT_DNA: return "DNA";
226  case GB_AT_AA: return "AMINO";
227 
228  case GB_AT_UNKNOWN: break;
229  }
230  return NULp;
231 }
232 
234  known_enum start; start.as_int = 0;
235  known_enum found = string2enum_or_die("alignment-type", ali_type, CASTSIG(enum2string, GBP_GB_alignment_type_2_charPtr), start);
236  return found.ali_type;
237 }
238 
239 // -----------------------------------------
240 // wrap functions moved to CORE lib
241 //
242 // As long as CORE lib is not xsub'd, we use wrappers for some
243 // functions used in perl
244 
246  return GB_await_error();
247 }
248 
249 // --------------------
250 // perl panic
251 
253  // called from die() in ../PERL2ARB/ARB.pm@prepare_to_die
255 }
256 
const char * GB_ERROR
Definition: arb_core.h:25
GB_TYPES type
static char * buildAllowedValuesString(known_enum start, enum2string lookup)
Definition: adperl.cxx:83
Definition: arbdb.h:65
int as_int
Definition: adperl.cxx:34
Definition: arbdb.h:69
GB_CASE case_sensitivity
Definition: adperl.cxx:37
const char * GBP_GB_SEARCH_TYPE_2_charPtr(GB_SEARCH_TYPE search_type)
Definition: adperl.cxx:131
GB_alignment_type ali_type
Definition: adperl.cxx:40
GB_TYPES db_type
Definition: adperl.cxx:38
char * ARB_strdup(const char *str)
Definition: arb_string.h:27
static known_enum string2enum(const char *string, enum2string lookup, known_enum start)
Definition: adperl.cxx:70
const char * GBP_GB_TYPES_2_charPtr(GB_TYPES type)
Definition: adperl.cxx:152
#define CASTSIG(sig, cb)
Definition: arbtools.h:120
const char * GBP_GB_CASE_2_charPtr(GB_CASE sensitivity)
Definition: adperl.cxx:204
static HelixNrInfo * start
GB_UNDO_TYPE
Definition: arbdb.h:107
GB_ERROR GB_await_error()
Definition: arb_msg.cxx:353
GB_alignment_type GBP_charPtr_2_GB_alignment_type(const char *ali_type)
Definition: adperl.cxx:233
Definition: arbdb.h:67
Definition: arbdb.h:78
void GBK_terminate(const char *error) __ATTR__NORETURN
Definition: arb_msg.cxx:463
void GBP_prepare_to_die()
Definition: adperl.cxx:252
Definition: arbdb.h:64
void message(char *errortext)
GB_ERROR GBC_await_error()
Definition: adperl.cxx:245
GB_SEARCH_TYPE search_type
Definition: adperl.cxx:36
GB_UNDO_TYPE undo_type
Definition: adperl.cxx:39
GB_SEARCH_TYPE
Definition: arbdb.h:99
GB_CASE
Definition: arb_core.h:30
GB_alignment_type
Definition: arbdb_base.h:61
void(* GBP_croak_function)(const char *message)
Definition: adperl.cxx:16
Definition: arbdb.h:72
fputs(TRACE_PREFIX, stderr)
Definition: arbdb.h:63
#define gb_assert(cond)
Definition: arbdbt.h:11
static void die(const char *with_last_words)
Definition: adperl.cxx:18
static known_enum next_known_enum_value(known_enum greaterThan, enum2string lookup)
Definition: adperl.cxx:48
const char *(* enum2string)(known_enum enumValue)
Definition: adperl.cxx:46
#define NULp
Definition: cxxforward.h:97
const char * GBP_GB_alignment_type_2_charPtr(GB_alignment_type ali_type)
Definition: adperl.cxx:222
GB_UNDO_TYPE GBP_charPtr_2_GB_UNDO_TYPE(const char *undo_type)
Definition: adperl.cxx:194
GB_TYPES
Definition: arbdb.h:62
static known_enum first_known_enum_value(known_enum greaterEqualThan, enum2string lookup)
Definition: adperl.cxx:64
#define ILLEGAL_VALUE
Definition: adperl.cxx:43
Definition: arbdb.h:71
void usage()
Definition: readseq.c:328
GB_TYPES GBP_charPtr_2_GB_TYPES(const char *type_name)
Definition: adperl.cxx:171
void gb_abort_and_close_all_DBs()
Definition: arbdb.cxx:704
const char * GBP_GB_UNDO_TYPE_2_charPtr(GB_UNDO_TYPE undo_type)
Definition: adperl.cxx:181
GB_CASE GBP_charPtr_2_GB_CASE(const char *sensitivity)
Definition: adperl.cxx:213
GB_SEARCH_TYPE GBP_charPtr_2_GB_SEARCH_TYPE(const char *search_mode)
Definition: adperl.cxx:143
static known_enum string2enum_or_die(const char *enum_name, const char *string, enum2string lookup, known_enum start)
Definition: adperl.cxx:102
char * GBS_global_string_copy(const char *templat,...)
Definition: arb_msg.cxx:195
Definition: arbdb.h:66