NCBI C Toolkit Cross Reference

C/object/objpub.c


  1 /*  objpub.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:  objpub.c
 27 *
 28 * Author:  James Ostell
 29 *   
 30 * Version Creation Date: 4/1/91
 31 *
 32 * $Revision: 6.8 $
 33 *
 34 * File Description:  Object manager for module NCBI-Pub
 35 *
 36 * Modifications:  
 37 * --------------------------------------------------------------------------
 38 * Date     Name        Description of modification
 39 * -------  ----------  -----------------------------------------------------
 40 * 05-13-93 Schuler     All public functions are now declared LIBCALL.
 41 *
 42 *
 43 * $Log: objpub.c,v $
 44 * Revision 6.8  2009/10/02 19:44:49  kans
 45 * address clang static analyzer warnings
 46 *
 47 * Revision 6.7  2005/12/29 13:46:18  bollin
 48 * added PubdescContentMatch function
 49 *
 50 * Revision 6.6  2004/04/01 13:43:08  lavr
 51 * Spell "occurred", "occurrence", and "occurring"
 52 *
 53 * Revision 6.5  2002/01/08 20:48:22  kans
 54 * PubLabelUnique internal call to PubLabelUnique (..., unique), not PubLabel
 55 *
 56 * Revision 6.4  2001/11/20 14:50:54  kans
 57 * PubLabelUnique return immediately if PMID or MUID, already unique
 58 *
 59 * Revision 6.3  2000/06/15 19:13:28  yaschenk
 60 * PubAsnWrite should not fail when pmid is stripped
 61 *
 62 * Revision 6.2  1998/12/30 20:28:34  ostell
 63 * fixed bug in PubLabelUnique() for author list. If alp->names is NULL,
 64 * diff was not initialized. So operations using diff moved inside
 65 * if (vnp2 != NULL)
 66 *
 67 * Revision 6.1  1998/08/24 18:28:08  kans
 68 * removed solaris -v -fd warnings
 69 *
 70 * Revision 6.0  1997/08/25 18:50:27  madden
 71 * Revision changed to 6.0
 72 *
 73 * Revision 4.12  1997/06/19 18:41:46  vakatov
 74 * [WIN32,MSVC++]  Adopted for the "NCBIOBJ.LIB" DLL'ization
 75 *
 76 * Revision 4.11  1996/09/12 18:42:53  epstein
 77 * spec_version fixes as suggested by J. Kans
 78 *
 79  * Revision 4.10  1996/07/30  15:22:20  epstein
 80  * correct logic errors for different spec_versions
 81  *
 82  * Revision 4.9  1996/07/01  17:46:53  tatiana
 83  * month and day added to PubLabelUnique() in submission label
 84  *
 85  * Revision 4.8  1996/05/30  21:11:24  tatiana
 86  * fill in the result buffer if cgp->cit is the only field set (in PubLabelUnique).
 87  *
 88  * Revision 4.7  1996/03/29  21:09:59  ostell
 89  * added support for PubMedId
 90  *
 91  * Revision 4.6  1996/03/01  18:08:53  tatiana
 92  * fix in PubLabelUnique
 93  *
 94  * Revision 4.5  1995/10/17  18:10:28  tatiana
 95  * fix in PubLabelUnique
 96  *
 97  * Revision 4.4  1995/10/13  14:04:26  tatiana
 98  * a bug fixed in PubLabelUnique
 99  *
100  * Revision 4.3  1995/09/07  14:16:55  tatiana
101  * fix in PubLabelUnique function
102  *
103  * Revision 4.2  1995/08/30  22:25:21  kans
104  * cap->title uses ->data.ptrvalue
105  *
106  * Revision 4.1  1995/08/30  18:33:53  ostell
107  * added PubLabelUnique function
108  *
109  * Revision 4.0  1995/07/26  13:48:06  ostell
110  * force revision to 4.0
111  *
112  * Revision 3.7  1995/05/15  21:22:00  ostell
113  * added Log line
114  *
115 *
116 *
117 * ==========================================================================
118 */
119 #include <objpub.h>                /* the pub interface */
120 #include <asnpub.h>        /* the AsnTool header */
121 #include <objmgr.h>
122 
123 static Boolean loaded = FALSE;
124 
125 /*****************************************************************************
126 *
127 *   Pub ObjMgr Routines
128 *
129 *****************************************************************************/
130 static CharPtr pubtypename = "Pub";
131 
132 static Pointer LIBCALLBACK PubNewFunc (void)
133 {
134         return (Pointer) ValNodeNew(NULL);
135 }
136 
137 static Pointer LIBCALLBACK PubFreeFunc (Pointer data)
138 {
139         return (Pointer) PubFree ((ValNodePtr) data);
140 }
141 
142 static Boolean LIBCALLBACK PubAsnWriteFunc (Pointer data, AsnIoPtr aip, AsnTypePtr atp)
143 {
144         return PubAsnWrite((ValNodePtr)data, aip, atp);
145 }
146 
147 static Pointer LIBCALLBACK PubAsnReadFunc (AsnIoPtr aip, AsnTypePtr atp)
148 {
149         return (Pointer) PubAsnRead (aip, atp);
150 }
151 
152 static Int2 LIBCALLBACK PubLabelFunc ( Pointer data, CharPtr buffer, Int2 buflen, Uint1 content)
153 {
154         return PubLabel((ValNodePtr)data, buffer, buflen, content);
155 }
156 
157 static Uint2 LIBCALLBACK PubSubTypeFunc (Pointer ptr)
158 {
159         if (ptr == NULL)
160                 return 0;
161         return (Uint2)((ValNodePtr)ptr)->choice;
162 }
163 
164 /*****************************************************************************
165 *
166 *   CitSub ObjMgr Routines
167 *
168 *****************************************************************************/
169 static CharPtr seqsubcittypename = "Cit";
170 
171 static Pointer LIBCALLBACK CitSubNewFunc (void)
172 {
173         return (Pointer) CitSubNew();
174 }
175 
176 static Pointer LIBCALLBACK CitSubFreeFunc (Pointer data)
177 {
178         return (Pointer) CitSubFree ((CitSubPtr) data);
179 }
180 
181 static Boolean LIBCALLBACK CitSubAsnWriteFunc (Pointer data, AsnIoPtr aip, AsnTypePtr atp)
182 {
183         return CitSubAsnWrite((CitSubPtr)data, aip, atp);
184 }
185 
186 static Pointer LIBCALLBACK CitSubAsnReadFunc (AsnIoPtr aip, AsnTypePtr atp)
187 {
188         return (Pointer) CitSubAsnRead (aip, atp);
189 }
190 
191 static Int2 LIBCALLBACK CitSubLabelFunc ( Pointer data, CharPtr buffer, Int2 buflen, Uint1 content)
192 {
193         ValNode vn;
194 
195         vn.choice = PUB_Sub;
196         vn.data.ptrvalue = data;
197         vn.next = NULL;
198 
199         return PubLabel(&vn, buffer, buflen, content);
200 }
201 
202 
203 /*****************************************************************************
204 *
205 *   PubSet ObjMgr Routines
206 *
207 *****************************************************************************/
208 static CharPtr pubsettypename = "PubSet";
209 
210 static Pointer LIBCALLBACK PubSetNewFunc (void)
211 {
212         return (Pointer) ValNodeNew(NULL);
213 }
214 
215 static Pointer LIBCALLBACK PubSetFreeFunc (Pointer data)
216 {
217         return (Pointer) PubSetFree ((ValNodePtr) data);
218 }
219 
220 static Boolean LIBCALLBACK PubSetAsnWriteFunc (Pointer data, AsnIoPtr aip, AsnTypePtr atp)
221 {
222         return PubSetAsnWrite((ValNodePtr)data, aip, atp);
223 }
224 
225 static Pointer LIBCALLBACK PubSetAsnReadFunc (AsnIoPtr aip, AsnTypePtr atp)
226 {
227         return (Pointer) PubSetAsnRead (aip, atp);
228 }
229 
230 static Int2 LIBCALLBACK PubSetLabelFunc ( Pointer data, CharPtr buffer, Int2 buflen, Uint1 content)
231 {
232         return PubSetLabel ((ValNodePtr)data, buffer, buflen, content);
233 }
234 
235 NLM_EXTERN Int2 LIBCALL PubSetLabel (ValNodePtr pubset, CharPtr buffer, Int2 buflen, Uint1 content)
236 {
237         static CharPtr set_names[8] = {
238                 "NotSet",
239                 "Pub",
240                 "Medline",
241                 "Articles",
242                 "Journals",
243                 "Books",
244                 "Procs",
245                 "Patents" };
246         Int2 diff, len, i = 0;
247         Char tbuf[40];
248         ValNodePtr vnp;
249 
250         if ((pubset == NULL) || (buflen < 1))
251                 return 0;
252 
253         if ((pubset->choice >=1) && (pubset->choice <= 7))
254                 i= (Int2)(pubset->choice);
255 
256         len = buflen;
257 
258         if (content == OM_LABEL_TYPE)
259                 return LabelCopy(buffer, set_names[i], buflen);
260 
261         if (content != OM_LABEL_CONTENT)
262         {
263                 diff = LabelCopyExtra(buffer, set_names[i], buflen, NULL, ": ");
264                 buflen -= diff;
265                 buffer += diff;
266         }
267 
268         i=0;
269         for (vnp = (ValNodePtr)(pubset->data.ptrvalue); vnp != NULL; vnp = vnp->next)
270                 i++;
271 
272         if (i == 1)
273                 sprintf(tbuf, "1 pub");
274         else
275                 sprintf(tbuf, "%d pubs", (int)i);
276 
277         diff = LabelCopy(buffer, tbuf, buflen);
278         buflen -= diff;
279         buffer += diff;
280 
281         return (len - buflen);   /* no special SUMMARY yet */
282 }
283 
284 static Uint2 LIBCALLBACK PubSetSubTypeFunc (Pointer ptr)
285 {
286         if (ptr == NULL)
287                 return 0;
288         return (Uint2)((ValNodePtr)ptr)->choice;
289 }
290 
291 /*****************************************************************************
292 *
293 *   PubAsnLoad()
294 *
295 *****************************************************************************/
296 NLM_EXTERN Boolean LIBCALL PubAsnLoad (void)
297 {
298     if (loaded)
299         return TRUE;
300     loaded = TRUE;
301 
302     if (! GeneralAsnLoad())
303     {
304         loaded = FALSE;
305         return FALSE;
306     }
307     if (! BiblioAsnLoad())
308     {
309         loaded = FALSE;
310         return FALSE;
311     }
312     if (! MedlineAsnLoad())
313     {
314         loaded = FALSE;
315         return FALSE;
316     }
317     if (! AsnLoad())
318     {
319         loaded = FALSE;
320         return FALSE;
321     }
322 
323         ObjMgrTypeLoad(OBJ_PUB, "Pub", pubtypename, "Publication",
324                 PUB, PubNewFunc, PubAsnReadFunc, PubAsnWriteFunc,
325                 PubFreeFunc, PubLabelFunc, PubSubTypeFunc);
326 
327         ObjMgrTypeLoad(OBJ_SEQSUB_CIT, "Cit", seqsubcittypename, "Submission Citation",
328                 PUB_sub, CitSubNewFunc, CitSubAsnReadFunc, CitSubAsnWriteFunc,
329                 CitSubFreeFunc, CitSubLabelFunc, NULL);
330 
331         ObjMgrTypeLoad(OBJ_SEQFEAT_CIT, "Seqfeat.cit", "Cit", "Feature Citation",
332                 PUB, PubNewFunc, PubAsnReadFunc, PubAsnWriteFunc,
333                 PubFreeFunc, PubLabelFunc, PubSubTypeFunc);
334 
335         ObjMgrTypeLoad(OBJ_PUB_SET, "Pub-set", pubsettypename, "Set of Publications",
336                 PUB_SET, PubSetNewFunc, PubSetAsnReadFunc, PubSetAsnWriteFunc,
337                 PubSetFreeFunc, PubSetLabelFunc, PubSetSubTypeFunc);
338 
339     return TRUE;
340 }
341 
342 
343 /*****************************************************************************
344 *
345 *   Pub Routines
346 *
347 *****************************************************************************/
348 /*****************************************************************************
349 *
350 *   Pub is a choice using an ValNode
351 *   choice:
352 *   0 = not set
353     1 = gen Cit-gen ,        -- general or generic unparsed
354     2 = sub Cit-sub ,        -- submission
355     3 = medline Medline-entry ,
356     4 = muid INTEGER ,       -- medline uid
357     5 = article Cit-art ,
358     6 = journal Cit-jour ,
359     7 = book Cit-book ,
360     8 = proc Cit-proc ,      -- proceedings of a meeting
361     9 = patent Cit-pat ,
362     10 = pat-id Id-pat ,      -- identify a patent
363     11 = man Cit-let ,        -- manuscript or letter
364     12 = equiv Pub-equiv      -- set of equivalent citation forms for 1 pub
365         13 = pmid INTEGER         -- PubMedId
366 *
367 *****************************************************************************/
368 /*****************************************************************************
369 *
370 *   PubFree(anp)
371 *       Frees one pub and associated data
372 *
373 *****************************************************************************/
374 NLM_EXTERN ValNodePtr LIBCALL PubFree (ValNodePtr anp)
375 {
376     Pointer pnt;
377 
378     if (anp == NULL)
379         return anp;
380     
381     pnt = anp->data.ptrvalue;
382     switch (anp->choice)
383     {
384         case 1:                   /* gen */
385             CitGenFree((CitGenPtr)pnt);
386                         break;
387         case 2:                   /* sub */
388             CitSubFree((CitSubPtr)pnt);
389             break;
390         case 3:                   /* medline */
391             MedlineEntryFree((MedlineEntryPtr)pnt);
392             break;
393         case 4:                   /* uid in intvalue */
394             break;
395         case 5:                   /* article */
396             CitArtFree((CitArtPtr)pnt);
397             break;
398         case 6:                   /* journal */
399             CitJourFree((CitJourPtr)pnt);
400             break;
401         case 7:                   /* book */
402         case 8:                   /* proceedings */
403         case 11:                  /* manuscript */
404             CitBookFree((CitBookPtr)pnt);
405             break;
406         case 9:                   /* patent */
407             CitPatFree((CitPatPtr)pnt);
408             break;
409         case 10:                  /* patent id */
410             IdPatFree((IdPatPtr)pnt);
411             break;
412         case 12:
413             PubEquivFree((ValNodePtr)pnt);
414             break;
415                 case 13:                  /* pubmedid */
416                         break;
417     }
418 
419         ObjMgrDelete(OBJ_PUB, (Pointer)anp);
420 
421         return (ValNodePtr)MemFree(anp);
422 }
423 
424 /*****************************************************************************
425 *
426 *   PubAsnWrite(anp, aip, atp)
427 *       atp is the current type (if identifier of a parent struct)
428 *       if atp == NULL, then assumes it stands alone (Pub ::=)
429 *
430 *****************************************************************************/
431 NLM_EXTERN Boolean LIBCALL PubAsnWrite (ValNodePtr anp, AsnIoPtr aip, AsnTypePtr orig)
432 {
433         DataVal av;
434         AsnTypePtr atp, writetype = NULL;
435     Pointer pnt;
436     AsnWriteFunc func = NULL;
437     Boolean retval = FALSE;
438 
439         if (! loaded)
440         {
441                 if (! PubAsnLoad())
442                         return FALSE;
443         }
444 
445         if (aip == NULL)
446                 return FALSE;
447 
448         atp = AsnLinkType(orig, PUB);   /* link local tree */
449     if (atp == NULL) return FALSE;
450 
451         if (anp == NULL) { AsnNullValueMsg(aip, atp); goto erret; }
452 
453         if ((aip->spec_version > 0 && aip->spec_version < 5) && anp->choice >= 13)  /* ASN4 strip new value */
454         {
455                 ErrPostEx(SEV_ERROR,0,0,"ASN4: PubMedId stripped");
456                 retval=TRUE;
457                 goto erret;
458         }
459 
460         av.ptrvalue = (Pointer)anp;
461         if (! AsnWriteChoice(aip, atp, (Int2)anp->choice, &av)) goto erret;
462 
463     pnt = anp->data.ptrvalue;
464     switch (anp->choice)
465     {
466         case 1:                   /* gen */
467             writetype = PUB_gen;
468             func = (AsnWriteFunc) CitGenAsnWrite;
469             break;
470         case 2:                   /* sub */
471             writetype = PUB_sub;
472             func = (AsnWriteFunc) CitSubAsnWrite;
473             break;
474         case 3:                   /* medline */
475             writetype = PUB_medline;
476             func = (AsnWriteFunc) MedlineEntryAsnWrite;
477             break;
478         case 4:                   /* uid in intvalue */
479             av.intvalue = anp->data.intvalue;
480             if (! AsnWrite(aip, PUB_muid, &av)) goto erret;
481             break;
482         case 5:                   /* article */
483             writetype = PUB_article;
484             func = (AsnWriteFunc) CitArtAsnWrite;
485             break;
486         case 6:                   /* journal */
487             writetype = PUB_journal;
488             func = (AsnWriteFunc) CitJourAsnWrite;
489             break;
490         case 7:                   /* book */
491             writetype = PUB_book;
492             func = (AsnWriteFunc) CitBookAsnWrite;
493             break;
494         case 8:                   /* proceedings */
495             writetype = PUB_proc;
496             func = (AsnWriteFunc) CitProcAsnWrite;
497             break;
498         case 11:                  /* manuscript */
499             writetype = PUB_man;
500             func = (AsnWriteFunc) CitLetAsnWrite;
501             break;
502         case 9:                   /* patent */
503             writetype = PUB_patent;
504             func = (AsnWriteFunc) CitPatAsnWrite;
505             break;
506         case 10:                  /* patent id */
507             writetype = PUB_pat_id;
508             func = (AsnWriteFunc) IdPatAsnWrite;
509             break;
510         case 12:                  /* equiv */
511             writetype = PUB_equiv;
512             func = (AsnWriteFunc) PubEquivAsnWrite;
513             break;
514         case 13:                   /* pmid in intvalue */
515             av.intvalue = anp->data.intvalue;
516             if (! AsnWrite(aip, PUB_pmid, &av)) goto erret;
517             break;
518    }
519     if (writetype != NULL)
520     {
521         if (! (*func)(pnt, aip, writetype)) goto erret;
522     }
523     retval = TRUE;
524 erret:
525         AsnUnlinkType(orig);       /* unlink local tree */
526         return retval;
527 }
528 /*****************************************************************************
529 *
530 *   PubAsnRead(aip, atp)
531 *       atp is the current type (if identifier of a parent struct)
532 *            assumption is readIdent has occurred
533 *       if atp == NULL, then assumes it stands alone and read ident
534 *            has not occurred.
535 *
536 *****************************************************************************/
537 NLM_EXTERN ValNodePtr LIBCALL PubAsnRead (AsnIoPtr aip, AsnTypePtr orig)
538 {
539         DataVal av;
540         AsnTypePtr atp;
541     ValNodePtr anp=NULL;
542     Uint1 choice = 0;
543     AsnReadFunc func = NULL;
544 
545         if (! loaded)
546         {
547                 if (! PubAsnLoad())
548                         return anp;
549         }
550 
551         if (aip == NULL)
552                 return anp;
553 
554         if (orig == NULL)           /* Pub ::= (self contained) */
555                 atp = AsnReadId(aip, amp, PUB);
556         else
557                 atp = AsnLinkType(orig, PUB);    /* link in local tree */
558     if (atp == NULL) return anp;
559 
560         anp = ValNodeNew(NULL);
561     if (anp == NULL) goto erret;
562 
563         if (AsnReadVal(aip, atp, &av) <= 0) goto erret;    /* read the CHOICE value (nothing) */
564         atp = AsnReadId(aip, amp, atp);  /* find the choice */
565     if (atp == NULL) goto erret;
566 
567         if (atp == PUB_gen)
568     {
569         choice = 1;
570         func = (AsnReadFunc) CitGenAsnRead;
571     }
572     else if (atp == PUB_sub)
573     {
574         choice = 2;
575         func = (AsnReadFunc) CitSubAsnRead;
576     }
577     else if (atp == PUB_medline)
578     {
579         choice = 3;
580         func = (AsnReadFunc) MedlineEntryAsnRead;
581     }
582     else if (atp == PUB_muid)
583     {
584         choice = 4;
585         if (AsnReadVal(aip, atp, &anp->data) <= 0) goto erret;
586     }
587     else if (atp == PUB_article)
588     {
589         choice = 5;
590         func = (AsnReadFunc) CitArtAsnRead;
591     }
592     else if (atp == PUB_journal)
593     {
594         choice = 6;
595         func = (AsnReadFunc) CitJourAsnRead;
596     }
597     else if (atp == PUB_book)
598     {
599         choice = 7;
600         func = (AsnReadFunc) CitBookAsnRead;
601     }
602     else if (atp == PUB_proc)
603     {
604         choice = 8;
605         func = (AsnReadFunc) CitProcAsnRead;
606     }
607     else if (atp == PUB_patent)
608     {
609         choice = 9;
610         func = (AsnReadFunc) CitPatAsnRead;
611     }
612     else if (atp == PUB_pat_id)
613     {
614         choice = 10;
615         func = (AsnReadFunc) IdPatAsnRead;
616     }
617     else if (atp == PUB_man)
618     {
619         choice = 11;
620         func = (AsnReadFunc) CitLetAsnRead;
621     }
622     else if (atp == PUB_equiv)
623     {
624         choice = 12;
625         func = (AsnReadFunc) PubEquivAsnRead;
626     }
627     else if (atp == PUB_pmid)
628     {
629         choice = 13;
630         if (AsnReadVal(aip, atp, &anp->data) <= 0) goto erret;
631     }
632 
633     anp->choice = choice;
634     if ((choice != 4) && (choice != 13) && func != NULL)
635     {
636         anp->data.ptrvalue = (* func)(aip, atp);
637         if (anp->data.ptrvalue == NULL) goto erret;
638     }
639 ret:
640         AsnUnlinkType(orig);       /* unlink local tree */
641         return anp;
642 erret:
643     anp = PubFree(anp);
644     goto ret;
645 }
646 
647 /*****************************************************************************
648 *
649 *   PubSet is a choice using an ValNode
650 *   choice:
651 *   0 = not set
652     1 = pub Pub ,        -- mixed pubs
653     3 = medline Medline-entry ,    -- use same mapping as Pub for these
654     5 = article Cit-art ,
655     6 = journal Cit-jour ,
656     7 = book Cit-book ,
657     8 = proc Cit-proc ,      -- proceedings of a meeting
658     9 = patent Cit-pat ,
659 *
660 *   PubSet->data.ptrvalue points to chain of Pub (even if not mixed) so
661 *      each Pub is self identifying anyway and Pub routines can be used
662 *****************************************************************************/
663 /*****************************************************************************
664 *
665 *   PubSetFree(anp)
666 *       Frees one Pub-set and associated data
667 *
668 *****************************************************************************/
669 NLM_EXTERN ValNodePtr LIBCALL PubSetFree (ValNodePtr anp)
670 {
671     if (anp == NULL)
672         return anp;
673 
674     PubEquivFree((ValNodePtr)anp->data.ptrvalue);
675 
676         ObjMgrDelete(OBJ_PUB_SET, (Pointer)anp);
677 
678     return (ValNodePtr)MemFree(anp);
679 }
680 
681 /*****************************************************************************
682 *
683 *   PubSetAsnWrite(anp, aip, atp)
684 *       atp is the current type (if identifier of a parent struct)
685 *       if atp == NULL, then assumes it stands alone (PubSet ::=)
686 *
687 *****************************************************************************/
688 NLM_EXTERN Boolean LIBCALL PubSetAsnWrite (ValNodePtr anp, AsnIoPtr aip, AsnTypePtr orig)
689 {
690         DataVal av;
691         AsnTypePtr atp, settype = NULL, elementtype;
692     Pointer pnt;
693     Uint1 choice;
694     AsnWriteFunc func = NULL;
695         ValNodePtr oldanp;
696     Boolean retval = FALSE;
697 
698         if (! loaded)
699         {
700                 if (! PubAsnLoad())
701                         return FALSE;
702         }
703 
704         if (aip == NULL)
705                 return FALSE;
706 
707         atp = AsnLinkType(orig, PUB_SET);   /* link local tree */
708     if (atp == NULL) return FALSE;
709 
710         if (anp == NULL) { AsnNullValueMsg(aip, atp); goto erret; }
711 
712         av.ptrvalue = (Pointer)anp;
713         if (! AsnWriteChoice(aip, atp, (Int2)anp->choice, &av)) goto erret;
714     choice = anp->choice;              /* type of set */
715     switch (choice)    
716     {
717         case 1:              
718             settype = PUB_SET_pub;
719             elementtype = PUB_SET_pub_E;
720             func = (AsnWriteFunc) PubAsnWrite;
721             break;
722         case 3:              
723             settype = PUB_SET_medline;
724             elementtype = PUB_SET_medline_E;
725             func = (AsnWriteFunc) MedlineEntryAsnWrite;
726             break;
727         case 5:              
728             settype = PUB_SET_article;
729             elementtype = PUB_SET_article_E;
730             func = (AsnWriteFunc) CitArtAsnWrite;
731             break;
732         case 6:              
733             settype = PUB_SET_journal;
734             elementtype = PUB_SET_journal_E;
735             func = (AsnWriteFunc) CitJourAsnWrite;
736             break;
737         case 7:  
738             settype = PUB_SET_book;
739             elementtype = PUB_SET_book_E;
740             func = (AsnWriteFunc) CitBookAsnWrite;
741             break;
742         case 8:
743             settype = PUB_SET_proc;
744             elementtype = PUB_SET_proc_E;
745             func = (AsnWriteFunc) CitBookAsnWrite;
746             break;
747         case 9:
748             settype = PUB_SET_patent;
749             elementtype = PUB_SET_patent_E;
750             func = (AsnWriteFunc) CitPatAsnWrite;
751             break;
752     }
753 
754         oldanp = anp;
755     if (! AsnOpenStruct(aip, settype, oldanp->data.ptrvalue))   /* start SET OF */
756         goto erret;
757 
758     anp = (ValNodePtr)anp->data.ptrvalue;
759 
760     while (anp != NULL)
761     {
762         if (choice == 1)
763             pnt = (Pointer)anp;
764         else
765             pnt = anp->data.ptrvalue;
766         if (func != NULL) {
767           if (! (*func)(pnt, aip, elementtype)) goto erret;
768         }
769         anp = anp->next;
770     }
771     
772     if (! AsnCloseStruct(aip, settype, oldanp->data.ptrvalue))  /* end SET OF */
773         goto erret;
774     retval = TRUE;
775 erret:
776         AsnUnlinkType(orig);       /* unlink local tree */
777         return retval;
778 }
779 
780 /*****************************************************************************
781 *
782 *   PubSetAsnRead(aip, atp)
783 *       atp is the current type (if identifier of a parent struct)
784 *            assumption is readIdent has occurred
785 *       if atp == NULL, then assumes it stands alone and read ident
786 *            has not occurred.
787 *
788 *****************************************************************************/
789 NLM_EXTERN ValNodePtr LIBCALL PubSetAsnRead (AsnIoPtr aip, AsnTypePtr orig)
790 {
791         DataVal av;
792         AsnTypePtr atp, settype;
793     Pointer pnt;
794     ValNodePtr anp=NULL, cit, curr;
795     Uint1 choice;
796     AsnReadFunc func;
797     Boolean first;
798 
799         if (! loaded)
800         {
801                 if (! PubAsnLoad())
802                         return anp;
803         }
804 
805         if (aip == NULL)
806                 return anp;
807 
808         if (orig == NULL)           /* PubSet ::= (self contained) */
809                 atp = AsnReadId(aip, amp, PUB_SET);
810         else
811                 atp = AsnLinkType(orig, PUB_SET);    /* link in local tree */
812     if (atp == NULL) return anp;
813 
814         anp = ValNodeNew(NULL);
815     if (anp == NULL) goto erret;
816 
817         if (AsnReadVal(aip, atp, &av) <= 0)    /* read the CHOICE value (nothing) */
818         goto erret;
819         settype = AsnReadId(aip, amp, atp);  /* find the choice */
820     if (settype == NULL) goto erret;
821     if (AsnReadVal(aip, settype, &av) <= 0)    /* read START_STRUCT */
822         goto erret;
823 
824         if (settype == PUB_SET_pub)
825     {
826         choice = 1;
827         func = (AsnReadFunc) PubAsnRead;
828     }
829     else if (settype == PUB_SET_medline)
830     {
831         choice = 3;
832         func = (AsnReadFunc) MedlineEntryAsnRead;
833     }
834     else if (settype == PUB_SET_article)
835     {
836         choice = 5;
837         func = (AsnReadFunc) CitArtAsnRead;
838     }
839     else if (settype == PUB_SET_journal)
840     {
841         choice = 6;
842         func = (AsnReadFunc) CitJourAsnRead;
843     }
844     else if (settype == PUB_SET_book)
845     {
846         choice = 7;
847         func = (AsnReadFunc) CitBookAsnRead;
848     }
849     else if (settype == PUB_SET_proc)
850     {
851         choice = 8;
852         func = (AsnReadFunc) CitBookAsnRead;
853     }
854     else if (settype == PUB_SET_patent)
855     {
856         choice = 9;
857         func = (AsnReadFunc) CitPatAsnRead;
858     }
859 
860     anp->choice = choice;
861     first = TRUE;
862     curr = NULL;
863     while ((atp = AsnReadId(aip, amp, settype)) != settype)
864     {
865         if (atp == NULL) goto erret;
866         pnt = (* func)(aip, atp);
867         if (pnt == NULL) goto erret;
868         if (settype == PUB_SET_pub)   /* already a Pub */
869         {
870             cit = (ValNodePtr)pnt;
871         }
872         else                          /* make into a Pub */
873         {
874             cit = ValNodeNew(NULL);
875             if (cit == NULL) goto erret;
876             cit->data.ptrvalue = pnt;
877             cit->choice = choice;
878         }
879 
880         if (first)
881         {
882             anp->data.ptrvalue = (Pointer)cit;
883             first = FALSE;
884         }
885         else
886         {
887             curr->next = cit;
888         }
889         curr = cit;
890     }
891     if (AsnReadVal(aip, settype, &av) <= 0)   /* read END_STRUCT for SET OF */
892         goto erret;
893         if (anp == NULL)
894                 ErrPost(CTX_NCBIOBJ, 1, "Empty SET OF Pub.  line %ld", aip->linenumber);
895 ret:
896         AsnUnlinkType(orig);       /* unlink local tree */
897         return anp;
898 erret:
899     anp = PubSetFree(anp);
900     goto ret;
901 }
902 
903 /*****************************************************************************
904 *
905 *   PubEquiv is just a chain of Pubs (ValNodes)
906 *   
907 *****************************************************************************/
908 /*****************************************************************************
909 *
910 *   PubEquivFree(anp)
911 *       Frees a chain of Pubs
912 *
913 *****************************************************************************/
914 NLM_EXTERN ValNodePtr LIBCALL PubEquivFree (ValNodePtr anp)
915 {
916     ValNodePtr next;
917 
918     while (anp != NULL)
919     {
920         next = anp->next;
921         PubFree(anp);  /* each node individually coded as Pub anyway */
922         anp = next;
923     }
924         return anp;
925 }
926 
927 /*****************************************************************************
928 *
929 *   PubEquivAsnWrite(anp, aip, atp)
930 *       atp is the current type (if identifier of a parent struct)
931 *       if atp == NULL, then assumes it stands alone (PubEquiv ::=)
932 *
933 *****************************************************************************/
934 NLM_EXTERN Boolean LIBCALL PubEquivAsnWrite (ValNodePtr anp, AsnIoPtr aip, AsnTypePtr orig)
935 {
936         AsnTypePtr atp;
937         ValNodePtr oldanp;
938     Boolean retval = FALSE;
939 
940         if (! loaded)
941         {
942                 if (! PubAsnLoad())
943                         return FALSE;
944         }
945 
946         if (aip == NULL)
947                 return FALSE;
948 
949         atp = AsnLinkType(orig, PUB_EQUIV);   /* link local tree */
950     if (atp == NULL) return FALSE;
951 
952         if (anp == NULL) { AsnNullValueMsg(aip, atp); goto erret; }
953 
954         oldanp = anp;
955     if (! AsnOpenStruct(aip, atp, (Pointer)oldanp))   /* start SET OF */
956         goto erret;
957 
958     while (anp != NULL)
959     {
960         if (! PubAsnWrite(anp, aip, PUB_EQUIV_E)) goto erret;
961         anp = anp->next;
962     }
963 
964     if (! AsnCloseStruct(aip, atp, (Pointer)oldanp))     /* end SET OF */
965         goto erret;
966     retval = TRUE;
967 erret:
968         AsnUnlinkType(orig);       /* unlink local tree */
969         return retval;
970 }
971 
972 /*****************************************************************************
973 *
974 *   PubEquivAsnRead(aip, atp)
975 *       atp is the current type (if identifier of a parent struct)
976 *            assumption is readIdent has occurred
977 *       if atp == NULL, then assumes it stands alone and read ident
978 *            has not occurred.
979 *
980 *****************************************************************************/
981 NLM_EXTERN ValNodePtr LIBCALL PubEquivAsnRead (AsnIoPtr aip, AsnTypePtr orig)
982 {
983         DataVal av;
984         AsnTypePtr atp, oldtype;
985     ValNodePtr anp=NULL, cit, curr;
986     Boolean first;
987 
988         if (! loaded)
989         {
990                 if (! PubAsnLoad())
991                         return anp;
992         }
993 
994         if (aip == NULL)
995                 return anp;
996 
997         first = TRUE;
998 
999         if (orig == NULL)           /* PubEquiv ::= (self contained) */
1000                 oldtype = AsnReadId(aip, amp, PUB_EQUIV);
1001         else
1002                 oldtype = AsnLinkType(orig, PUB_EQUIV);    /* link in local tree */
1003     if (oldtype == NULL) return anp;
1004 
1005     if (AsnReadVal(aip, oldtype, &av) <= 0)    /* read START_STRUCT */
1006         goto erret;
1007     atp = oldtype;
1008 
1009     curr = NULL;
1010     anp = NULL;
1011     while ((atp = AsnReadId(aip, amp, atp)) != oldtype)
1012     {
1013         if (atp == NULL) goto erret;
1014 
1015         cit = PubAsnRead(aip, atp);
1016         if (cit == NULL) goto erret;
1017 
1018         if (first)
1019         {
1020             anp = cit;
1021             first = FALSE;
1022         }
1023         else
1024         {
1025             curr->next = cit;
1026         }
1027         curr = cit;
1028     }
1029     if (AsnReadVal(aip, oldtype, &av) <= 0)   /* read END_STRUCT for SET OF */
1030         goto erret;
1031 ret:
1032         AsnUnlinkType(orig);       /* unlink local tree */
1033         return anp;
1034 erret:
1035     anp = PubEquivFree(anp);
1036     goto ret;
1037 }
1038 
1039 /*****************************************************************************
1040 *
1041 *   Int2 PubMatch(a, b)
1042 *       returns 0 if can determine pubs POINT TO SAME CITATION (not that
1043 *               they are identical)
1044 *       returns positive or negative number if not the same,
1045 *               for arbitrary ordering
1046 *       -2, +2  = different types
1047 *       -1, +1  = different values, same type
1048 *
1049 *****************************************************************************/
1050 NLM_EXTERN Int2 LIBCALL PubMatch (ValNodePtr a, ValNodePtr b)
1051 {
1052         ValNode vn1;
1053         ValNodePtr ap, bp, tp, vnp[2];
1054         Int2 retval, i;
1055         Int4 muid[2];
1056         Int4 pmid[2];
1057         CitArtPtr cap[2];
1058         CharPtr country[2],   /* for patents */
1059                 number[2],
1060                 app_number[2];
1061 
1062         if (a == NULL) return 2;
1063         if (b == NULL) return -2;
1064 
1065                                 /* default return for different pub types */
1066         if (a->choice > b->choice)
1067                 retval = 2;
1068         else
1069                 retval = -2;
1070 
1071                                                         /* if either is a Pub-equiv, treat as both */
1072         if ((a->choice == PUB_Equiv) || (b->choice == PUB_Equiv))
1073         {
1074                 ap = (ValNodePtr)(a->data.ptrvalue);
1075                 bp = (ValNodePtr)(b->data.ptrvalue);
1076                 tp = NULL;
1077                 if (a->choice != PUB_Equiv)
1078                 {
1079                         tp = a;
1080                         ap = NULL;
1081                 }
1082                 else if (b->choice != PUB_Equiv)
1083                 {
1084                         tp = b;
1085                         bp = NULL;
1086                 }
1087                 if (tp != NULL)   /* convert one */
1088                 {
1089                         MemCopy((Pointer)&vn1, tp, sizeof(ValNode));  /* make a copy of the Pub */
1090                         vn1.next = NULL;                   /* remove from any chain */
1091                         tp = (ValNodePtr)&vn1;
1092                         if (ap == NULL)
1093                                 ap = tp;
1094                         else
1095                                 bp = tp;
1096                 }
1097                 return PubEquivMatch(ap, bp);   /* use the PubEquivMatch() */
1098         }
1099                                    /** here we are just matching two pubs */
1100                                                         /* handle Medline/CitArt combinations */
1101                                 /* handle CitPat, IdPat combinations */
1102         vnp[0] = a;
1103         vnp[1] = b;
1104         for (i = 0; i < 2; i++)
1105         {
1106                 cap[i] = NULL;
1107                 muid[i] = 0;
1108                 pmid[i] = 0;
1109                 country[i] = NULL;
1110                 number[i] = NULL;
1111                 app_number[i] = NULL;
1112 
1113                 switch (vnp[i]->choice)
1114                 {
1115                         case PUB_Medline:
1116                                 muid[i] = ((MedlineEntryPtr)(vnp[i]->data.ptrvalue))->uid;
1117                                 cap[i] = ((MedlineEntryPtr)(vnp[i]->data.ptrvalue))->cit;
1118                                 pmid[i] = ((MedlineEntryPtr)(vnp[i]->data.ptrvalue))->pmid;
1119                                 break;
1120                         case PUB_Muid:
1121                                 muid[i] = vnp[i]->data.intvalue;
1122                                 break;
1123                         case PUB_Article:
1124                                 cap[i] = (CitArtPtr)(vnp[i]->data.ptrvalue);
1125                                 break;
1126                         case PUB_Patent:
1127                                 country[i] = ((CitPatPtr)(vnp[i]->data.ptrvalue))->country;
1128                                 number[i] = ((CitPatPtr)(vnp[i]->data.ptrvalue))->number;
1129                                 app_number[i] = ((CitPatPtr)(vnp[i]->data.ptrvalue))->app_number;
1130                                 break;
1131                         case PUB_Pat_id:
1132                                 country[i] = ((IdPatPtr)(vnp[i]->data.ptrvalue))->country;
1133                                 number[i] = ((IdPatPtr)(vnp[i]->data.ptrvalue))->number;
1134                                 app_number[i] = ((IdPatPtr)(vnp[i]->data.ptrvalue))->app_number;
1135                                 break;
1136                         case PUB_PMid:
1137                                 pmid[i] = vnp[i]->data.intvalue;
1138                                 break;
1139                 }
1140         }
1141 
1142         if ((pmid[0] > 0) && (pmid[1] > 0))   /* got 2 muids */
1143         {
1144                 if (pmid[0] == pmid[1])
1145                         return (Int2)0;
1146                 else if (pmid[0] < pmid[1])
1147                         return (Int2)-1;
1148                 else
1149                         return (Int2) 1;
1150         }
1151 
1152         if ((muid[0] > 0) && (muid[1] > 0))   /* got 2 muids */
1153         {
1154                 if (muid[0] == muid[1])
1155                         return (Int2)0;
1156                 else if (muid[0] < muid[1])
1157                         return (Int2)-1;
1158                 else
1159                         return (Int2) 1;
1160         }
1161 
1162         if ((cap[0] != NULL) && (cap[1] != NULL))  /* 2 articles */
1163         {
1164                 return CitArtMatch(cap[0], cap[1]);
1165         }
1166 
1167         if ((country[0] != NULL) && (country[1] != NULL))  /* 2 patents */
1168         {
1169                 retval = (Int2)StringICmp(country[0], country[1]);
1170                 if (retval < 0)   /* different countries */
1171                         return (Int2) -1;
1172                 else if (retval > 0)
1173                         return (Int2) 1;
1174 
1175                 if ((number[0] != NULL) && (number[1] != NULL))
1176                 {
1177                         retval = (Int2)StringICmp(number[0], number[1]);
1178                         if (retval < 0)   /* different number */
1179                                 return (Int2) -1;
1180                         else if (retval > 0)
1181                                 return (Int2) 1;
1182                         else
1183                                 return retval;
1184                 }
1185                 if ((app_number[0] != NULL) && (app_number[1] != NULL))
1186                 {
1187                         retval = (Int2)StringICmp(app_number[0], app_number[1]);
1188                         if (retval < 0)   /* different appl number */
1189                                 return (Int2) -1;
1190                         else if (retval > 0)
1191                                 return (Int2) 1;
1192                         else
1193                                 return retval;
1194                 }
1195                 if (number[0] != NULL)
1196                         return (Int2) -1;
1197                 return (Int2) 1;
1198         }
1199 
1200         if (a->choice != b->choice)    /* all others must be same type */
1201         {
1202                 return retval;
1203         }
1204                                                         /* compare other types */
1205         switch (a->choice)
1206         {
1207                 case PUB_Gen:        /* generic */
1208                         return CitGenMatch((CitGenPtr)a->data.ptrvalue,
1209                                         (CitGenPtr)b->data.ptrvalue, TRUE);
1210                 case PUB_Sub:        /* Submission */
1211                         return CitSubMatch((CitSubPtr)a->data.ptrvalue,
1212                                         (CitSubPtr)b->data.ptrvalue);
1213                 case PUB_Journal:
1214                         return CitJourMatch((CitJourPtr)a->data.ptrvalue,
1215                                         (CitJourPtr)b->data.ptrvalue);
1216                 case PUB_Book:
1217                 case PUB_Proc:
1218                 case PUB_Man:
1219                         return CitBookMatch((CitBookPtr)a->data.ptrvalue,
1220                                         (CitBookPtr)b->data.ptrvalue);
1221         }
1222 
1223         return retval;
1224 }
1225 
1226 /*****************************************************************************
1227 *
1228 *   Int2 PubEquivMatch(a, b)
1229 *       returns 0 if can determine pubs POINT TO SAME CITATION (not that
1230 *               they are identical)
1231 *       returns +1 or -1 if not the same,
1232 *               for arbitrary ordering
1233 *
1234 *****************************************************************************/
1235 NLM_EXTERN Int2 LIBCALL PubEquivMatch (ValNodePtr a, ValNodePtr b)
1236 {
1237         Int2 retval = 0, tmp;
1238         ValNodePtr vnp;
1239 
1240         while (a != NULL)
1241         {
1242                 vnp = b;
1243                 while (vnp != NULL)
1244                 {
1245                         tmp = PubMatch(a, vnp);
1246                         if (! tmp)         /* a match */
1247                         {
1248                                 return tmp;
1249                         }
1250                         if (! retval)   /* first one */
1251                                 retval = tmp;
1252                         else if ((retval == 2) || (retval == -2))  /* type diffs only */
1253                                 retval = tmp;
1254 
1255                         vnp = vnp->next;
1256                 }
1257                 a = a->next;
1258         }
1259         if (retval < 0)
1260                 retval = -1;
1261         else
1262                 retval = 1;
1263         return retval;
1264 }
1265 
1266 
1267 /*****************************************************************************
1268 *
1269 *   PubdescContentMatch(pub1, pub2)
1270 *
1271 *   returns TRUE if content of pub1 matches content of pub2, FALSE otherwise
1272 *****************************************************************************/
1273 NLM_EXTERN Boolean LIBCALL PubdescContentMatch (PubdescPtr pdp1, PubdescPtr pdp2)
1274 {
1275     if (pdp1 == NULL && pdp2 == NULL)
1276     {
1277         return TRUE;
1278     }
1279     else if (pdp1 == NULL || pdp2 == NULL)
1280     {
1281         return FALSE;
1282     }
1283     else if (pdp1->reftype != pdp2->reftype)
1284     {
1285         return FALSE;
1286     }
1287     else if (StringCmp (pdp1->name, pdp2->name) != 0
1288              || StringCmp (pdp1->fig, pdp2->fig) != 0
1289              || StringCmp (pdp1->maploc, pdp2->maploc) != 0
1290              || StringCmp (pdp1->seq_raw, pdp2->seq_raw) != 0
1291              || StringCmp (pdp1->comment, pdp2->comment) != 0)
1292     {
1293         return FALSE;
1294     }
1295     else if (PubMatch (pdp1->pub, pdp2->pub) != 0)
1296     {
1297         return FALSE;
1298     }
1299     else
1300     {
1301         return TRUE;
1302     }
1303 }
1304 
1305 
1306 /*****************************************************************************
1307 *
1308 *   PubLabel(pubptr, buf, buflen, content)
1309 *       makes a short label for any Pub in buf, up to buflen size
1310 *       content follows objmgr OM_LABEL_
1311 *
1312 *****************************************************************************/
1313 NLM_EXTERN Int2 LIBCALL PubLabel (ValNodePtr pub, CharPtr buf, Int2 buflen, Uint1 content)
1314 {
1315         return PubLabelUnique (pub, buf, buflen, content, FALSE);
1316 }
1317 
1318 /*****************************************************************************
1319 *
1320 *   PubLabelUnique(pubptr, buf, buflen, content, unique)
1321 *       makes a short label for any Pub in buf, up to buflen size
1322 *       content follows objmgr OM_LABEL_
1323 *       if (unique is TRUE, appends a string based on title words to make
1324 *           unique key base on ANSI std Z39.56-1991
1325 *
1326 *****************************************************************************/
1327 NLM_EXTERN Int2 LIBCALL PubLabelUnique (ValNodePtr pub, CharPtr buf, Int2 buflen, Uint1 content, Boolean unique)
1328 {
1329         CharPtr typelabel = NULL;
1330         static CharPtr pubtypes [14] = {
1331                 "Unknown",
1332                 "Generic",
1333                 "Submit",
1334                 "Medline",
1335                 "MUID",
1336                 "Article",
1337                 "Journal",
1338                 "Book",
1339                 "Proceedings",
1340                 "Patent",
1341                 "PatID",
1342                 "Manuscript",
1343                 "Equiv" ,
1344                 "PMID" };
1345         ValNodePtr vnp2=NULL, title=NULL;
1346         Int2 len, diff;
1347         Char tbuf[41];
1348         Boolean first = TRUE;
1349 
1350         Int4 muid = 0, pmid = 0;
1351         AuthListPtr alp=NULL;
1352         AuthorPtr ap;
1353         ImprintPtr imp = NULL;
1354         CharPtr year = NULL,
1355                         volume = NULL,
1356                         issue = NULL,
1357                         pages = NULL,
1358                         title1=NULL,
1359                         title2=NULL,
1360                         titleunique = NULL,
1361                         part_sup = NULL,
1362                         part_supi = NULL;
1363         CitArtPtr cap;
1364         CitJourPtr cjp;
1365         CitBookPtr cbp=NULL;
1366         CitSubPtr csp;
1367         CitPatPtr cpp;
1368         IdPatPtr ipp;
1369         CitGenPtr cgp;
1370         MedlineEntryPtr mep;
1371         DatePtr dp = NULL;
1372         Boolean unpublished = FALSE, done;
1373         ValNodePtr eq[5];
1374         Int2 i;
1375         CharPtr s, cit;
1376 
1377 
1378 
1379         if ((buf == NULL) || (buflen < 1)) return 0;
1380 
1381         buf[0] = '?';
1382         buf[1] = '\0';
1383 
1384         if (pub == NULL) return 0;
1385 
1386         if (pub->choice > 13)
1387                 typelabel = pubtypes[0];
1388         else
1389                 typelabel = pubtypes[pub->choice];
1390 
1391         len = buflen;
1392 
1393         if (content == OM_LABEL_TYPE)
1394                 return LabelCopy(buf, typelabel, buflen);
1395 
1396         if (content == OM_LABEL_BOTH)
1397         {
1398                 diff = LabelCopyExtra(buf, typelabel, buflen, NULL, ": ");
1399                 buflen -= diff; buf += diff;
1400         }
1401 
1402         switch (pub->choice)
1403         {
1404                 case PUB_Muid:
1405                         sprintf(tbuf, "NLM%ld", (long)(pub->data.intvalue));
1406                         diff = LabelCopy(buf, tbuf, buflen);
1407                         buflen -= diff;
1408                         return (len - buflen); /* already unique */
1409                         break;
1410                 case PUB_PMid:
1411                         sprintf(tbuf, "PM%ld", (long)(pub->data.intvalue));
1412                         diff = LabelCopy(buf, tbuf, buflen);
1413                         buflen -= diff;
1414                         return (len - buflen); /* already unique */
1415                         break;
1416                 case PUB_Equiv:
1417                         for (i = 0; i < 5; i++)
1418                                 eq[i] = NULL;
1419                         i = 0;
1420                         for (vnp2 = (ValNodePtr)(pub->data.ptrvalue);
1421                                       ((vnp2 != NULL) && (buflen)); vnp2 = vnp2->next)
1422                         {
1423                                 switch (vnp2->choice)
1424                                 {
1425                                         case PUB_Muid:
1426                                                 eq[3] = vnp2;
1427                                                 break;
1428                                         case PUB_Gen:
1429                                                 cgp = (CitGenPtr)(vnp2->data.ptrvalue);
1430                                                 if (cgp->serial_number > 0)
1431                                                 {
1432                                                         eq[4] = vnp2;
1433                                                         break;
1434                                                 }
1435                                         default:
1436                                                 if (i < 5)
1437                                                         eq[i] = vnp2;
1438                                                 i++;
1439                                                 break;
1440                                 }       
1441                         }
1442                         for (i = 0; i < 5; i++)
1443                         {
1444                                 if (eq[i] != NULL)
1445                                 {
1446                                         if (! first)
1447                                         {
1448                                                 diff = LabelCopy(buf, " ", buflen);
1449                                                 buflen -= diff; buf += diff;
1450                                         }
1451                                         else
1452                                                 first = FALSE;
1453 
1454                                         diff = PubLabelUnique (eq[i], buf, buflen, OM_LABEL_CONTENT, unique);
1455                                         buflen -= diff; buf += diff;
1456                                 }
1457                         }
1458                         break;
1459                 case PUB_Medline:
1460                         mep = (MedlineEntryPtr)(pub->data.ptrvalue);
1461                         if (mep->pmid > 0)
1462                                 sprintf(tbuf, "PM%ld", (long)(mep->pmid));
1463                         else
1464                                 sprintf(tbuf, "NLM%ld", (long)(mep->uid));
1465                         diff = LabelCopyExtra(buf, tbuf, buflen, NULL, " ");
1466                         buflen -= diff;
1467                         cap = mep->cit;
1468                         goto cit_art;
1469                 case PUB_Article:
1470                         cap = (CitArtPtr)(pub->data.ptrvalue);
1471 cit_art:        alp = cap->authors;
1472                         if (cap->title != NULL)
1473                                 titleunique = (CharPtr)(cap->title->data.ptrvalue);
1474                         switch (cap->from)
1475                         {
1476                                 case 1:
1477                                         cjp = (CitJourPtr)(cap->fromptr);
1478                                         goto cit_jour;
1479                                 case 2:
1480                                 case 3:
1481                                         cbp = (CitBookPtr)(cap->fromptr);
1482                                         goto cit_book;
1483                         }
1484                         break;
1485                 case PUB_Journal:
1486                         cjp = (CitJourPtr)(pub->data.ptrvalue);
1487 cit_jour:       imp = cjp->imp;
1488                         title = cjp->title;
1489                         break;
1490                 case PUB_Book:
1491                 case PUB_Proc:
1492                 case PUB_Man:
1493                         cbp = (CitBookPtr)(pub->data.ptrvalue);
1494                         title = cbp->title;
1495 cit_book:   imp = cbp->imp;
1496                         if (alp == NULL)
1497                                 alp = cbp->authors;
1498                         break;
1499                 case PUB_Sub:
1500                         csp = (CitSubPtr)(pub->data.ptrvalue);
1501                         alp = csp->authors;
1502                         imp = csp->imp;
1503                         dp = csp->date;
1504                         break;
1505                 case PUB_Patent:
1506                         cpp = (CitPatPtr)(pub->data.ptrvalue);
1507                         alp = cpp->authors;
1508                         dp = cpp->date_issue;
1509                         if (dp == NULL)
1510                                 dp = cpp->app_date;
1511                         title1 = cpp->country;
1512                         title2 = cpp->number;
1513                         if (title2 == NULL)
1514                                 title2 = cpp->app_number;
1515                         break;
1516                 case PUB_Pat_id:
1517                         ipp = (IdPatPtr)(pub->data.ptrvalue);
1518                         title1 = ipp->country;
1519                         title2 = ipp->number;
1520                         if (title2 == NULL)
1521                                 title2 = ipp->app_number;
1522                         break;
1523                 case PUB_Gen:
1524                         cgp = (CitGenPtr)(pub->data.ptrvalue);
1525                         if (cgp->serial_number > 0)
1526                         {
1527                                 sprintf(tbuf, "[%d]", (int)(cgp->serial_number));
1528                                 diff = LabelCopy(buf, tbuf, buflen);
1529                                 buflen -= diff; buf += diff;
1530                         }
1531                         if (cgp->muid > 0)
1532                         {
1533                                 sprintf(tbuf, "NLM%ld", (long)(cgp->muid));
1534                                 diff = LabelCopy(buf, tbuf, buflen);
1535                                 buflen -= diff; buf += diff;
1536 
1537                         }
1538                         dp = cgp->date;
1539                         title = cgp->journal;
1540                         alp = cgp->authors;
1541                         if (cgp->cit != NULL)
1542                         {
1543                                 if (! StringICmp("Unpublished", cgp->cit))
1544                                         unpublished = TRUE;
1545                                 else if (title == NULL)
1546                                         title2 = cgp->cit;
1547                         }
1548                         volume = cgp->volume;
1549                         issue=cgp->issue;
1550                         pages=cgp->pages;
1551             if (cgp->title != NULL)
1552                                 titleunique = cgp->title;
1553                         else if (title2 != NULL)
1554                                 titleunique = title2;
1555                         else if (title == NULL)
1556                                 titleunique = cgp->cit;
1557                         if (title == NULL && alp == NULL && cgp->title == NULL &&
1558                                 volume == NULL && pages == NULL && issue == NULL) {
1559                                 titleunique = NULL;
1560                                 if ((cit = StringSave(cgp->cit)) != NULL) {
1561                                         if (!unique) {
1562                                                 for (s = cit + StringLen(cit) -1; 
1563                                                                         s > cit && *s !='|';   s--) continue;
1564                                                 if (*s == '|' ) {
1565                                                         *s = '\0';
1566                                                 }
1567                                         }
1568                                         diff = LabelCopy(buf, cit, buflen);
1569                                         MemFree(cit);
1570                                 }
1571                                 return 0;
1572                         }
1573                         break;
1574                 default:
1575                         sprintf(tbuf,"Unknown pub[%d]", (int)(pub->choice));
1576                         title2 = tbuf;
1577                         break;
1578 
1579         }
1580 
1581         if (imp != NULL)
1582         {
1583                 if (dp == NULL)
1584                         dp = imp->date;
1585                 if (volume == NULL)
1586                         volume = imp->volume;
1587                 if (issue == NULL)
1588                         issue = imp->issue;
1589                 if (pages == NULL)
1590                         pages = imp->pages;
1591                 part_sup = imp->part_sup;
1592                 part_supi = imp->part_supi;
1593         }
1594 
1595         if (alp != NULL)
1596         {
1597                 vnp2 = alp->names;
1598                 if (vnp2 != NULL)
1599                 {
1600                         if (alp->choice == 1)   /* std name */
1601                         {
1602                                 ap = (AuthorPtr)(vnp2->data.ptrvalue);
1603                                 diff = PersonIdLabel(ap->name, buf, buflen, PIDLABEL_GENBANK);
1604                         }
1605                         else
1606                                 diff = LabelCopy(buf, (CharPtr)(vnp2->data.ptrvalue), buflen);
1607                 buflen -= diff;
1608                 buf += diff;
1609                 }
1610         }
1611 
1612         if (dp != NULL)
1613         {
1614                 if (dp->data[0])
1615                 {
1616                         if (pub->choice == PUB_Sub && dp->data[2] != 0 && dp->data[3] != 0){
1617                                 sprintf(tbuf, "%d-%d-%d", (int)(dp->data[2]), 
1618                                                 (int)(dp->data[3]), (int)(dp->data[1])+1900);
1619                                 year = tbuf;
1620                         } else {
1621                                 sprintf(tbuf, "%d", (int)(dp->data[1])+1900);
1622                                 year = tbuf;
1623                         }
1624                 }
1625                 else
1626                         year = dp->str; 
1627                 diff = LabelCopyExtra(buf, year, buflen, " (", ") ");
1628                 buflen -= diff; buf += diff;
1629         }
1630 
1631         if ((title != NULL) && (titleunique == NULL))
1632                 titleunique = (CharPtr)(title->data.ptrvalue);
1633 
1634         if (title2 == NULL)
1635         {
1636                 if (title != NULL)
1637                         title2 = (CharPtr)(title->data.ptrvalue);
1638                         
1639         }
1640 
1641         if (title2 != NULL)
1642         {
1643                 if (cbp != NULL)
1644                         title1 = "(in) ";
1645 
1646                 diff = LabelCopyExtra(buf, title2, buflen, title1, " ");
1647                 buflen -= diff; buf += diff;
1648         }
1649 
1650         if (volume != NULL)
1651         {
1652                 if (part_sup != NULL)
1653                         title1 = part_sup;
1654                 else
1655                         title1 = ":";
1656                         
1657                 diff = LabelCopyExtra(buf, volume, buflen, NULL, title1);
1658                 buflen -= diff; buf += diff;
1659                 if (part_sup != NULL)
1660                 {
1661                         diff = LabelCopyExtra(buf, ":", buflen, NULL, NULL);
1662                         buflen -= diff; buf += diff;
1663                 }
1664         }
1665 
1666         if (issue != NULL)
1667         {
1668                 if (part_supi != NULL)
1669                         title1 = part_supi;
1670                 else
1671                         title1 = ")";
1672                         
1673                 diff = LabelCopyExtra(buf, issue, buflen, "(" , title1);
1674                 buflen -= diff; buf += diff;
1675                 if (part_supi != NULL)
1676                 {
1677                         diff = LabelCopyExtra(buf, ")", buflen, NULL, NULL);
1678                         buflen -= diff; buf += diff;
1679                 }
1680         }
1681 
1682         if (pages != NULL)
1683         {
1684                 diff = LabelCopy(buf, pages, buflen);
1685                 buflen -= diff; buf += diff;
1686         }
1687      
1688     if (unpublished)
1689     {
1690         diff = LabelCopy(buf, "Unpublished", buflen);
1691         buflen -= diff; buf += diff;
1692     }
1693 
1694         if (unique)  /* put on unique tag made from title */
1695         {
1696                 done = FALSE;
1697                 i=0;
1698                 if (titleunique != NULL && *titleunique != '\0')
1699                 {
1700                         while ((! done) && (i < 40))
1701                         {
1702                                 tbuf[i] = *titleunique;
1703                                 i++;
1704                                 while (! IS_WHITESP(*titleunique))
1705                                 {
1706                                         titleunique++;
1707                                         if (*titleunique == '\0')
1708                                         {
1709                                                 done = TRUE;
1710                                                 break;
1711                                         }
1712                                 }
1713                                 while (IS_WHITESP(*titleunique))
1714                                 {
1715                                         titleunique++;
1716                                         if (*titleunique == '\0')
1717                                         {
1718                                                 done = TRUE;
1719                                                 break;
1720                                         }
1721                                 }
1722                         }
1723                 }
1724                 tbuf[i] = '\0';
1725                 diff = LabelCopyExtra(buf, tbuf, buflen, "|" , NULL);
1726                 buflen -= diff; buf += diff;
1727         }
1728 
1729     
1730         return (len - buflen);
1731 }
1732 
1733 

source navigation ]   [ diff markup ]   [ identifier search ]   [ freetext search ]   [ file search ]  

This page was automatically generated by the LXR engine.
Visit the LXR main site for more information.