1 /*  objfdef.c
2 * ===========================================================================
3 *
4 *                            PUBLIC DOMAIN NOTICE
5 *               National Center for Biotechnology Information
6 *
7 *  This software/database is a "United States Government Work" under the
8 *  terms of the United States Copyright Act.  It was written as part of
9 *  the author's official duties as a United States Government employee and
10 *  thus cannot be copyrighted.  This software/database is freely available
11 *  to the public for use. The National Library of Medicine and the U.S.
12 *  Government have not placed any restriction on its use or reproduction.
13 *
14 *  Although all reasonable efforts have been taken to ensure the accuracy
15 *  and reliability of the software and data, the NLM and the U.S.
16 *  Government do not and cannot warrant the performance or results that
17 *  may be obtained by using this software or data. The NLM and the U.S.
18 *  Government disclaim all warranties, express or implied, including
19 *  warranties of performance, merchantability or fitness for any particular
20 *  purpose.
21 *
22 *  Please cite the author in any work or product based on this material.
23 *
24 * ===========================================================================
25 *
26 * File Name:  objfdef.c
27 *
28 * Author:  James Ostell
29 *
30 * Version Creation Date: 9/94
31 *
32 * $Revision: 6.54 $
33 *
34 * File Description:  Object manager for feature definitions
35 *
36 * Modifications:
37 * --------------------------------------------------------------------------
38 * Date       Name        Description of modification
39 * -------  ----------  -----------------------------------------------------
40 *
41 * ==========================================================================
42 */
43 #include <objfdef.h>           /* the features interface */
44 #include <asnfdef.h>        /* the AsnTool header */
45 #include <sequtil.h>
46 #include <explore.h>  /* new public location of SeqMgrGetBestProteinFeature */
47 
48 static Boolean loaded = FALSE;
49 
50 /*****************************************************************************
51 *
52 *   FeatDefAsnLoad()
53 *      requires SeqAsnLoad() to be called first
54 *
55 *****************************************************************************/
FeatDefAsnLoad(void)56 NLM_EXTERN Boolean LIBCALL FeatDefAsnLoad (void)
57 {
58     if (loaded)
59         return TRUE;
60     loaded = TRUE;
61 
62     if ( ! AsnLoad())
63     {
64         loaded = FALSE;
65         return FALSE;
66     }
67     return TRUE;
68 }
69 
70 /*****************************************************************************
71 *
72 *   FeatDef Routines
73 *
74 *****************************************************************************/
75 /*****************************************************************************
76 *
77 *   FeatDefNew()
78 *
79 *****************************************************************************/
FeatDefNew(void)80 NLM_EXTERN FeatDefPtr LIBCALL FeatDefNew (void)
81 {
82     return (FeatDefPtr)MemNew(sizeof(FeatDef));
83 }
84 
85 /*****************************************************************************
86 *
87 *   FeatDefFree(fdp)
88 *       Frees one FeatDef and associated data
89 *
90 *****************************************************************************/
FeatDefFree(FeatDefPtr fdp)91 NLM_EXTERN FeatDefPtr LIBCALL FeatDefFree (FeatDefPtr fdp)
92 {
93     if (fdp == NULL)
94         return (FeatDefPtr)NULL;
95 
96     MemFree(fdp->typelabel);
97     MemFree(fdp->menulabel);
98     return (FeatDefPtr)MemFree(fdp);
99 }
100 
101 /*****************************************************************************
102 *
103 *   FeatDefAsnWrite(fdp, aip, atp)
104 *       atp is the current type (if identifier of a parent struct)
105 *       if atp == NULL, then assumes it stands alone (FeatDef ::=)
106 *
107 *****************************************************************************/
FeatDefAsnWrite(FeatDefPtr fdp,AsnIoPtr aip,AsnTypePtr orig)108 NLM_EXTERN Boolean LIBCALL FeatDefAsnWrite (FeatDefPtr fdp, AsnIoPtr aip, AsnTypePtr orig)
109 {
110     DataVal av;
111     AsnTypePtr atp;
112     Boolean retval = FALSE;
113 
114     if (! loaded)
115     {
116         if (! FeatDefAsnLoad())
117             return FALSE;
118     }
119 
120     if (aip == NULL)
121         return FALSE;
122 
123     atp = AsnLinkType(orig, FEATDEF);   /* link local tree */
124     if (atp == NULL)
125         return FALSE;
126 
127     if (fdp == NULL) { AsnNullValueMsg(aip, atp); goto erret; }
128 
129     MemSet ((Pointer) (&av), 0, sizeof (DataVal));
130 
131     if (! AsnOpenStruct(aip, atp, (Pointer)fdp))
132         goto erret;
133 
134     av.ptrvalue = fdp->typelabel;
135     if (! AsnWrite(aip, FEATDEF_typelabel, &av)) goto erret;
136 
137     av.ptrvalue = fdp->menulabel;
138     if (! AsnWrite(aip, FEATDEF_menulabel, &av)) goto erret;
139 
140     av.intvalue = (Int4)(fdp->featdef_key);
141     if (! AsnWrite(aip, FEATDEF_featdef_key, &av)) goto erret;
142 
143     av.intvalue = (Int4)(fdp->seqfeat_key);
144     if (! AsnWrite(aip, FEATDEF_seqfeat_key, &av)) goto erret;
145 
146     av.intvalue = (Int4)(fdp->entrygroup);
147     if (! AsnWrite(aip, FEATDEF_entrygroup, &av)) goto erret;
148 
149     av.intvalue = (Int4)(fdp->displaygroup);
150     if (! AsnWrite(aip, FEATDEF_displaygroup, &av)) goto erret;
151 
152     av.intvalue = (Int4)(fdp->molgroup);
153     if (! AsnWrite(aip, FEATDEF_molgroup, &av)) goto erret;
154 
155     if (! AsnCloseStruct(aip, atp, (Pointer)fdp))
156         goto erret;
157     retval = TRUE;
158 erret:
159     AsnUnlinkType(orig);       /* unlink local tree */
160     return retval;
161 }
162 
163 /*****************************************************************************
164 *
165 *   FeatDefAsnRead(aip, atp)
166 *       atp is the current type (if identifier of a parent struct)
167 *            assumption is readIdent has occurred
168 *       if atp == NULL, then assumes it stands alone and read ident
169 *            has not occurred.
170 *
171 *****************************************************************************/
FeatDefAsnRead(AsnIoPtr aip,AsnTypePtr orig)172 NLM_EXTERN FeatDefPtr LIBCALL FeatDefAsnRead (AsnIoPtr aip, AsnTypePtr orig)
173 {
174     DataVal av;
175     AsnTypePtr atp, oldtype;
176     FeatDefPtr fdp;
177 
178     if (! loaded)
179     {
180         if (! FeatDefAsnLoad())
181             return (FeatDefPtr)NULL;
182     }
183 
184     if (aip == NULL)
185         return (FeatDefPtr)NULL;
186 
187     if (orig == NULL)           /* FeatDef ::= (self contained) */
188         atp = AsnReadId(aip, amp, FEATDEF);
189     else
190         atp = AsnLinkType(orig, FEATDEF);    /* link in local tree */
191     oldtype = atp;
192     if (atp == NULL)
193         return (FeatDefPtr)NULL;
194 
195     fdp = FeatDefNew();
196     if (fdp == NULL)
197         goto erret;
198 
199     if (AsnReadVal(aip, atp, &av) <= 0) goto erret;    /* read the start struct */
200     while ((atp = AsnReadId(aip, amp, atp)) != oldtype)
201     {
202         if (atp == NULL) goto erret;
203         if (AsnReadVal(aip, atp, &av) <= 0) goto erret;
204         if (atp == FEATDEF_typelabel)
205             fdp->typelabel = (CharPtr)av.ptrvalue;
206         else if (atp == FEATDEF_menulabel)
207             fdp->menulabel = (CharPtr)av.ptrvalue;
208         else if (atp == FEATDEF_featdef_key)
209             fdp->featdef_key = (Uint1)(av.intvalue);
210         else if (atp == FEATDEF_seqfeat_key)
211             fdp->seqfeat_key = (Uint1)(av.intvalue);
212         else if (atp == FEATDEF_entrygroup)
213             fdp->entrygroup = (Uint1)(av.intvalue);
214         else if (atp == FEATDEF_displaygroup)
215             fdp->displaygroup = (Uint1)(av.intvalue);
216         else if (atp == FEATDEF_molgroup)
217             fdp->molgroup = (Uint1)(av.intvalue);
218     }
219     if (AsnReadVal(aip, atp, &av) <= 0) goto erret;   /* end struct */
220 ret:
221     AsnUnlinkType(orig);       /* unlink local tree */
222     return fdp;
223 erret:
224     fdp = FeatDefFree(fdp);
225     goto ret;
226 }
227 
228 /*****************************************************************************
229 *
230 *   FeatDefSetFree(fdp)
231 *       Frees set of FeatDef
232 *
233 *****************************************************************************/
FeatDefSetFree(FeatDefPtr fdp)234 NLM_EXTERN FeatDefPtr LIBCALL FeatDefSetFree (FeatDefPtr fdp)
235 {
236     FeatDefPtr next;
237 
238     while (fdp != NULL)
239     {
240         next = fdp->next;
241         FeatDefFree(fdp);
242         fdp = next;
243     }
244     return (FeatDefPtr)NULL;
245 }
246 
247 /*****************************************************************************
248 *
249 *   FeatDefSetAsnWrite(fdp, aip, atp)
250 *       atp is the current type (if identifier of a parent struct)
251 *       if atp == NULL, then assumes it stands alone (FeatDef ::=)
252 *
253 *****************************************************************************/
FeatDefSetAsnWrite(FeatDefPtr fdp,AsnIoPtr aip,AsnTypePtr orig)254 NLM_EXTERN Boolean LIBCALL FeatDefSetAsnWrite (FeatDefPtr fdp, AsnIoPtr aip, AsnTypePtr orig)
255 {
256     AsnTypePtr atp;
257     Boolean retval = FALSE;
258 
259     if (! loaded)
260     {
261         if (! FeatDefAsnLoad())
262             return FALSE;
263     }
264 
265     if (aip == NULL)
266         return FALSE;
267 
268     atp = AsnLinkType(orig, FEATDEFSET);   /* link local tree */
269     if (atp == NULL)
270         return FALSE;
271 
272     if (fdp == NULL) { AsnNullValueMsg(aip, atp); goto erret; }
273 
274     if (! AsnOpenStruct(aip, atp, (Pointer)fdp))
275         goto erret;
276 
277     while (fdp != NULL)
278     {
279         if (! FeatDefAsnWrite(fdp, aip, FEATDEFSET_E))
280             goto erret;
281         fdp = fdp->next;
282     }
283 
284     if (! AsnCloseStruct(aip, atp, (Pointer)fdp))
285         goto erret;
286     retval = TRUE;
287 erret:
288     AsnUnlinkType(orig);       /* unlink local tree */
289     return retval;
290 }
291 
292 /*****************************************************************************
293 *
294 *   FeatDefSetAsnRead(aip, atp)
295 *       atp is the current type (if identifier of a parent struct)
296 *            assumption is readIdent has occurred
297 *       if atp == NULL, then assumes it stands alone and read ident
298 *            has not occurred.
299 *
300 *****************************************************************************/
FeatDefSetAsnRead(AsnIoPtr aip,AsnTypePtr orig)301 NLM_EXTERN FeatDefPtr LIBCALL FeatDefSetAsnRead (AsnIoPtr aip, AsnTypePtr orig)
302 {
303     DataVal av;
304     AsnTypePtr atp, oldtype;
305     FeatDefPtr fdp, first=NULL, last=NULL;
306 
307     if (! loaded)
308     {
309         if (! FeatDefAsnLoad())
310             return (FeatDefPtr)NULL;
311     }
312 
313     if (aip == NULL)
314         return (FeatDefPtr)NULL;
315 
316     if (orig == NULL)           /* FeatDef ::= (self contained) */
317         atp = AsnReadId(aip, amp, FEATDEFSET);
318     else
319         atp = AsnLinkType(orig, FEATDEFSET);    /* link in local tree */
320     oldtype = atp;
321     if (atp == NULL)
322         return (FeatDefPtr)NULL;
323 
324     if (AsnReadVal(aip, atp, &av) <= 0) goto erret;    /* read the start struct */
325     while ((atp = AsnReadId(aip, amp, atp)) != oldtype)
326     {
327         if (atp == NULL) goto erret;
328         fdp = FeatDefAsnRead(aip, atp);
329         if (fdp == NULL) goto erret;
330         if (first == NULL) first = fdp;
331         if (last != NULL) last->next = fdp;
332         last = fdp;
333     }
334     if (AsnReadVal(aip, atp, &av) <= 0) goto erret;   /* end struct */
335 ret:
336     AsnUnlinkType(orig);       /* unlink local tree */
337     return first;
338 erret:
339     first = FeatDefSetFree(first);
340     goto ret;
341 }
342 
343 /*****************************************************************************
344 *
345 *   FeatDispGroup Routines
346 *
347 *****************************************************************************/
348 /*****************************************************************************
349 *
350 *   FeatDispGroupNew()
351 *
352 *****************************************************************************/
FeatDispGroupNew(void)353 NLM_EXTERN FeatDispGroupPtr LIBCALL FeatDispGroupNew (void)
354 {
355     return (FeatDispGroupPtr)MemNew(sizeof(FeatDispGroup));
356 }
357 
358 /*****************************************************************************
359 *
360 *   FeatDispGroupFree(fdp)
361 *       Frees one FeatDispGroup and associated data
362 *
363 *****************************************************************************/
FeatDispGroupFree(FeatDispGroupPtr fdp)364 NLM_EXTERN FeatDispGroupPtr LIBCALL FeatDispGroupFree (FeatDispGroupPtr fdp)
365 {
366     if (fdp == NULL)
367         return (FeatDispGroupPtr)NULL;
368 
369     MemFree(fdp->groupname);
370     return (FeatDispGroupPtr)MemFree(fdp);
371 }
372 
373 /*****************************************************************************
374 *
375 *   FeatDispGroupAsnWrite(fdp, aip, atp)
376 *       atp is the current type (if identifier of a parent struct)
377 *       if atp == NULL, then assumes it stands alone (FeatDispGroup ::=)
378 *
379 *****************************************************************************/
FeatDispGroupAsnWrite(FeatDispGroupPtr fdp,AsnIoPtr aip,AsnTypePtr orig)380 NLM_EXTERN Boolean LIBCALL FeatDispGroupAsnWrite (FeatDispGroupPtr fdp, AsnIoPtr aip, AsnTypePtr orig)
381 {
382     DataVal av;
383     AsnTypePtr atp;
384     Boolean retval = FALSE;
385 
386     if (! loaded)
387     {
388         if (! FeatDefAsnLoad())
389             return FALSE;
390     }
391 
392     if (aip == NULL)
393         return FALSE;
394 
395     atp = AsnLinkType(orig, FEATDISPGROUP);   /* link local tree */
396     if (atp == NULL)
397         return FALSE;
398 
399     if (fdp == NULL) { AsnNullValueMsg(aip, atp); goto erret; }
400 
401     MemSet ((Pointer) (&av), 0, sizeof (DataVal));
402 
403     if (! AsnOpenStruct(aip, atp, (Pointer)fdp))
404         goto erret;
405 
406     av.intvalue = (Int4)(fdp->groupkey);
407     if (! AsnWrite(aip, FEATDISPGROUP_groupkey, &av)) goto erret;
408 
409     av.ptrvalue = fdp->groupname;
410     if (! AsnWrite(aip, FEATDISPGROUP_groupname, &av)) goto erret;
411 
412     if (! AsnCloseStruct(aip, atp, (Pointer)fdp))
413         goto erret;
414     retval = TRUE;
415 erret:
416     AsnUnlinkType(orig);       /* unlink local tree */
417     return retval;
418 }
419 
420 /*****************************************************************************
421 *
422 *   FeatDispGroupAsnRead(aip, atp)
423 *       atp is the current type (if identifier of a parent struct)
424 *            assumption is readIdent has occurred
425 *       if atp == NULL, then assumes it stands alone and read ident
426 *            has not occurred.
427 *
428 *****************************************************************************/
FeatDispGroupAsnRead(AsnIoPtr aip,AsnTypePtr orig)429 NLM_EXTERN FeatDispGroupPtr LIBCALL FeatDispGroupAsnRead (AsnIoPtr aip, AsnTypePtr orig)
430 {
431     DataVal av;
432     AsnTypePtr atp, oldtype;
433     FeatDispGroupPtr fdp;
434 
435     if (! loaded)
436     {
437         if (! FeatDefAsnLoad())
438             return (FeatDispGroupPtr)NULL;
439     }
440 
441     if (aip == NULL)
442         return (FeatDispGroupPtr)NULL;
443 
444     if (orig == NULL)           /* FeatDispGroup ::= (self contained) */
445         atp = AsnReadId(aip, amp, FEATDISPGROUP);
446     else
447         atp = AsnLinkType(orig, FEATDISPGROUP);    /* link in local tree */
448     oldtype = atp;
449     if (atp == NULL)
450         return (FeatDispGroupPtr)NULL;
451 
452     fdp = FeatDispGroupNew();
453     if (fdp == NULL)
454         goto erret;
455 
456     if (AsnReadVal(aip, atp, &av) <= 0) goto erret;    /* read the start struct */
457     while ((atp = AsnReadId(aip, amp, atp)) != oldtype)
458     {
459         if (atp == NULL) goto erret;
460         if (AsnReadVal(aip, atp, &av) <= 0) goto erret;
461         if (atp == FEATDISPGROUP_groupname)
462             fdp->groupname = (CharPtr)av.ptrvalue;
463         else if (atp == FEATDISPGROUP_groupkey)
464             fdp->groupkey = (Uint1)(av.intvalue);
465     }
466     if (AsnReadVal(aip, atp, &av) <= 0) goto erret;   /* end struct */
467 ret:
468     AsnUnlinkType(orig);       /* unlink local tree */
469     return fdp;
470 erret:
471     fdp = FeatDispGroupFree(fdp);
472     goto ret;
473 }
474 
475 /*****************************************************************************
476 *
477 *   FeatDispGroupSetFree(fdp)
478 *       Frees set of FeatDispGroup
479 *
480 *****************************************************************************/
FeatDispGroupSetFree(FeatDispGroupPtr fdp)481 NLM_EXTERN FeatDispGroupPtr LIBCALL FeatDispGroupSetFree (FeatDispGroupPtr fdp)
482 {
483     FeatDispGroupPtr next;
484 
485     while (fdp != NULL)
486     {
487         next = fdp->next;
488         FeatDispGroupFree(fdp);
489         fdp = next;
490     }
491     return (FeatDispGroupPtr)NULL;
492 }
493 
494 /*****************************************************************************
495 *
496 *   FeatDispGroupSetAsnWrite(fdp, aip, atp)
497 *       atp is the current type (if identifier of a parent struct)
498 *       if atp == NULL, then assumes it stands alone (FeatDispGroup ::=)
499 *
500 *****************************************************************************/
FeatDispGroupSetAsnWrite(FeatDispGroupPtr fdp,AsnIoPtr aip,AsnTypePtr orig)501 NLM_EXTERN Boolean LIBCALL FeatDispGroupSetAsnWrite (FeatDispGroupPtr fdp, AsnIoPtr aip, AsnTypePtr orig)
502 {
503     AsnTypePtr atp;
504     Boolean retval = FALSE;
505 
506     if (! loaded)
507     {
508         if (! FeatDefAsnLoad())
509             return FALSE;
510     }
511 
512     if (aip == NULL)
513         return FALSE;
514 
515     atp = AsnLinkType(orig, FEATDISPGROUPSET);   /* link local tree */
516     if (atp == NULL)
517         return FALSE;
518 
519     if (fdp == NULL) { AsnNullValueMsg(aip, atp); goto erret; }
520 
521     if (! AsnOpenStruct(aip, atp, (Pointer)fdp))
522         goto erret;
523 
524     while (fdp != NULL)
525     {
526         if (! FeatDispGroupAsnWrite(fdp, aip, FEATDISPGROUPSET_E))
527             goto erret;
528         fdp = fdp->next;
529     }
530 
531     if (! AsnCloseStruct(aip, atp, (Pointer)fdp))
532         goto erret;
533     retval = TRUE;
534 erret:
535     AsnUnlinkType(orig);       /* unlink local tree */
536     return retval;
537 }
538 
539 /*****************************************************************************
540 *
541 *   FeatDispGroupSetAsnRead(aip, atp)
542 *       atp is the current type (if identifier of a parent struct)
543 *            assumption is readIdent has occurred
544 *       if atp == NULL, then assumes it stands alone and read ident
545 *            has not occurred.
546 *
547 *****************************************************************************/
FeatDispGroupSetAsnRead(AsnIoPtr aip,AsnTypePtr orig)548 NLM_EXTERN FeatDispGroupPtr LIBCALL FeatDispGroupSetAsnRead (AsnIoPtr aip, AsnTypePtr orig)
549 {
550     DataVal av;
551     AsnTypePtr atp, oldtype;
552     FeatDispGroupPtr fdp, first=NULL, last=NULL;
553 
554     if (! loaded)
555     {
556         if (! FeatDefAsnLoad())
557             return (FeatDispGroupPtr)NULL;
558     }
559 
560     if (aip == NULL)
561         return (FeatDispGroupPtr)NULL;
562 
563     if (orig == NULL)           /* FeatDispGroup ::= (self contained) */
564         atp = AsnReadId(aip, amp, FEATDISPGROUPSET);
565     else
566         atp = AsnLinkType(orig, FEATDISPGROUPSET);    /* link in local tree */
567     oldtype = atp;
568     if (atp == NULL)
569         return (FeatDispGroupPtr)NULL;
570 
571     if (AsnReadVal(aip, atp, &av) <= 0) goto erret;    /* read the start struct */
572     while ((atp = AsnReadId(aip, amp, atp)) != oldtype)
573     {
574         if (atp == NULL) goto erret;
575         fdp = FeatDispGroupAsnRead(aip, atp);
576         if (fdp == NULL) goto erret;
577         if (first == NULL) first = fdp;
578         if (last != NULL) last->next = fdp;
579         last = fdp;
580     }
581     if (AsnReadVal(aip, atp, &av) <= 0) goto erret;   /* end struct */
582 ret:
583     AsnUnlinkType(orig);       /* unlink local tree */
584     return first;
585 erret:
586     first = FeatDispGroupSetFree(first);
587     goto ret;
588 }
589 
590 static FeatDefPtr featdefp = NULL;
591 static FeatDefPtr PNTR featdeflookup = NULL;  /* kludge which assumes featdef_key in order */
592 static Int2 numfdef, numfdispg;
593 static FeatDispGroupPtr featdgp;
594 
595 /*****************************************************************************
596 *
597 *   featDefSetMemStr as last resort embedded version of featdef.prt
598 *
599 *****************************************************************************/
600 
601 #ifndef WIN16
602 static CharPtr featDefSetMemStr = "FeatDefGroupSet ::= {\n" \
603 "groups {\n" \
604 "{ groupkey 0 , groupname \"Unrecognized Features\" } ,\n" \
605 "{ groupkey 1 , groupname \"Genes and Named Regions\" } ,\n" \
606 "{ groupkey 2 , groupname \"Coding Regions and Transcripts\" } ,\n" \
607 "{ groupkey 3 , groupname \"Structural RNAs\" } ,\n" \
608 "{ groupkey 4 , groupname \"Bibliographic and Comments\" } ,\n" \
609 "{ groupkey 5 , groupname \"Sites and Bonds\" } } ,\n" \
610 "defs {\n" \
611 "{ typelabel \"???\" , menulabel \"Unsupported feature\" , featdef-key 0 , seqfeat-key 0 , entrygroup 0 , displaygroup 0 , molgroup both } ,\n" \
612 "{ typelabel \"Gene\" , menulabel \"Gene\" , featdef-key 1 , seqfeat-key 1 , entrygroup 1 , displaygroup 1 , molgroup na } ,\n" \
613 "{ typelabel \"Org\" , menulabel \"Organism\" , featdef-key 2 , seqfeat-key 2 , entrygroup 4 , displaygroup 4 , molgroup both } ,\n" \
614 "{ typelabel \"CDS\" , menulabel \"Coding Region\" , featdef-key 3 , seqfeat-key 3 , entrygroup 2 , displaygroup 2 , molgroup na } ,\n" \
615 "{ typelabel \"Prot\" , menulabel \"Protein Names\" , featdef-key 4 , seqfeat-key 4 , entrygroup 1 , displaygroup 1 , molgroup aa } ,\n" \
616 "{ typelabel \"preRNA\" , menulabel \"Precursor RNA\" , featdef-key 5 , seqfeat-key 5 , entrygroup 2 , displaygroup 2 , molgroup na } ,\n" \
617 "{ typelabel \"mRNA\" , menulabel \"Mature Messenger RNA\" , featdef-key 6 , seqfeat-key 5 , entrygroup 2 , displaygroup 2 , molgroup na } ,\n" \
618 "{ typelabel \"tRNA\" , menulabel \"Transfer RNA\" , featdef-key 7 , seqfeat-key 5 , entrygroup 3 , displaygroup 3 , molgroup na } ,\n" \
619 "{ typelabel \"rRNA\" , menulabel \"Ribosomal RNA\" , featdef-key 8 , seqfeat-key 5 , entrygroup 3 , displaygroup 3 , molgroup na } ,\n" \
620 "{ typelabel \"snRNA\" , menulabel \"Small Nuclear RNA\" , featdef-key 9 , seqfeat-key 5 , entrygroup 0 , displaygroup 3 , molgroup na } ,\n" \
621 "{ typelabel \"scRNA\" , menulabel \"Small Cytoplasmic RNA\" , featdef-key 10 , seqfeat-key 5 , entrygroup 0 , displaygroup 3 , molgroup na } ,\n" \
622 "{ typelabel \"RNA\" , menulabel \"Other Types of RNA\" , featdef-key 11 , seqfeat-key 5 , entrygroup 3 , displaygroup 3 , molgroup na } ,\n" \
623 "{ typelabel \"Cit\" , menulabel \"Bibliographic Citations\" , featdef-key 12 , seqfeat-key 6 , entrygroup 4 , displaygroup 4 , molgroup both } ,\n" \
624 "{ typelabel \"Xref\" , menulabel \"Reference to Another Sequence\" , featdef-key 13 , seqfeat-key 7 , entrygroup 4 , displaygroup 4 , molgroup both } ,\n" \
625 "{ typelabel \"Import\" , menulabel \"Unclassified ImpFeat\" , featdef-key 14 , seqfeat-key 8 , entrygroup 0 , displaygroup 0 , molgroup na } ,\n" \
626 "{ typelabel \"allele\" , menulabel \"Allelic Varient\" , featdef-key 15 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
627 "{ typelabel \"attenuator\" , menulabel \"Attenuator\" , featdef-key 16 , seqfeat-key 8 , entrygroup 0 , displaygroup 5 , molgroup na } ,\n" \
628 "{ typelabel \"C_region\" , menulabel \"Immunoglobin/T-cell receptor constant region\" , featdef-key 17 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
629 "{ typelabel \"CAAT_signal\" , menulabel \"CAAT box\" , featdef-key 18 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
630 "{ typelabel \"CDS\" , menulabel \"Untranslatable coding region\" , featdef-key 19 , seqfeat-key 8 , entrygroup 0 , displaygroup 4 , molgroup na } ,\n" \
631 "{ typelabel \"conflict\" , menulabel \"Sequence determinations differ\" , featdef-key 20 , seqfeat-key 8 , entrygroup 0 , displaygroup 4 , molgroup na } ,\n" \
632 "{ typelabel \"D-loop\" , menulabel \"Displacement Loop\" , featdef-key 21 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
633 "{ typelabel \"D_segment\" , menulabel \"Diversity Segment of Immunoglobin\" , featdef-key 22 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
634 "{ typelabel \"enhancer\" , menulabel \"Enhancer\" , featdef-key 23 , seqfeat-key 8 , entrygroup 0 , displaygroup 5 , molgroup na } ,\n" \
635 "{ typelabel \"exon\" , menulabel \"Exon\" , featdef-key 24 , seqfeat-key 8 , entrygroup 2 , displaygroup 2 , molgroup na } ,\n" \
636 "{ typelabel \"GC_signal\" , menulabel \"GC box\" , featdef-key 25 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
637 "{ typelabel \"iDNA\" , menulabel \"intervening DNA\" , featdef-key 26 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
638 "{ typelabel \"intron\" , menulabel \"Intron\" , featdef-key 27 , seqfeat-key 8 , entrygroup 2 , displaygroup 2 , molgroup na } ,\n" \
639 "{ typelabel \"J_segment\" , menulabel \"IG joining segment\" , featdef-key 28 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
640 "{ typelabel \"LTR\" , menulabel \"Long Terminal Repeat\" , featdef-key 29 , seqfeat-key 8 , entrygroup 1 , displaygroup 1 , molgroup na } ,\n" \
641 "{ typelabel \"mat_peptide\" , menulabel \"Mature Peptide labeled on Nuc Acid\" , featdef-key 30 , seqfeat-key 8 , entrygroup 0 , displaygroup 2 , molgroup na } ,\n" \
642 "{ typelabel \"misc_binding\" , menulabel \"Miscellaneaous binding site\" , featdef-key 31 , seqfeat-key 8 , entrygroup 0 , displaygroup 5 , molgroup na } ,\n" \
643 "{ typelabel \"misc_difference\" , menulabel \"Miscellaneous sequence difference\" , featdef-key 32 , seqfeat-key 8 , entrygroup 0 , displaygroup 4 , molgroup na } ,\n" \
644 "{ typelabel \"misc_feature\" , menulabel \"Miscellaneaous feature\" , featdef-key 33 , seqfeat-key 8 , entrygroup 0 , displaygroup 4 , molgroup na } ,\n" \
645 "{ typelabel \"misc_recomb\" , menulabel \"Miscellaneous recombination\" , featdef-key 34 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
646 "{ typelabel \"misc_RNA\" , menulabel \"Miscellaneous RNA\" , featdef-key 35 , seqfeat-key 8 , entrygroup 0 , displaygroup 3 , molgroup na } ,\n" \
647 "{ typelabel \"misc_signal\" , menulabel \"Miscellaneous signal sequence\" , featdef-key 36 , seqfeat-key 8 , entrygroup 0 , displaygroup 5 , molgroup na } ,\n" \
648 "{ typelabel \"misc_structure\" , menulabel \"Miscellaneous secondary structure\" , featdef-key 37 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
649 "{ typelabel \"modified_base\" , menulabel \"Modified base\" , featdef-key 38 , seqfeat-key 8 , entrygroup 0 , displaygroup 5 , molgroup na } ,\n" \
650 "{ typelabel \"mutation\" , menulabel \"site of mutation in related strain\" , featdef-key 39 , seqfeat-key 8 , entrygroup 0 , displaygroup 5 , molgroup na } ,\n" \
651 "{ typelabel \"N_region\" , menulabel \"Extra na in rearranged IG\" , featdef-key 40 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
652 "{ typelabel \"old_sequence\" , menulabel \"Location of sequence revision\" , featdef-key 41 , seqfeat-key 8 , entrygroup 0 , displaygroup 4 , molgroup na } ,\n" \
653 "{ typelabel \"polyA_signal\" , menulabel \"PolyA addition recognition signal\" , featdef-key 42 , seqfeat-key 8 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
654 "{ typelabel \"polyA_site\" , menulabel \"Point where polyA tail begins\" , featdef-key 43 , seqfeat-key 8 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
655 "{ typelabel \"precursor_RNA\" , menulabel \"RNA which is a post-transcriptional intermediate\" , featdef-key 44 , seqfeat-key 8 , entrygroup 0 , displaygroup 2 , molgroup na } ,\n" \
656 "{ typelabel \"prim_transcript\" , menulabel \"Primary transcript\" , featdef-key 45 , seqfeat-key 8 , entrygroup 0 , displaygroup 2 , molgroup na } ,\n" \
657 "{ typelabel \"primer_bind\" , menulabel \"Primer binding site\" , featdef-key 46 , seqfeat-key 8 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
658 "{ typelabel \"promoter\" , menulabel \"Promoter\" , featdef-key 47 , seqfeat-key 8 , entrygroup 0 , displaygroup 5 , molgroup na } ,\n" \
659 "{ typelabel \"protein_bind\" , menulabel \"Protein binding site\" , featdef-key 48 , seqfeat-key 8 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
660 "{ typelabel \"RBS\" , menulabel \"Ribosome binding site\" , featdef-key 49 , seqfeat-key 8 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
661 "{ typelabel \"repeat_region\" , menulabel \"Region containing repeats\" , featdef-key 50 , seqfeat-key 8 , entrygroup 1 , displaygroup 1 , molgroup na } ,\n" \
662 "{ typelabel \"repeat_unit\" , menulabel \"Single repeat unit\" , featdef-key 51 , seqfeat-key 8 , entrygroup 1 , displaygroup 1 , molgroup na } ,\n" \
663 "{ typelabel \"rep_origin\" , menulabel \"Origin of replication\" , featdef-key 52 , seqfeat-key 8 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
664 "{ typelabel \"S_region\" , menulabel \"IG switch region\" , featdef-key 53 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
665 "{ typelabel \"satellite\" , menulabel \"satellite repeat region\" , featdef-key 54 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
666 "{ typelabel \"sig_peptide\" , menulabel \"Signal Peptide annotated on Nuc Acid\" , featdef-key 55 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
667 "{ typelabel \"source\" , menulabel \"Source of Nuc Acid\" , featdef-key 56 , seqfeat-key 8 , entrygroup 0 , displaygroup 4 , molgroup na } ,\n" \
668 "{ typelabel \"stem_loop\" , menulabel \"Stem loop structure\" , featdef-key 57 , seqfeat-key 8 , entrygroup 1 , displaygroup 1 , molgroup na } ,\n" \
669 "{ typelabel \"STS\" , menulabel \"Sequence tagged site\" , featdef-key 58 , seqfeat-key 8 , entrygroup 1 , displaygroup 1 , molgroup na } ,\n" \
670 "{ typelabel \"TATA_signal\" , menulabel \"TATA box\" , featdef-key 59 , seqfeat-key 8 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
671 "{ typelabel \"terminator\" , menulabel \"Transcription terminator\" , featdef-key 60 , seqfeat-key 8 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
672 "{ typelabel \"transit_peptide\" , menulabel \"Transit peptide annotated on Nuc Acid\" , featdef-key 61 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
673 "{ typelabel \"unsure\" , menulabel \"Unsure of exact sequence\" , featdef-key 62 , seqfeat-key 8 , entrygroup 0 , displaygroup 4 , molgroup na } ,\n" \
674 "{ typelabel \"V_region\" , menulabel \"IG variable region\" , featdef-key 63 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
675 "{ typelabel \"V_segment\" , menulabel \"IG variable segment\" , featdef-key 64 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
676 "{ typelabel \"variation\" , menulabel \"Strain differences\" , featdef-key 65 , seqfeat-key 8 , entrygroup 0 , displaygroup 4 , molgroup na } ,\n" \
677 "{ typelabel \"virion\" , menulabel \"Viral genome\" , featdef-key 66 , seqfeat-key 8 , entrygroup 0 , displaygroup 4 , molgroup na } ,\n" \
678 "{ typelabel \"3'clip\" , menulabel \"3' region of transcript clipped off in processing\" , featdef-key 67 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
679 "{ typelabel \"3'UTR\" , menulabel \"3' untranslated region\" , featdef-key 68 , seqfeat-key 8 , entrygroup 2 , displaygroup 2 , molgroup na } ,\n" \
680 "{ typelabel \"5'clip\" , menulabel \"5' region of transcript clipped off in processing\" , featdef-key 69 , seqfeat-key 8 , entrygroup 0 , displaygroup 1 , molgroup na } ,\n" \
681 "{ typelabel \"5'UTR\" , menulabel \"5' untranslated region\" , featdef-key 70 , seqfeat-key 8 , entrygroup 2 , displaygroup 2 , molgroup na } ,\n" \
682 "{ typelabel \"-10_signal\" , menulabel \"Pribnow box\" , featdef-key 71 , seqfeat-key 8 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
683 "{ typelabel \"-35_signal\" , menulabel \"-35 region of transcription start\" , featdef-key 72 , seqfeat-key 8 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
684 "{ typelabel \"Site-ref\" , menulabel \"SITES type reference\" , featdef-key 73 , seqfeat-key 8 , entrygroup 0 , displaygroup 4 , molgroup na } ,\n" \
685 "{ typelabel \"Region\" , menulabel \"Named region of sequence\" , featdef-key 74 , seqfeat-key 9 , entrygroup 1 , displaygroup 1 , molgroup both } ,\n" \
686 "{ typelabel \"Comment\" , menulabel \"Comment associated with sequence\" , featdef-key 75 , seqfeat-key 10 , entrygroup 4 , displaygroup 4 , molgroup both } ,\n" \
687 "{ typelabel \"Bond\" , menulabel \"Chemical bonds\" , featdef-key 76 , seqfeat-key 11 , entrygroup 5 , displaygroup 5 , molgroup aa } ,\n" \
688 "{ typelabel \"Site\" , menulabel \"Binding/Active Sites\" , featdef-key 77 , seqfeat-key 12 , entrygroup 5 , displaygroup 5 , molgroup both } ,\n" \
689 "{ typelabel \"Rsite\" , menulabel \"Restriction Sites\" , featdef-key 78 , seqfeat-key 13 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
690 "{ typelabel \"User\" , menulabel \"User Defined feature\" , featdef-key 79 , seqfeat-key 14 , entrygroup 0 , displaygroup 4 , molgroup both } ,\n" \
691 "{ typelabel \"TxInit\" , menulabel \"Transcription Initiation Site\" , featdef-key 80 , seqfeat-key 15 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
692 "{ typelabel \"Num\" , menulabel \"Numbering System for Sequence\" , featdef-key 81 , seqfeat-key 16 , entrygroup 4 , displaygroup 4 , molgroup both } ,\n" \
693 "{ typelabel \"SecStr\" , menulabel \"Protein Secondary Structure\" , featdef-key 82 , seqfeat-key 17 , entrygroup 1 , displaygroup 1 , molgroup aa } ,\n" \
694 "{ typelabel \"NonStdRes\" , menulabel \"Non-standard Residue\" , featdef-key 83 , seqfeat-key 18 , entrygroup 5 , displaygroup 5 , molgroup aa } ,\n" \
695 "{ typelabel \"Het\" , menulabel \"Heterogen\" , featdef-key 84 , seqfeat-key 19 , entrygroup 5 , displaygroup 5 , molgroup aa } ,\n" \
696 "{ typelabel \"Src\" , menulabel \"Biological Source\" , featdef-key 85 , seqfeat-key 20 , entrygroup 4 , displaygroup 4 , molgroup both } ,\n" \
697 "{ typelabel \"proprotein\" , menulabel \"Proprotein\" , featdef-key 86 , seqfeat-key 4 , entrygroup 1 , displaygroup 1 , molgroup aa } ,\n" \
698 "{ typelabel \"mat_peptide\" , menulabel \"Mature Peptide\" , featdef-key 87 , seqfeat-key 4 , entrygroup 1 , displaygroup 1 , molgroup aa } ,\n" \
699 "{ typelabel \"sig_peptide\" , menulabel \"Signal Peptide\" , featdef-key 88 , seqfeat-key 4 , entrygroup 1 , displaygroup 1 , molgroup aa } ,\n" \
700 "{ typelabel \"transit_peptide\" , menulabel \"Transit Peptide\" , featdef-key 89 , seqfeat-key 4 , entrygroup 1 , displaygroup 1 , molgroup aa } ,\n" \
701 "{ typelabel \"snoRNA\" , menulabel \"Small Nucleolar RNA\" , featdef-key 90 , seqfeat-key 5 , entrygroup 0 , displaygroup 3 , molgroup na } ,\n" \
702 "{ typelabel \"gap\" , menulabel \"Gap\" , featdef-key 91 , seqfeat-key 8 , entrygroup 0 , displaygroup 4 , molgroup na } ,\n" \
703 "{ typelabel \"operon\" , menulabel \"Operon\" , featdef-key 92 , seqfeat-key 8 , entrygroup 1 , displaygroup 1 , molgroup na } ,\n" \
704 "{ typelabel \"oriT\" , menulabel \"Origin of Transcription\" , featdef-key 93 , seqfeat-key 8 , entrygroup 5 , displaygroup 5 , molgroup na } ,\n" \
705 "{ typelabel \"ncRNA\" , menulabel \"Non-coding RNA\" , featdef-key 94 , seqfeat-key 5 , entrygroup 3 , displaygroup 3 , molgroup na } ,\n" \
706 "{ typelabel \"tmRNA\" , menulabel \"Transfer-messenger RNA\" , featdef-key 95 , seqfeat-key 5 , entrygroup 3 , displaygroup 3 , molgroup na } ,\n" \
707 "{ typelabel \"CloneRef\" , menulabel \"Clone Reference\" , featdef-key 96 , seqfeat-key 21 , entrygroup 0 , displaygroup 0 , molgroup na } ,\n" \
708 "{ typelabel \"VariationRef\" , menulabel \"Variation Reference\" , featdef-key 97 , seqfeat-key 22 , entrygroup 0 , displaygroup 0 , molgroup na } ,\n" \
709 "{ typelabel \"mobile_element\" , menulabel \"Mobile genetic element\" , featdef-key 98 , seqfeat-key 8 , entrygroup 1 , displaygroup 1 , molgroup na } ,\n" \
710 "{ typelabel \"centromere\" , menulabel \"Centromere\" , featdef-key 99 , seqfeat-key 8 , entrygroup 1 , displaygroup 1 , molgroup na } ,\n" \
711 "{ typelabel \"telomere\" , menulabel \"Telomere\" , featdef-key 100 , seqfeat-key 8 , entrygroup 1 , displaygroup 1 , molgroup na } ,\n" \
712 "{ typelabel \"assembly_gap\" , menulabel \"Assembly Gap\" , featdef-key 101 , seqfeat-key 8 , entrygroup 0 , displaygroup 4 , molgroup na } ,\n" \
713 "{ typelabel \"regulatory\" , menulabel \"Regulatory\" , featdef-key 102 , seqfeat-key 8 , entrygroup 1 , displaygroup 1 , molgroup na } ,\n" \
714 "{ typelabel \"propeptide\" , menulabel \"Propeptide labeled on Nuc Acid\" , featdef-key 103 , seqfeat-key 8 , entrygroup 0 , displaygroup 2 , molgroup na } ,\n" \
715 "{ typelabel \"propeptide\" , menulabel \"Propeptide\" , featdef-key 104 , seqfeat-key 4 , entrygroup 1 , displaygroup 1 , molgroup aa } } };\n";
716 #endif
717 
718 /*****************************************************************************
719 *
720 *   FeatDefPtr FeatDefSetLoad()
721 *       loads all current feature defintions
722 *       looks for "featdef.val" in the "data" directory
723 *
724 *****************************************************************************/
FeatDefGroupSetAsnRead(AsnIoPtr aip,AsnTypePtr orig)725 static FeatDefPtr LIBCALL FeatDefGroupSetAsnRead (AsnIoPtr aip, AsnTypePtr orig)
726 {
727     FeatDefPtr fdp;
728     FeatDispGroupPtr fdgp;
729     Int2 i, num;
730     DataVal av;
731     AsnTypePtr atp, oldtype;
732 
733     if (! loaded)
734     {
735         if (! FeatDefAsnLoad())
736             return (FeatDefPtr)NULL;
737     }
738 
739     if (aip == NULL)
740         return (FeatDefPtr)NULL;
741 
742     if (orig == NULL)           /* FeatDefGroupSet ::= (self contained) */
743         atp = AsnReadId(aip, amp, FEATDEFGROUPSET);
744     else
745         atp = AsnLinkType(orig, FEATDEFGROUPSET);    /* link in local tree */
746     oldtype = atp;
747     if (atp == NULL)
748         return (FeatDefPtr)NULL;
749 
750     if (AsnReadVal(aip, atp, &av) <= 0) goto erret;    /* read the start struct */
751     while ((atp = AsnReadId(aip, amp, atp)) != oldtype)
752     {
753         if (atp == NULL) goto erret;
754         if (atp == FEATDEFGROUPSET_groups)
755         {
756             featdgp = FeatDispGroupSetAsnRead(aip, atp);
757             if (featdgp == NULL) goto erret;
758         }
759         else if (atp == FEATDEFGROUPSET_defs)
760         {
761             featdefp = FeatDefSetAsnRead(aip, atp);
762             if (featdefp == NULL) goto erret;
763         }
764     }
765     if (AsnReadVal(aip, atp, &av) <= 0) goto erret;   /* end struct */
766 
767     for (numfdef = 0, fdp = featdefp; fdp != NULL; fdp = fdp->next)
768         numfdef++;
769 
770     num = numfdef;
771     if (num < FEATDEF_MAX) {
772         num = FEATDEF_MAX;
773     }
774     featdeflookup = MemNew((size_t)(sizeof(FeatDefPtr) * num));
775 
776     for (i = 0, fdp = featdefp; fdp != NULL && i < numfdef; fdp = fdp->next, i++)
777         featdeflookup[i] = fdp;
778 
779     for (numfdispg = 0, fdgp = featdgp; fdgp != NULL; fdgp = fdgp->next)
780         numfdispg++;
781 
782 ret:
783     AsnUnlinkType(orig);       /* unlink local tree */
784     return featdefp;
785 erret:
786     featdgp = FeatDispGroupSetFree(featdgp);
787     featdefp = FeatDefSetFree(featdefp);
788     goto ret;
789 }
790 
LoadFeatDefFromLocalString(void)791 static Boolean LoadFeatDefFromLocalString (void)
792 
793 {
794 #ifndef WIN16
795   AsnIoMemPtr aimp;
796 
797   aimp = AsnIoMemOpen ("r", (BytePtr) featDefSetMemStr, (Int4) StringLen (featDefSetMemStr));
798   if (aimp == NULL || aimp->aip == NULL) return FALSE;
799   FeatDefGroupSetAsnRead (aimp->aip, NULL);
800   AsnIoMemClose (aimp);
801 #endif
802   return (Boolean) (featdefp != NULL);
803 }
804 
FeatDefSetLoad(void)805 NLM_EXTERN FeatDefPtr LIBCALL FeatDefSetLoad (void)
806 {
807     Char buf[256];
808     AsnIoPtr aip;
809 
810     if (featdefp != NULL)
811         return featdefp;
812 
813     if (! loaded)
814     {
815         if (! FeatDefAsnLoad())
816             return (FeatDefPtr)NULL;
817     }
818 
819 #ifdef OS_UNIX
820     if (getenv ("USE_FEATDEF_FILE") == NULL) {
821           if (LoadFeatDefFromLocalString ()) {
822               return featdefp;
823           }
824     }
825 #endif
826 
827     if (! FindPath("ncbi", "ncbi", "data", buf, sizeof (buf)))
828     {
829 
830         if (LoadFeatDefFromLocalString ()) {
831             return featdefp;
832         }
833 
834         ErrPost(CTX_NCBIOBJ, 1, "FindPath failed in FeatDefSetTableLoad - ncbi configuration file missing or incorrect");
835         return featdefp;
836     }
837 
838     StringCat(buf, "featdef.val");
839     if ((aip = AsnIoOpen(buf, "rb")) == NULL)
840     {
841 
842         if (LoadFeatDefFromLocalString ()) {
843             return featdefp;
844         }
845 
846         ErrPost(CTX_NCBIOBJ, 1, "Couldn't open [%s]", buf);
847         return featdefp;
848     }
849 
850     FeatDefGroupSetAsnRead (aip, NULL);
851 
852     AsnIoClose(aip);
853     return featdefp;
854 }
855 
856 /*****************************************************************************
857 *
858 *   FindImpFeatType(sfp)
859 *       returns the featdef_key by matching the key of an Imp-feat
860 *       returns FEATDEF_BAD if can't match it
861 *
862 *****************************************************************************/
FindImpFeatType(SeqFeatPtr sfp)863 static Uint1 FindImpFeatType (SeqFeatPtr sfp)
864 {
865     FeatDefPtr PNTR fdpp;
866     FeatDefPtr fdp;
867     ImpFeatPtr ifp;
868     CharPtr tmp;
869     Int2 i;
870 
871     if (sfp == NULL) return FEATDEF_BAD;
872     if (sfp->data.choice != SEQFEAT_IMP) return FEATDEF_BAD;
873 
874     ifp = (ImpFeatPtr)(sfp->data.value.ptrvalue);
875     tmp = ifp->key;
876 
877     if (FeatDefSetLoad() == NULL) return FEATDEF_BAD;
878     fdpp = featdeflookup;
879 
880     for (i = 0; i < numfdef; i++, fdpp++)
881     {
882         fdp = *fdpp;
883         if (fdp != NULL && fdp->seqfeat_key == SEQFEAT_IMP)
884         {
885             if (! StringCmp(fdp->typelabel, tmp))
886                 return fdp->featdef_key;
887         }
888     }
889 
890     return FEATDEF_BAD;
891 }
892 
893 
894 /*****************************************************************************
895 *
896 *   FindFeatDefType(sfp)
897 *       Finds the featdef_type for a SeqFeat
898 *       returns FEATDEF_BAD if can't find it
899 *
900 *****************************************************************************/
FindFeatDefType(SeqFeatPtr sfp)901 NLM_EXTERN Uint1 LIBCALL FindFeatDefType(SeqFeatPtr sfp)
902 {
903     CharPtr     name;
904     ProtRefPtr  prp;
905     RnaRefPtr   rrp;
906 
907     if (sfp == NULL) return FEATDEF_BAD;
908     switch (sfp->data.choice)
909     {
910         case SEQFEAT_GENE:
911             return FEATDEF_GENE;
912         case SEQFEAT_ORG:
913             return FEATDEF_ORG;
914         case SEQFEAT_CDREGION:
915             return FEATDEF_CDS;
916         case SEQFEAT_PROT:
917             prp = (ProtRefPtr)(sfp->data.value.ptrvalue);
918             switch (prp->processed)
919             {
920                 case 0:
921                     return FEATDEF_PROT;
922                 case 1:
923                     return FEATDEF_preprotein;
924                 case 2:
925                     return FEATDEF_mat_peptide_aa;
926                 case 3:
927                     return FEATDEF_sig_peptide_aa;
928                 case 4:
929                     return FEATDEF_transit_peptide_aa;
930                 case 5:
931                     return FEATDEF_propeptide_aa;
932             }
933             return FEATDEF_BAD;
934         case SEQFEAT_RNA:
935             rrp = (RnaRefPtr)(sfp->data.value.ptrvalue);
936             switch (rrp->type)
937             {
938                 case 0:
939                     return FEATDEF_otherRNA; /* unknownRNA mapped to otherRNA */
940                 case 1:
941                     return FEATDEF_preRNA;
942                 case 2:
943                     return FEATDEF_mRNA;
944                 case 3:
945                     return FEATDEF_tRNA;
946                 case 4:
947                     return FEATDEF_rRNA;
948                 case 5:
949                     return FEATDEF_snRNA;
950                 case 6:
951                     return FEATDEF_scRNA;
952                 case 7:
953                     return FEATDEF_snoRNA;
954                 case 8:
955                     return FEATDEF_ncRNA;
956                 case 9:
957                     return FEATDEF_tmRNA;
958                 case 10:
959                     return FEATDEF_otherRNA;
960                 case 255:
961                     if (rrp->ext.choice == 1) {
962                       name = (CharPtr) rrp->ext.value.ptrvalue;
963                       if (StringICmp (name, "misc_RNA") == 0) return FEATDEF_otherRNA;
964                       if (StringICmp (name, "ncRNA") == 0) return FEATDEF_ncRNA;
965                       if (StringICmp (name, "tmRNA") == 0) return FEATDEF_tmRNA;
966                     }
967                     return FEATDEF_otherRNA;
968             }
969             return FEATDEF_BAD;
970         case SEQFEAT_PUB:
971             return FEATDEF_PUB;
972         case SEQFEAT_SEQ:
973             return FEATDEF_SEQ;
974         case SEQFEAT_IMP:
975             return FindImpFeatType(sfp);
976         case SEQFEAT_REGION:
977             return FEATDEF_REGION;
978         case SEQFEAT_COMMENT:
979             return FEATDEF_COMMENT;
980         case SEQFEAT_BOND:
981             return FEATDEF_BOND;
982         case SEQFEAT_SITE:
983             return FEATDEF_SITE;
984         case SEQFEAT_RSITE:
985             return FEATDEF_RSITE;
986         case SEQFEAT_USER:
987             return FEATDEF_USER;
988         case SEQFEAT_TXINIT:
989             return FEATDEF_TXINIT;
990         case SEQFEAT_NUM:
991             return FEATDEF_NUM;
992         case SEQFEAT_PSEC_STR:
993             return FEATDEF_PSEC_STR;
994         case SEQFEAT_NON_STD_RESIDUE:
995             return FEATDEF_NON_STD_RESIDUE;
996         case SEQFEAT_HET:
997             return FEATDEF_HET;
998         case SEQFEAT_BIOSRC:
999             return FEATDEF_BIOSRC;
1000         case SEQFEAT_CLONEREF:
1001             return FEATDEF_CLONEREF;
1002         case SEQFEAT_VARIATIONREF:
1003             return FEATDEF_VARIATIONREF;
1004     }
1005 
1006     return FEATDEF_BAD;
1007 }
1008 
1009 /*****************************************************************************
1010 *
1011 *   FeatDefTypeLabel(sfp)
1012 *       returns the type label for the feature
1013 *       returns NULL if can't find one
1014 *
1015 *****************************************************************************/
FeatDefTypeLabel(SeqFeatPtr sfp)1016 NLM_EXTERN const char * LIBCALL FeatDefTypeLabel(SeqFeatPtr sfp)
1017 {
1018     Int2 i;
1019     FeatDefPtr fdp;
1020 
1021     if (sfp == NULL) return (const char *)NULL;
1022     if (FeatDefSetLoad() == NULL) return (const char *)NULL;
1023 
1024     i = (Int2) FindFeatDefType(sfp);
1025     if (i == FEATDEF_BAD) return NULL;
1026 
1027     fdp = featdeflookup[i];
1028     if (fdp == NULL) return NULL;
1029     return (const char *)(fdp->typelabel);
1030 }
1031 
FeatDefLabelContent(SeqFeatPtr sfp,CharPtr buf,Int2 buflen,Uint1 labeltype,CharPtr typelabel)1032 static Int2 NEAR FeatDefLabelContent (SeqFeatPtr sfp, CharPtr buf, Int2 buflen, Uint1 labeltype, CharPtr typelabel)
1033 {
1034     GeneRefPtr grp=NULL;
1035     OrgRefPtr orp=NULL;
1036     ProtRefPtr prp=NULL;
1037     SeqFeatXrefPtr sfxrp;
1038     SeqIdPtr sip;
1039     BioseqPtr bsp;
1040     BioseqContextPtr bcp;
1041     SeqFeatPtr sfp2;
1042     RsiteRefPtr rrp;
1043     UserObjectPtr uop;
1044     BioSourcePtr bsrcp;
1045     CharPtr label = NULL;
1046     RnaRefPtr trrp;
1047     tRNAPtr trp;
1048     RNAGenPtr rgp;
1049     Char tbuf[40], snpbuf [64];
1050     Int2 len = buflen, diff;
1051     GBQualPtr gbp;
1052     CharPtr prefix=NULL, suffix=NULL, ptr;
1053     PubdescPtr pdp;
1054     ValNodePtr vnp;
1055     ImpFeatPtr ifp;
1056     Boolean first;
1057     ValNode vn;
1058     static CharPtr slash = " /";
1059     SeqMapTablePtr smtp;
1060     SeqCodeTablePtr sctp;
1061     Uint1 aacode;
1062     DbtagPtr dbt;
1063     ObjectIdPtr oip;
1064 
1065     if (sfp == NULL) return 0;
1066 
1067     switch (sfp->data.choice)
1068     {
1069         case SEQFEAT_GENE:
1070             grp = (GeneRefPtr)(sfp->data.value.ptrvalue);
1071 generef:    if (grp->locus != NULL)
1072                 label = (grp->locus);
1073             else if (grp->desc != NULL)
1074                 label = (grp->desc);
1075             else if (grp->locus_tag != NULL)
1076                 label = (grp->locus_tag);
1077             else if (grp->syn != NULL)
1078                 label = (CharPtr)(grp->syn->data.ptrvalue);
1079             else if (grp->db != NULL)
1080                 return DbtagLabel((DbtagPtr)(grp->db->data.ptrvalue), buf, buflen);
1081             else if (grp->maploc != NULL)
1082                 label = (grp->maploc);
1083             break;
1084         case SEQFEAT_ORG:
1085             orp = (OrgRefPtr)(sfp->data.value.ptrvalue);
1086 orgref:        if (orp->taxname != NULL)
1087                 label = (orp->taxname);
1088             else if (orp->common != NULL)
1089                 label = (orp->common);
1090             else if (orp->db != NULL)
1091                 return DbtagLabel((DbtagPtr)(orp->db->data.ptrvalue), buf, buflen);
1092             break;
1093         case SEQFEAT_CDREGION:
1094             for (sfxrp = sfp->xref; sfxrp != NULL; sfxrp = sfxrp->next)
1095             {
1096                 switch (sfxrp->data.choice)
1097                 {
1098                     case SEQFEAT_PROT:
1099                         prp = (ProtRefPtr)(sfxrp->data.value.ptrvalue);
1100                         break;
1101                     case SEQFEAT_GENE:
1102                         grp = (GeneRefPtr)(sfxrp->data.value.ptrvalue);
1103                         break;
1104                 }
1105             }
1106             if (prp != NULL) goto protref;
1107             if (sfp->product != NULL)
1108             {
1109                 sip = SeqLocId(sfp->product);
1110                 bsp = BioseqFind(sip);
1111                 if (bsp != NULL)
1112                 {
1113                     /* first see if preindexed in object manager */
1114                     sfp2 = SeqMgrGetBestProteinFeature (bsp, NULL);
1115                     if (sfp2 != NULL) {
1116                         prp = (ProtRefPtr)(sfp2->data.value.ptrvalue);
1117                         if (prp != NULL) {
1118                             goto protref;
1119                         }
1120                     }
1121                     /* if not preindexed, find with bioseq context */
1122                     bcp = BioseqContextNew(bsp);
1123                     sfp2 = BioseqContextGetSeqFeat(bcp, SEQFEAT_PROT, NULL, NULL, 0);
1124                     BioseqContextFree(bcp);
1125                     if (sfp2 != NULL)
1126                     {
1127                         prp = (ProtRefPtr)(sfp2->data.value.ptrvalue);
1128                         goto protref;
1129                     }
1130                 }
1131             }
1132             if (grp != NULL &&
1133                 ((grp->locus != NULL && grp->locus [0] != '\0') ||
1134                     grp->allele != NULL || grp->desc != NULL ||
1135                     grp->maploc != NULL || grp->locus_tag != NULL || grp->pseudo ||
1136                     grp->db != NULL || grp->syn != NULL)) goto generef;
1137             break;
1138         case SEQFEAT_PROT:
1139             prp = (ProtRefPtr)(sfp->data.value.ptrvalue);
1140 protref:    if (prp->name != NULL)
1141                 label = (prp->name->data.ptrvalue);
1142             else if (prp->desc != NULL)
1143                 label = (prp->desc);
1144             else if (prp->db != NULL)
1145                 return DbtagLabel((DbtagPtr)(prp->db->data.ptrvalue), buf, buflen);
1146             break;
1147         case SEQFEAT_RNA:
1148             trrp = (RnaRefPtr)(sfp->data.value.ptrvalue);
1149             if (labeltype == OM_LABEL_CONTENT)
1150             {
1151                 prefix = StringMove(tbuf, typelabel);
1152                 StringMove(prefix, "-");
1153                 prefix = tbuf;
1154             }
1155 
1156             switch (trrp->ext.choice)
1157             {
1158                 case 0:
1159                     label = sfp->comment;
1160                     if (label != NULL) {    /* if RNA already in comment, skip it */
1161                       if (StringStr(label, typelabel) != NULL)
1162                           prefix = NULL;
1163                     }
1164                     else
1165                     {
1166                         prefix = NULL;
1167                         label = typelabel;
1168                     }
1169                     break;
1170                 case 1:
1171                     label = (CharPtr)(trrp->ext.value.ptrvalue);
1172                     if (StringCmp (label, "ncRNA") == 0 ||
1173                         StringCmp (label, "tmRNA") == 0 ||
1174                         StringCmp (label, "misc_RNA") == 0) {
1175                       for (gbp = sfp->qual; gbp != NULL; gbp = gbp->next) {
1176                         if (StringICmp ("product", gbp->qual) == 0) {
1177                                         label = gbp->val;
1178                           break;
1179                         }
1180                       }
1181                     }
1182                     if (label != NULL) {
1183                       if (StringStr(label, typelabel) != NULL)
1184                           prefix = NULL;
1185                     }
1186                     else
1187                     {
1188                         prefix = NULL;
1189                         label = typelabel;
1190                     }
1191                     break;
1192                 case 2:
1193                     trp = (tRNAPtr)(trrp->ext.value.ptrvalue);
1194                     switch (trp->aatype)
1195                     {
1196                         case 1:
1197                             aacode = Seq_code_iupacaa;
1198                             break;
1199                         case 2:
1200                             aacode = Seq_code_ncbieaa;
1201                             break;
1202                         case 3:
1203                             aacode = Seq_code_ncbi8aa;
1204                             break;
1205                         case 4:
1206                             aacode = Seq_code_ncbistdaa;
1207                             break;
1208                         default:
1209                             aacode = 0;
1210                             break;
1211                     }
1212                     if (! aacode)
1213                         break;
1214                     sctp = SeqCodeTableFind(Seq_code_iupacaa3);
1215                     if (sctp == NULL)
1216                     {
1217                         label = prefix;
1218                         prefix = NULL;
1219                         break;
1220                     }
1221                     if (aacode != Seq_code_ncbistdaa)
1222                     {
1223                         smtp = SeqMapTableFind(Seq_code_ncbistdaa, aacode);
1224                         if (smtp == NULL)
1225                         {
1226                             label = prefix;
1227                             prefix = NULL;
1228                             break;
1229                         }
1230                         aacode = SeqMapTableConvert(smtp, trp->aa);
1231                     } else {
1232                         aacode = trp->aa;
1233                     }
1234                     if (aacode == 255) {
1235                         if (trp->aatype == Seq_code_iupacaa || trp->aatype == Seq_code_ncbieaa) {
1236                             if (trp->aa == 74) {
1237                                 aacode = 27; /* Xle */
1238                             } else if (trp->aa == 79) {
1239                                 aacode = 26; /* Pyl */
1240                             }
1241                         }
1242                     }
1243                     if (aacode == 255) {
1244                         label = prefix;
1245                         prefix = NULL;
1246                         break;
1247                     }
1248                     label = sctp->symbols[aacode - sctp->start_at];
1249                     break;
1250                 case 3:
1251                     rgp = (RNAGenPtr) trrp->ext.value.ptrvalue;
1252                     if (rgp != NULL) {
1253                         if (StringDoesHaveText (rgp->product)) {
1254                           label = rgp->product;
1255                         } else if (StringDoesHaveText (rgp->_class)) {
1256                           label = rgp->_class;
1257                         }
1258                     }
1259                     break;
1260                 default:
1261                     break;
1262             }
1263             break;    /* just return the type label for now */
1264         case SEQFEAT_PUB:
1265             pdp = (PubdescPtr)(sfp->data.value.ptrvalue);
1266             vn.choice = PUB_Equiv;
1267             vn.data.ptrvalue = pdp->pub;
1268             vn.next = NULL;
1269             return PubLabel(&vn, buf, buflen, OM_LABEL_CONTENT);
1270         case SEQFEAT_SEQ:
1271             break;
1272         case SEQFEAT_IMP:
1273             ifp = (ImpFeatPtr)(sfp->data.value.ptrvalue);
1274             if (! StringICmp("Site-ref", ifp->key))
1275             {
1276                 if (sfp->cit != NULL)
1277                 {
1278                     first = TRUE;
1279                     for (vnp = (ValNodePtr)(sfp->cit->data.ptrvalue);
1280                                   vnp != NULL; vnp = vnp->next)
1281                     {
1282                         if (! first)
1283                         {
1284                             diff = LabelCopy(buf, ",", buflen);
1285                             buflen -= diff; buf += diff;
1286                         }
1287                         else
1288                             first = FALSE;
1289                         diff = PubLabel(vnp, buf, buflen, OM_LABEL_CONTENT);
1290                         buflen -= diff; buf += diff;
1291                         first = FALSE;
1292                     }
1293                     return (len - buflen);
1294                 }
1295             }
1296             else if(! StringICmp("variation", ifp->key))
1297             {
1298                 /* For variation, label should be a
1299                    list of replace quals */
1300                 for (gbp = sfp->qual; gbp != NULL; gbp = gbp->next)
1301                 {
1302                     if (! StringICmp("replace", gbp->qual)) {
1303                         diff = LabelCopy(buf, gbp->val, buflen);
1304                         buflen -= diff; buf += diff;
1305                     }
1306                 }
1307                 return (len - buflen);
1308             }
1309             else if (labeltype == OM_LABEL_CONTENT) /* show key */
1310             {
1311                 if (! StringICmp("CDS", ifp->key))
1312                     label = "[CDS]";
1313                 else if ((! StringICmp("repeat_unit", ifp->key))    ||
1314                         (! StringICmp("repeat_region", ifp->key)))
1315                 {
1316                     for (gbp = sfp->qual; ((label == NULL) && (gbp != NULL)); gbp = gbp->next)
1317                     {
1318                         if (! StringICmp("rpt_family", gbp->qual))
1319                             label = gbp->val;
1320                     }
1321                     if (label == NULL)
1322                         label = typelabel;
1323                 }
1324                 else if (! StringICmp("STS", ifp->key))
1325                 {
1326                     for (gbp = sfp->qual; ((label == NULL) && (gbp != NULL)); gbp = gbp->next)
1327                     {
1328                         if (! StringICmp("standard_name", gbp->qual))
1329                             label = gbp->val;
1330                     }
1331                     if (label == NULL && (! StringHasNoText (sfp->comment))) {
1332                         StringNCpy_0 (snpbuf, sfp->comment, sizeof (snpbuf));
1333                         ptr = StringChr (snpbuf, ';');
1334                         if (ptr != NULL) {
1335                             *ptr = '\0';
1336                         }
1337                         label = snpbuf;
1338                     }
1339                     if (label == NULL)
1340                         label = typelabel;
1341                 }
1342                 else if (StringICmp("misc_feature", ifp->key)) {
1343                     for (gbp = sfp->qual; label == NULL && gbp != NULL; gbp = gbp->next) {
1344                         if (StringICmp ("standard_name", gbp->qual) == 0) {
1345                             label = gbp->val;
1346                         }
1347                     }
1348                     for (gbp = sfp->qual; label == NULL && gbp != NULL; gbp = gbp->next) {
1349                         if (StringICmp ("function", gbp->qual) == 0) {
1350                             label = gbp->val;
1351                         }
1352                     }
1353                     for (gbp = sfp->qual; label == NULL && gbp != NULL; gbp = gbp->next) {
1354                         if (StringICmp ("number", gbp->qual) == 0) {
1355                             label = gbp->val;
1356                         }
1357                     }
1358                     for (gbp = sfp->qual; label == NULL && gbp != NULL; gbp = gbp->next) {
1359                         label = gbp->val;
1360                     }
1361                     if (label == NULL)
1362                         label = typelabel;
1363                 }
1364             }
1365             break;
1366         case SEQFEAT_REGION:
1367             label = (sfp->data.value.ptrvalue);
1368             if (StringICmp (label, "Domain") == 0 && sfp->comment != NULL) {
1369               label = sfp->comment;
1370             } else if (StringICmp (label, "Variant") == 0 && sfp->comment != NULL) {
1371               label = sfp->comment;
1372             }
1373             break;
1374         case SEQFEAT_COMMENT:
1375             label = sfp->comment;
1376             break;
1377         case SEQFEAT_BOND:
1378             label =  AsnEnumStr("SeqFeatData.bond",
1379                 (Int2)(sfp->data.value.intvalue));
1380             break;
1381         case SEQFEAT_SITE:
1382             label =  AsnEnumStr("SeqFeatData.site",
1383                 (Int2)(sfp->data.value.intvalue));
1384             break;
1385         case SEQFEAT_RSITE:
1386             rrp = (RsiteRefPtr)(sfp->data.value.ptrvalue);
1387             if (rrp->choice == 1)
1388                 label = (rrp->data.ptrvalue);
1389             else if (rrp->choice == 2) {
1390                 /* return DbtagLabel((DbtagPtr)(rrp->data.ptrvalue), buf, buflen); */
1391                 label = "?";
1392                 dbt = (DbtagPtr) rrp->data.ptrvalue;
1393                 if (dbt != NULL) {
1394                     oip = dbt->tag;
1395                     if (oip != NULL) {
1396                         label = oip->str;
1397                     }
1398                 }
1399             }
1400             break;
1401         case SEQFEAT_USER:
1402             uop = (UserObjectPtr)(sfp->data.value.ptrvalue);
1403             label = (uop->_class);
1404             if (label == NULL) {
1405                 oip = uop->type;
1406                 if (oip != NULL) {
1407                     label = oip->str;
1408                 }
1409             }
1410             break;
1411         case SEQFEAT_TXINIT:
1412             break;
1413         case SEQFEAT_NUM:
1414             break;
1415         case SEQFEAT_PSEC_STR:
1416             label =  AsnEnumStr("SeqFeatData.psec-str",
1417                 (Int2)(sfp->data.value.intvalue));
1418             break;
1419         case SEQFEAT_NON_STD_RESIDUE:
1420             label = (sfp->data.value.ptrvalue);
1421             break;
1422         case SEQFEAT_HET:
1423             label = (sfp->data.value.ptrvalue);
1424             break;
1425         case SEQFEAT_BIOSRC:
1426             bsrcp = (BioSourcePtr)(sfp->data.value.ptrvalue);
1427             orp = bsrcp->org;
1428             goto orgref;
1429         case SEQFEAT_CLONEREF:
1430             break;
1431         case SEQFEAT_VARIATIONREF:
1432             break;
1433         default:
1434             break;
1435     }
1436 
1437     if (label != NULL)
1438         return LabelCopyExtra (buf, label, buflen, prefix, suffix);
1439 
1440     first = TRUE;
1441     diff = 1;     /* just to make the first pass through loop work */
1442     for (gbp=sfp->qual; ((gbp != NULL) && (diff)); gbp = gbp->next)
1443     {
1444         if (first)
1445             prefix = (slash + 1);
1446         else
1447             prefix = slash;
1448         first = FALSE;
1449         diff = LabelCopyExtra (buf, gbp->qual, buflen, prefix, NULL);
1450         buflen -= diff;
1451         buf += diff;
1452         if (gbp->val != NULL)
1453         {
1454             prefix = "=";
1455             diff = LabelCopyExtra(buf, gbp->val, buflen, prefix, NULL);
1456             buflen -= diff;
1457             buf += diff;
1458         }
1459     }
1460 
1461     if (sfp->comment != NULL)
1462     {
1463         if (! first)
1464             prefix = "; ";
1465         else
1466             prefix = NULL;
1467         diff = LabelCopyExtra(buf, sfp->comment, buflen, prefix, NULL);
1468         buflen -= diff;
1469     }
1470 
1471     return (len - buflen);
1472 }
1473 
1474 /*****************************************************************************
1475 *
1476 *   FeatDefLabel(sfp, buf, buflen, type)
1477 *       fills in buf with a content based label
1478 *       if longer than buflen, makes the last visible char >
1479 *       guarantees a '\0' at the end of the string
1480 *
1481 *   NOTE: buf MUST be (buflen+1) long
1482 *
1483 *       This function makes nicer labels since it can combine elements
1484 *       returns length of string or 0 on failure
1485 *
1486 *       type is OM_LABEL_TYPE_ defined in objmgr.h
1487 *
1488 *****************************************************************************/
FeatDefLabel(SeqFeatPtr sfp,CharPtr buf,Int2 buflen,Uint1 labeltype)1489 NLM_EXTERN Int2 LIBCALL FeatDefLabel (SeqFeatPtr sfp, CharPtr buf, Int2 buflen, Uint1 labeltype)
1490 {
1491     Int2 len, i, diff;
1492     CharPtr curr, typelabel, tmp;
1493     Char tbuf[40];
1494     ImpFeatPtr ifp;
1495     FeatDefPtr fdp;
1496     CharPtr suffix = NULL;
1497 
1498     if ((sfp == NULL) || (buf == NULL) || (! buflen))
1499         return 0;
1500 
1501     buf[0] = '\0';
1502     curr = buf;
1503     len = buflen;
1504 
1505     if (FeatDefSetLoad() == NULL) return 0;
1506 
1507     i = (Int2) FindFeatDefType(sfp);
1508     if (i != FEATDEF_BAD)
1509     {
1510         fdp = featdeflookup[i];
1511         if (fdp == NULL) return 0;
1512         typelabel = fdp->typelabel;
1513         if ((sfp->data.choice == SEQFEAT_IMP) &&
1514             (! StringCmp("CDS", typelabel)))
1515         {
1516             tmp = StringMove(tbuf, "[");
1517             tmp = StringMove(tmp, typelabel);
1518             tmp = StringMove(tmp, "]");
1519             typelabel = tbuf;
1520         } else if (sfp->data.choice == SEQFEAT_REGION &&
1521                    StringICmp ((CharPtr) sfp->data.value.ptrvalue, "Domain") == 0 &&
1522                    sfp->comment != NULL) {
1523             StringCpy (tbuf, "Domain");
1524             typelabel = tbuf;
1525         } else if (sfp->data.choice == SEQFEAT_REGION &&
1526                    StringICmp ((CharPtr) sfp->data.value.ptrvalue, "Variant") == 0 &&
1527                    sfp->comment != NULL) {
1528             StringCpy (tbuf, "Variant");
1529             typelabel = tbuf;
1530         }
1531     }
1532     else
1533     {
1534         typelabel = tbuf;
1535         switch (sfp->data.choice)
1536         {
1537             case SEQFEAT_IMP:
1538                 ifp = (ImpFeatPtr)(sfp->data.value.ptrvalue);
1539                 tmp = StringMove(tbuf, "[");
1540                 tmp = StringMove(tmp, ifp->key);
1541                 tmp = StringMove(tmp, "]");
1542                 break;
1543             default:
1544                 sprintf(tbuf, "[Unknown=%d]", (int)(sfp->data.choice));
1545                 break;
1546         }
1547     }
1548 
1549     if ((labeltype == OM_LABEL_TYPE) || (labeltype == OM_LABEL_BOTH))
1550     {
1551         if (labeltype == OM_LABEL_BOTH)
1552             suffix = ": ";
1553         else
1554             suffix = NULL;
1555 
1556         diff = LabelCopyExtra(curr, typelabel, buflen, NULL, suffix);
1557         curr += diff;
1558         buflen -= diff;
1559     }
1560 
1561     if ((labeltype == OM_LABEL_TYPE) || (! buflen))
1562         return (len - buflen);
1563 
1564     diff = FeatDefLabelContent (sfp, curr, buflen, labeltype, typelabel);
1565     buflen -= diff;
1566 
1567     if ((! diff) && (labeltype == OM_LABEL_CONTENT))
1568     {
1569         buflen -= LabelCopy(curr, typelabel, buflen);
1570     }
1571 
1572     return (len - buflen);
1573 }
1574 
1575 /*****************************************************************************
1576 *
1577 *   DispGroupNum()
1578 *       returns number of display groups
1579 *       returns 0 on failure
1580 *       loads featdef.val if not already loaded
1581 *
1582 *****************************************************************************/
DispGroupNum(void)1583 NLM_EXTERN Int2 LIBCALL DispGroupNum(void)
1584 {
1585     FeatDefSetLoad();
1586     return numfdispg;
1587 }
1588 
1589 /*****************************************************************************
1590 *
1591 *   DispGroupFindNext(curr, groupptr, groupname)
1592 *     returns display groups in order
1593 *     start with curr=NULL, then return current in curr until function
1594 *       returns NULL
1595 *     loads featdef.val if necessary
1596 *     groupptr is filled in with the key for the group, used
1597 *       in FeatDefFindNext() below.
1598 *     groupname points to the string naming the group
1599 *
1600 *****************************************************************************/
DispGroupFindNext(FeatDispGroupPtr curr,Uint1Ptr groupptr,CharPtr PNTR groupname)1601 NLM_EXTERN FeatDispGroupPtr LIBCALL DispGroupFindNext(FeatDispGroupPtr curr, Uint1Ptr groupptr, CharPtr PNTR groupname)
1602 {
1603     FeatDefSetLoad();
1604     if (curr == NULL)
1605         curr = featdgp;
1606     else
1607         curr = curr->next;
1608 
1609     if (curr != NULL)
1610     {
1611         *groupptr = curr->groupkey;
1612         *groupname = curr->groupname;
1613     }
1614     return curr;
1615 }
1616 
1617 /*****************************************************************************
1618 *
1619 *   FeatDefNum()
1620 *       returns total number of FeatDef
1621 *       loads featdef.val if necessary
1622 *
1623 *****************************************************************************/
FeatDefNum(void)1624 NLM_EXTERN Int2 LIBCALL FeatDefNum(void)
1625 {
1626     FeatDefSetLoad();
1627     return numfdef;
1628 }
1629 
1630 /*****************************************************************************
1631 *
1632 *   FeatDefFindNext(curr, keyptr, menulabel, group, for_display)
1633 *       returns next FeatDef within display group
1634 *       if group == FEATDEF_ANY returns all
1635 *       start with curr = NULL and return current in curr until function
1636 *         returns NULL
1637 *       keyptr is filled in with featdef-key
1638 *       menulabel is filled in with menulabel
1639 *       if for_display == TRUE then group must match display group
1640 *         else group must match entrygroup
1641 *       loads featdef.val if necessary
1642 *
1643 *****************************************************************************/
FeatDefFindNext(FeatDefPtr curr,Uint1Ptr keyptr,CharPtr PNTR menulabel,Uint1 group,Boolean for_display)1644 NLM_EXTERN FeatDefPtr LIBCALL FeatDefFindNext (FeatDefPtr curr, Uint1Ptr keyptr,
1645                            CharPtr PNTR menulabel, Uint1 group, Boolean for_display)
1646 {
1647     FeatDefSetLoad();
1648     if (curr == NULL)
1649         curr = featdefp;
1650     else
1651         curr = curr->next;
1652 
1653     if ((group == FEATDEF_ANY) && (curr != NULL))
1654     {
1655         *keyptr = curr->featdef_key;
1656         *menulabel = curr->menulabel;
1657         return curr;
1658     }
1659 
1660     while (curr != NULL)
1661     {
1662         if (for_display)
1663         {
1664             if (group == curr->displaygroup)
1665             {
1666                 *keyptr = curr->featdef_key;
1667                 *menulabel = curr->menulabel;
1668                 return curr;
1669             }
1670         }
1671         else
1672         {
1673             if (group == curr->entrygroup)
1674             {
1675                 *keyptr = curr->featdef_key;
1676                 *menulabel = curr->menulabel;
1677                 return curr;
1678             }
1679         }
1680         curr = curr->next;
1681     }
1682     return curr;
1683 }
1684 
1685