MIDAS
Loading...
Searching...
No Matches
Midas Elog Functions (el_xxx)

Functions

static void el_decode (const char *message, const char *key, char *result, int size)
 
static void xwrite (const char *filename, int fd, const void *data, int size)
 
static int xread (const char *filename, int fd, void *data, int size)
 
static void xtruncate (const char *filename, int fd)
 
INT el_submit (int run, const char *author, const char *type, const char *syst, const char *subject, const char *text, const char *reply_to, const char *encoding, const char *afilename1, const char *buffer1, INT buffer_size1, const char *afilename2, const char *buffer2, INT buffer_size2, const char *afilename3, const char *buffer3, INT buffer_size3, char *tag, INT tag_size)
 
INT el_search_message (char *tag, int *fh, BOOL walk, char *xfilename, int xfilename_size)
 
INT el_retrieve (char *tag, char *date, int *run, char *author, char *type, char *syst, char *subject, char *text, int *textsize, char *orig_tag, char *reply_tag, char *attachment1, char *attachment2, char *attachment3, char *encoding)
 
INT el_search_run (int run, char *return_tag)
 
INT el_delete_message (const char *tag)
 

Detailed Description

dox


Function Documentation

◆ el_decode()

static void el_decode ( const char message,
const char key,
char result,
int  size 
)
static

dox

Definition at line 35 of file elog.cxx.

36{
37 int i;
38 const char *pc;
39
40 if (result == NULL)
41 return;
42
43 *result = 0;
44
45 pc = strstr(message, key);
46
47 if (!pc)
48 return;
49
50 pc += strlen(key);
51
52 for (i=0; i<size; i++) {
53 if (pc[i] == 0)
54 break;
55 if (pc[i] == '\n')
56 break;
57 result[i] = pc[i];
58 }
59
60 assert(i<=size); // ensure that code above did not overrun the "result" array
61
62 if (i==size)
63 result[size-1] = 0;
64 else
65 result[i] = 0;
66}
KEY key
Definition mdump.cxx:34
INT i
Definition mdump.cxx:32
#define message(type, str)
TH1X EXPRT * h1_book(const char *name, const char *title, int bins, double min, double max)
Definition rmidas.h:24
Here is the call graph for this function:
Here is the caller graph for this function:

◆ el_delete_message()

INT el_delete_message ( const char tag)

Definition at line 1014 of file elog.cxx.

1031{
1032#ifdef LOCAL_ROUTINES
1033 INT size, fh, semaphore, offset = 0, tail_size, status;
1034 char dir[256];
1035 char str[256];
1036 char file_name[256+256+10];
1037 HNDLE hDB;
1038 char *buffer = NULL;
1039
1041
1042 /* request semaphore */
1044 status = ss_semaphore_wait_for(semaphore, 5 * 60 * 1000);
1045 if (status != SS_SUCCESS) {
1046 cm_msg(MERROR, "el_delete_message",
1047 "Cannot lock experiment semaphore, ss_semaphore_wait_for() status %d", status);
1048 abort();
1049 }
1050
1051 /* generate file name YYMMDD.log in data directory */
1053
1054 size = sizeof(dir);
1055 memset(dir, 0, size);
1056 status = db_get_value(hDB, 0, "/Logger/Elog dir", dir, &size, TID_STRING, FALSE);
1057 if (status != DB_SUCCESS)
1058 db_get_value(hDB, 0, "/Logger/Data dir", dir, &size, TID_STRING, TRUE);
1059
1060 if (dir[0] != 0 && dir[strlen(dir) - 1] != DIR_SEPARATOR)
1062
1063 strcpy(str, tag);
1064 if (strchr(str, '.')) {
1065 offset = atoi(strchr(str, '.') + 1);
1066 *strchr(str, '.') = 0;
1067 }
1068 sprintf(file_name, "%s%s.log", dir, str);
1069 fh = open(file_name, O_CREAT | O_RDWR | O_BINARY, 0644);
1070 if (fh < 0) {
1071 ss_semaphore_release(semaphore);
1072 return EL_FILE_ERROR;
1073 }
1075 xread(file_name, fh, str, 16);
1076 size = atoi(str + 9);
1077
1078 /* buffer tail of logfile */
1079 lseek(fh, 0, SEEK_END);
1080 tail_size = TELL(fh) - (offset + size);
1081
1082 if (tail_size > 0) {
1083 buffer = (char *) M_MALLOC(tail_size);
1084 if (buffer == NULL) {
1085 close(fh);
1086 ss_semaphore_release(semaphore);
1087 return EL_FILE_ERROR;
1088 }
1089
1090 lseek(fh, offset + size, SEEK_SET);
1091 xread(file_name, fh, buffer, tail_size);
1092 }
1094
1095 if (tail_size > 0) {
1096 xwrite(file_name, fh, buffer, tail_size);
1097 M_FREE(buffer);
1098 }
1099
1100 /* truncate file here */
1101#ifdef OS_WINNT
1102 chsize(fh, TELL(fh));
1103#else
1105#endif
1106
1107 /* if file length gets zero, delete file */
1108 tail_size = lseek(fh, 0, SEEK_END);
1109 close(fh);
1110
1111 if (tail_size == 0)
1113
1114 /* release elog semaphore */
1115 ss_semaphore_release(semaphore);
1116#endif /* LOCAL_ROUTINES */
1117
1118 return EL_SUCCESS;
1119}
#define FALSE
Definition cfortran.h:309
INT cm_get_experiment_database(HNDLE *hDB, HNDLE *hKeyClient)
Definition midas.cxx:3011
INT cm_get_experiment_semaphore(INT *semaphore_alarm, INT *semaphore_elog, INT *semaphore_history, INT *semaphore_msg)
Definition midas.cxx:3033
static void xwrite(const char *filename, int fd, const void *data, int size)
Definition elog.cxx:68
static int xread(const char *filename, int fd, void *data, int size)
Definition elog.cxx:76
static void xtruncate(const char *filename, int fd)
Definition elog.cxx:89
#define DB_SUCCESS
Definition midas.h:631
#define SS_SUCCESS
Definition midas.h:663
#define EL_SUCCESS
Definition midas.h:745
#define EL_FILE_ERROR
Definition midas.h:746
#define TID_STRING
Definition midas.h:346
#define MERROR
Definition midas.h:559
#define O_BINARY
Definition msystem.h:219
INT ss_semaphore_release(HNDLE semaphore_handle)
Definition system.cxx:2781
INT ss_semaphore_wait_for(HNDLE semaphore_handle, DWORD timeout_millisec)
Definition system.cxx:2639
INT cm_msg(INT message_type, const char *filename, INT line, const char *routine, const char *format,...)
Definition midas.cxx:915
#define TELL(fh)
Definition msystem.h:243
INT db_get_value(HNDLE hDB, HNDLE hKeyRoot, const char *key_name, void *data, INT *buf_size, DWORD type, BOOL create)
Definition odb.cxx:5415
HNDLE hDB
main ODB handle
Definition mana.cxx:207
static int offset
Definition mgd.cxx:1500
#define DIR_SEPARATOR
Definition midas.h:193
INT HNDLE
Definition midas.h:132
#define M_MALLOC(x)
Definition midas.h:1552
#define DIR_SEPARATOR_STR
Definition midas.h:194
int INT
Definition midas.h:129
#define M_FREE(x)
Definition midas.h:1554
#define TRUE
Definition midas.h:182
static std::string remove(const std::string s, char c)
Definition mjsonrpc.cxx:253
char str[256]
Definition odbhist.cxx:33
char file_name[256]
Definition odbhist.cxx:41
DWORD status
Definition odbhist.cxx:39
Here is the call graph for this function:
Here is the caller graph for this function:

◆ el_retrieve()

INT el_retrieve ( char tag,
char date,
int run,
char author,
char type,
char syst,
char subject,
char text,
int textsize,
char orig_tag,
char reply_tag,
char attachment1,
char attachment2,
char attachment3,
char encoding 
)

Definition at line 770 of file elog.cxx.

804{
805 int size, fh = 0, search_status, rd;
806 char str[256], *p;
807 char thread[256];
808 char attachment_all[3*256+100]; /* size of attachement1/2/3 from show_elog_submit_query() */
809 char *message = NULL;
810 size_t message_size = 0;
811 char filename[256];
812
813 if (tag[0]) {
814 search_status = el_search_message(tag, &fh, TRUE, filename, sizeof(filename));
816 return search_status;
817 } else {
818 /* open most recent message */
819 strcpy(tag, "-1");
820 search_status = el_search_message(tag, &fh, TRUE, filename, sizeof(filename));
822 return search_status;
823 }
824
825 //printf("el_retrieve: reading [%s]\n", filename);
826
827 /* extract message size */
828 TELL(fh);
829 rd = xread(filename, fh, str, 15);
830 if (rd != 15)
831 return EL_FILE_ERROR;
832
833 /* make sure the input string is zero-terminated before we call atoi() */
834 str[15] = 0;
835
836 /* get size */
837 size = atoi(str + 9);
838
839 if ((strncmp(str, "$Start$:", 8) != 0) || (size <= 15)) {
840 cm_msg(MERROR, "el_retrieve", "cannot read from \'%s\', corrupted file: no $Start$ or bad size in \"%s\"", filename, str);
841 close(fh);
842 return EL_FILE_ERROR;
843 }
844
845 message_size = size + 1;
846 message = (char*)malloc(message_size);
847
848 if (!message) {
849 cm_msg(MERROR, "el_retrieve", "cannot read from \'%s\', cannot malloc() %d bytes, errno %d (%s)", filename, (int)message_size, errno, strerror(errno));
850 free(message);
851 close(fh);
852 return EL_FILE_ERROR;
853 }
854
856
857 rd = read(fh, message, size);
858 if (rd <= 0 || !((rd + 15 == size) || (rd == size))) {
859 cm_msg(MERROR, "el_retrieve", "cannot read from \'%s\', read(%d) returned %d, errno %d (%s)", filename, size, rd, errno, strerror(errno));
860 free(message);
861 close(fh);
862 return EL_FILE_ERROR;
863 }
864
865 close(fh);
866
867 /* decode message */
868 if (strstr(message, "Run: ") && run)
869 *run = atoi(strstr(message, "Run: ") + 5);
870
871 el_decode(message, "Date: ", date, 80); /* size from show_elog_submit_query() */
872 el_decode(message, "Thread: ", thread, sizeof(thread));
873 el_decode(message, "Author: ", author, 80); /* size from show_elog_submit_query() */
874 el_decode(message, "Type: ", type, 80); /* size from show_elog_submit_query() */
875 el_decode(message, "System: ", syst, 80); /* size from show_elog_submit_query() */
876 el_decode(message, "Subject: ", subject, 256); /* size from show_elog_submit_query() */
877 el_decode(message, "Attachment: ", attachment_all, sizeof(attachment_all));
878 el_decode(message, "Encoding: ", encoding, 80); /* size from show_elog_submit_query() */
879
880 /* break apart attachements */
882 attachment1[0] = attachment2[0] = attachment3[0] = 0;
883 p = strtok(attachment_all, ",");
884 if (p != NULL) {
885 mstrlcpy(attachment1, p, 256); /* size from show_elog_submit_query() */
886 p = strtok(NULL, ",");
887 if (p != NULL) {
888 mstrlcpy(attachment2, p, 256); /* size from show_elog_submit_query() */
889 p = strtok(NULL, ",");
890 if (p != NULL)
891 mstrlcpy(attachment3, p, 256); /* size from show_elog_submit_query() */
892 }
893 }
894 }
895
896 /* conver thread in reply-to and reply-from */
897 if (orig_tag != NULL && reply_tag != NULL) {
898 p = strtok(thread, " \r");
899 if (p != NULL)
900 strcpy(orig_tag, p);
901 else
902 strcpy(orig_tag, "");
903 p = strtok(NULL, " \r");
904 if (p != NULL)
905 strcpy(reply_tag, p);
906 else
907 strcpy(reply_tag, "");
908 if (atoi(orig_tag) == 0)
909 orig_tag[0] = 0;
910 if (atoi(reply_tag) == 0)
911 reply_tag[0] = 0;
912 }
913
914 p = strstr(message, "========================================\n");
915
916 if (text != NULL) {
917 if (p != NULL) {
918 p += 41;
919 if ((int) strlen(p) >= *textsize) {
920 strncpy(text, p, *textsize - 1);
921 text[*textsize - 1] = 0;
922 free(message);
923 return EL_TRUNCATED;
924 } else {
925 strcpy(text, p);
926
927 /* strip end tag */
928 if (strstr(text, "$End$"))
929 *strstr(text, "$End$") = 0;
930
931 *textsize = strlen(text);
932 }
933 } else {
934 text[0] = 0;
935 *textsize = 0;
936 }
937 }
938
939 free(message);
940 message = NULL;
941
943 return EL_LAST_MSG;
944
945 return EL_SUCCESS;
946}
double textsize
static void el_decode(const char *message, const char *key, char *result, int size)
Definition elog.cxx:35
INT el_search_message(char *tag, int *fh, BOOL walk, char *xfilename, int xfilename_size)
Definition elog.cxx:500
#define EL_TRUNCATED
Definition midas.h:748
#define EL_LAST_MSG
Definition midas.h:750
INT type
Definition mana.cxx:269
#define read(n, a, f)
INT thread(void *p)
Definition odbedit.cxx:43
DWORD run
Definition odbhist.cxx:39
Here is the call graph for this function:
Here is the caller graph for this function:

◆ el_search_message()

INT el_search_message ( char tag,
int fh,
BOOL  walk,
char xfilename,
int  xfilename_size 
)

dox

Definition at line 500 of file elog.cxx.

501{
502 int i, size, offset, direction, status;
503 struct tm tms;
504 time_t lt, ltime=0, lact;
505 char str[256];
506 char dir[256];
507 char file_name[256+100];
508 HNDLE hDB;
509
510 ss_tzset(); // required by localtime_r()
511
512 if (xfilename && xfilename_size > 0)
513 *xfilename = 0;
514
515 /* open file */
517
518 size = sizeof(dir);
519 memset(dir, 0, size);
520 status = db_get_value(hDB, 0, "/Logger/Elog dir", dir, &size, TID_STRING, FALSE);
521 if (status != DB_SUCCESS)
522 db_get_value(hDB, 0, "/Logger/Data dir", dir, &size, TID_STRING, TRUE);
523
524 if (dir[0] != 0 && dir[strlen(dir) - 1] != DIR_SEPARATOR)
526
527 /* check tag for direction */
528 direction = 0;
529 if (strpbrk(tag, "+-")) {
530 direction = atoi(strpbrk(tag, "+-"));
531 *strpbrk(tag, "+-") = 0;
532 }
533
534 /* if tag is given, open file directly */
535 if (tag[0]) {
536 /* extract time structure from tag */
537 memset(&tms, 0, sizeof(struct tm));
538 tms.tm_year = (tag[0] - '0') * 10 + (tag[1] - '0');
539 tms.tm_mon = (tag[2] - '0') * 10 + (tag[3] - '0') - 1;
540 tms.tm_mday = (tag[4] - '0') * 10 + (tag[5] - '0');
541 tms.tm_hour = 12;
542
543 if (tms.tm_year < 90)
544 tms.tm_year += 100;
545 ltime = lt = ss_mktime(&tms);
546
547 strcpy(str, tag);
548 if (strchr(str, '.')) {
549 offset = atoi(strchr(str, '.') + 1);
550 *strchr(str, '.') = 0;
551 } else
552 return EL_FILE_ERROR;
553
554 do {
556
557 sprintf(file_name, "%s%02d%02d%02d.log", dir, tms.tm_year % 100, tms.tm_mon + 1, tms.tm_mday);
558
559 if (xfilename)
561
562 *fh = open(file_name, O_RDWR | O_BINARY, 0644);
563
564 if (*fh < 0) {
565 if (!walk)
566 return EL_FILE_ERROR;
567
568 if (direction == -1)
569 ltime -= 3600 * 24; /* one day back */
570 else
571 ltime += 3600 * 24; /* go forward one day */
572
573 /* set new tag */
575 sprintf(tag, "%02d%02d%02d.0", tms.tm_year % 100, tms.tm_mon + 1, tms.tm_mday);
576 }
577
578 /* in forward direction, stop today */
579 if (direction != -1 && ltime > time(NULL) + 3600 * 24)
580 break;
581
582 /* in backward direction, go back 10 years */
583 if (direction == -1 && abs((INT) lt - (INT) ltime) > 3600 * 24 * 365 * 10)
584 break;
585
586 } while (*fh < 0);
587
588 if (*fh < 0)
589 return EL_FILE_ERROR;
590
592
593 /* check if start of message */
594 i = xread(file_name, *fh, str, 15);
595 if (i <= 0) {
596 close(*fh);
597 return EL_FILE_ERROR;
598 }
599
600 if (strncmp(str, "$Start$: ", 9) != 0) {
601 close(*fh);
602 return EL_FILE_ERROR;
603 }
604
606 }
607
608 /* open most recent file if no tag given */
609 if (tag[0] == 0) {
610 time((time_t *) &lt);
611 ltime = lt;
612 do {
614
615 sprintf(file_name, "%s%02d%02d%02d.log", dir, tms.tm_year % 100, tms.tm_mon + 1, tms.tm_mday);
616
617 if (xfilename)
619
620 *fh = open(file_name, O_RDWR | O_BINARY, 0644);
621
622 if (*fh < 0)
623 ltime -= 3600 * 24; /* one day back */
624
625 } while (*fh < 0 && (INT) lt - (INT) ltime < 3600 * 24 * 365);
626
627 if (*fh < 0)
628 return EL_FILE_ERROR;
629
630 /* remember tag */
631 sprintf(tag, "%02d%02d%02d", tms.tm_year % 100, tms.tm_mon + 1, tms.tm_mday);
632
633 lseek(*fh, 0, SEEK_END);
634
635 sprintf(tag + strlen(tag), ".%d", (int) TELL(*fh));
636 }
637
638
639 if (direction == -1) {
640 /* seek previous message */
641
642 if (TELL(*fh) == 0) {
643 /* go back one day */
644 close(*fh);
645
646 lt = ltime;
647 do {
648 lt -= 3600 * 24;
649 localtime_r(&lt, &tms);
650 sprintf(str, "%02d%02d%02d.0", tms.tm_year % 100, tms.tm_mon + 1, tms.tm_mday);
651
653
654 if (xfilename)
656
657 } while (status != EL_SUCCESS && (INT) ltime - (INT) lt < 3600 * 24 * 365);
658
659 if (status != EL_SUCCESS)
660 return EL_FIRST_MSG;
661
662 /* adjust tag */
663 strcpy(tag, str);
664
665 /* go to end of current file */
666 lseek(*fh, 0, SEEK_END);
667 }
668
669 /* read previous message size */
670 lseek(*fh, -17, SEEK_CUR);
671 i = xread(file_name, *fh, str, 17);
672 if (i <= 0) {
673 close(*fh);
674 return EL_FILE_ERROR;
675 }
676
677 if (strncmp(str, "$End$: ", 7) != 0) {
678 close(*fh);
679 return EL_FILE_ERROR;
680 }
681
682 /* make sure the input string to atoi() is zero-terminated:
683 * $End$: 355garbage
684 * 01234567890123456789 */
685 str[15] = 0;
686
687 size = atoi(str + 7);
688 if (size <= 15) {
689 close(*fh);
690 return EL_FILE_ERROR;
691 }
692
693 lseek(*fh, -size, SEEK_CUR);
694
695 /* adjust tag */
696 sprintf(strchr(tag, '.') + 1, "%d", (int) TELL(*fh));
697 }
698
699 if (direction == 1) {
700 /* seek next message */
701
702 /* read current message size */
703 TELL(*fh);
704
705 i = xread(file_name, *fh, str, 15);
706 if (i <= 0) {
707 close(*fh);
708 return EL_FILE_ERROR;
709 }
710 lseek(*fh, -15, SEEK_CUR);
711
712 if (strncmp(str, "$Start$: ", 9) != 0) {
713 close(*fh);
714 return EL_FILE_ERROR;
715 }
716
717 /* make sure the input string to atoi() is zero-terminated
718 * $Start$: 606garbage
719 * 01234567890123456789 */
720 str[15] = 0;
721
722 size = atoi(str + 9);
723
724 if (size <= 15) {
725 close(*fh);
726 return EL_FILE_ERROR;
727 }
728
729 lseek(*fh, size, SEEK_CUR);
730
731 /* if EOF, goto next day */
732 i = xread(file_name, *fh, str, 15);
733 if (i < 15) {
734 close(*fh);
735 time((time_t *) &lact);
736
737 lt = ltime;
738 do {
739 lt += 3600 * 24;
740 localtime_r(&lt, &tms);
741 sprintf(str, "%02d%02d%02d.0", tms.tm_year % 100, tms.tm_mon + 1, tms.tm_mday);
742
744
745 if (xfilename)
747
748 } while (status != EL_SUCCESS && (INT) lt - (INT) lact < 3600 * 24);
749
750 if (status != EL_SUCCESS)
751 return EL_LAST_MSG;
752
753 /* adjust tag */
754 strcpy(tag, str);
755
756 /* go to beginning of current file */
757 lseek(*fh, 0, SEEK_SET);
758 } else
759 lseek(*fh, -15, SEEK_CUR);
760
761 /* adjust tag */
762 sprintf(strchr(tag, '.') + 1, "%d", (int) TELL(*fh));
763 }
764
765 return EL_SUCCESS;
766}
#define EL_FIRST_MSG
Definition midas.h:749
time_t ss_mktime(struct tm *tms)
Definition system.cxx:3365
void ss_tzset()
Definition system.cxx:3355
MUTEX_T * tm
Definition odbedit.cxx:39
Here is the call graph for this function:
Here is the caller graph for this function:

◆ el_search_run()

INT el_search_run ( int  run,
char return_tag 
)

Definition at line 950 of file elog.cxx.

968{
969 int actual_run=0, fh, status;
970 char tag[256];
971
972 tag[0] = return_tag[0] = 0;
973
974 do {
975 /* open first message in file */
976 strcat(tag, "-1");
977 status = el_search_message(tag, &fh, TRUE, NULL, 0);
978 if (status == EL_FIRST_MSG)
979 break;
980 if (status != EL_SUCCESS)
981 return status;
982 close(fh);
983
984 if (strchr(tag, '.') != NULL)
985 strcpy(strchr(tag, '.'), ".0");
986
989 } while (actual_run >= run);
990
991 while (actual_run < run) {
992 strcat(tag, "+1");
993 status = el_search_message(tag, &fh, TRUE, NULL, 0);
994 if (status == EL_LAST_MSG)
995 break;
996 if (status != EL_SUCCESS)
997 return status;
998 close(fh);
999
1002 }
1003
1004 strcpy(return_tag, tag);
1005
1007 return status;
1008
1009 return EL_SUCCESS;
1010}
INT el_retrieve(char *tag, char *date, int *run, char *author, char *type, char *syst, char *subject, char *text, int *textsize, char *orig_tag, char *reply_tag, char *attachment1, char *attachment2, char *attachment3, char *encoding)
Definition elog.cxx:770
Here is the call graph for this function:
Here is the caller graph for this function:

◆ el_submit()

INT el_submit ( int  run,
const char author,
const char type,
const char syst,
const char subject,
const char text,
const char reply_to,
const char encoding,
const char afilename1,
const char buffer1,
INT  buffer_size1,
const char afilename2,
const char buffer2,
INT  buffer_size2,
const char afilename3,
const char buffer3,
INT  buffer_size3,
char tag,
INT  tag_size 
)

dox Submit an ELog entry.

Parameters
runRun Number.
authorMessage author.
typeMessage type.
systMessage system.
subjectSubject.
textMessage text.
reply_toIn reply to this message.
encodingText encoding, either HTML or plain.
afilename1File name of attachment.
buffer1File contents.
buffer_size1Size of buffer in bytes.
afilename2File name of attachment.
buffer2File contents.
buffer_size2Size of buffer in bytes.
afilename3File name of attachment.
buffer3File contents.
buffer_size3Size of buffer in bytes.
tagIf given, edit existing message.
tag_sizeMaximum size of tag.
Returns
EL_SUCCESS

Definition at line 124 of file elog.cxx.

129{
130 if (rpc_is_remote())
131 return rpc_call(RPC_EL_SUBMIT, run, author, type, syst, subject,
132 text, reply_to, encoding,
135
136#ifdef LOCAL_ROUTINES
137 {
138 INT size, fh, status, run_number, semaphore, idx, offset = 0, tail_size = 0;
139 char file_name[256+256+100];
140 char afile_name[3][256+256];
141 char dir[256];
142 char start_str[80], end_str[80], last[80], date[80], thread[80], attachment[256];
143 HNDLE hDB;
144 time_t now;
145 char *p;
146 char* message = NULL;
147 size_t message_size = 0;
148 BOOL bedit;
149 struct tm tms;
150
152
153 bedit = (tag[0] != 0);
154
155 /* request semaphore */
157 status = ss_semaphore_wait_for(semaphore, 5 * 60 * 1000);
158 if (status != SS_SUCCESS) {
159 cm_msg(MERROR, "el_submit", "Cannot lock experiment semaphore, ss_semaphore_wait_for() status %d", status);
160 abort();
161 }
162
163 /* get run number from ODB if not given */
164 if (run > 0)
165 run_number = run;
166 else {
167 /* get run number */
168 size = sizeof(run_number);
169 status = db_get_value(hDB, 0, "/Runinfo/Run number", &run_number, &size, TID_INT, TRUE);
170 assert(status == SUCCESS);
171 }
172
173 if (run_number < 0) {
174 cm_msg(MERROR, "el_submit", "aborting on attempt to use invalid run number %d", run_number);
175 abort();
176 }
177
178 for (idx = 0; idx < 3; idx++) {
179 /* generate filename for attachment */
180 afile_name[idx][0] = file_name[0] = 0;
181
182 char afilename[256];
183 const char* buffer = NULL;
184 int buffer_size = 0;
185
186 if (idx == 0) {
188 buffer = buffer1;
189 buffer_size = buffer_size1;
190 } else if (idx == 1) {
192 buffer = buffer2;
193 buffer_size = buffer_size2;
194 } else if (idx == 2) {
196 buffer = buffer3;
197 buffer_size = buffer_size3;
198 }
199
200 if (afilename[0]) {
201 strcpy(file_name, afilename);
202 p = file_name;
203 while (strchr(p, ':'))
204 p = strchr(p, ':') + 1;
205 while (strchr(p, '\\'))
206 p = strchr(p, '\\') + 1; /* NT */
207 while (strchr(p, '/'))
208 p = strchr(p, '/') + 1; /* Unix */
209 while (strchr(p, ']'))
210 p = strchr(p, ']') + 1; /* VMS */
211
212 /* assemble ELog filename */
213 if (p[0]) {
214 dir[0] = 0;
215 if (hDB > 0) {
216 size = sizeof(dir);
217 memset(dir, 0, size);
218 status = db_get_value(hDB, 0, "/Logger/Elog dir", dir, &size, TID_STRING, FALSE);
219 if (status != DB_SUCCESS)
220 db_get_value(hDB, 0, "/Logger/Data dir", dir, &size, TID_STRING, TRUE);
221
222 if (dir[0] != 0 && dir[strlen(dir) - 1] != DIR_SEPARATOR)
224 }
225
226 ss_tzset();
227 time(&now);
228 localtime_r(&now, &tms);
229
230 char str[256];
231 mstrlcpy(str, p, sizeof(str));
232 sprintf(afile_name[idx], "%02d%02d%02d_%02d%02d%02d_%s",
233 tms.tm_year % 100, tms.tm_mon + 1, tms.tm_mday,
234 tms.tm_hour, tms.tm_min, tms.tm_sec, str);
235 sprintf(file_name, "%s%02d%02d%02d_%02d%02d%02d_%s", dir,
236 tms.tm_year % 100, tms.tm_mon + 1, tms.tm_mday,
237 tms.tm_hour, tms.tm_min, tms.tm_sec, str);
238
239 /* save attachment */
240 fh = open(file_name, O_CREAT | O_RDWR | O_BINARY, 0644);
241 if (fh < 0) {
242 cm_msg(MERROR, "el_submit", "Cannot write attachment file \"%s\", open() returned %d, errno %d (%s)", file_name, fh, errno, strerror(errno));
243 } else {
244 xwrite(file_name, fh, buffer, buffer_size);
245 close(fh);
246 }
247 }
248 }
249 } // loop over attachmnents
250
251 /* generate new file name YYMMDD.log in data directory */
253
254 size = sizeof(dir);
255 memset(dir, 0, size);
256 status = db_get_value(hDB, 0, "/Logger/Elog dir", dir, &size, TID_STRING, FALSE);
257 if (status != DB_SUCCESS)
258 db_get_value(hDB, 0, "/Logger/Data dir", dir, &size, TID_STRING, TRUE);
259
260 if (dir[0] != 0 && dir[strlen(dir) - 1] != DIR_SEPARATOR)
262
263 ss_tzset();
264
265 char* buffer = NULL;
266
267 if (bedit) {
268 /* edit existing message */
269 char str[256];
270 mstrlcpy(str, tag, sizeof(str));
271 if (strchr(str, '.')) {
272 offset = atoi(strchr(str, '.') + 1);
273 *strchr(str, '.') = 0;
274 }
275 sprintf(file_name, "%s%s.log", dir, str);
276 fh = open(file_name, O_CREAT | O_RDWR | O_BINARY, 0644);
277 if (fh < 0) {
278 ss_semaphore_release(semaphore);
279 return EL_FILE_ERROR;
280 }
282 xread(file_name, fh, str, 16);
283
284 if (strncmp(str, "$Start$", 7) != 0) {
285 cm_msg(MERROR, "el_submit", "cannot read from \'%s\', corrupted file: no $Start$ in \"%s\"", file_name, str);
286 close(fh);
287 return EL_FILE_ERROR;
288 }
289
290 size = atoi(str + 9);
291
292 if (size < 1) {
293 cm_msg(MERROR, "el_submit", "cannot read from \'%s\', corrupted file: bad size %d in \"%s\"", file_name, size, str);
294 close(fh);
295 return EL_FILE_ERROR;
296 }
297
298 message = (char*)malloc(size);
299
300 if (!message) {
301 cm_msg(MERROR, "el_submit", "cannot read from \'%s\', corrupted file: bad size %d in \"%s\", cannot malloc(%d): errno %d (%s)", file_name, size, str, size, errno, strerror(errno));
302 close(fh);
303 return EL_FILE_ERROR;
304 }
305
306 status = read(fh, message, size);
307 if (status != size && status + 16 != size) {
308 free(message);
309 return EL_FILE_ERROR;
310 }
311
312 el_decode(message, "Date: ", date, sizeof(date));
313 el_decode(message, "Thread: ", thread, sizeof(thread));
314 el_decode(message, "Attachment: ", attachment, sizeof(attachment));
315
316 free(message);
317 message = NULL;
318
319 /* buffer tail of logfile */
320 lseek(fh, 0, SEEK_END);
321 tail_size = TELL(fh) - (offset + size);
322
323 if (tail_size > 0) {
324 int n;
325
326 buffer = (char *) M_MALLOC(tail_size);
327 if (buffer == NULL) {
328 close(fh);
329 ss_semaphore_release(semaphore);
330 return EL_FILE_ERROR;
331 }
332
333 lseek(fh, offset + size, SEEK_SET);
334 n = xread(file_name, fh, buffer, tail_size);
335 if (n != tail_size)
336 return EL_FILE_ERROR;
337 }
339 } else {
340 /* create new message */
341 ss_tzset(); // required by localtime_r()
342 time(&now);
343 localtime_r(&now, &tms);
344
345 sprintf(file_name, "%s%02d%02d%02d.log", dir, tms.tm_year % 100, tms.tm_mon + 1, tms.tm_mday);
346
347 fh = open(file_name, O_CREAT | O_RDWR | O_BINARY, 0644);
348 if (fh < 0) {
349 ss_semaphore_release(semaphore);
350 return EL_FILE_ERROR;
351 }
352
353 assert(sizeof(date) >= 32);
354 ctime_r(&now, date);
355 date[24] = 0;
356
357 if (reply_to[0])
358 sprintf(thread, "%16s %16s", reply_to, "0");
359 else
360 sprintf(thread, "%16s %16s", "0", "0");
361
362 lseek(fh, 0, SEEK_END);
363 }
364
365 message_size = 1000;
367 message_size += strlen(author);
376 message_size += strlen(text);
377
378 //printf("message_size %d, text %d\n", (int)message_size, (int)strlen(text));
379
380 message = (char*)malloc(message_size);
381
382 if (!message) {
383 cm_msg(MERROR, "el_submit", "cannot malloc() %d bytes: errno %d (%s)", size, errno, strerror(errno));
384 close(fh);
385 return EL_FILE_ERROR;
386 }
387
388 /* compose message */
389
390 sprintf(message, "Date: %s\n", date);
391 sprintf(message + strlen(message), "Thread: %s\n", thread);
392 sprintf(message + strlen(message), "Run: %d\n", run_number);
393 sprintf(message + strlen(message), "Author: %s\n", author);
394 sprintf(message + strlen(message), "Type: %s\n", type);
395 sprintf(message + strlen(message), "System: %s\n", syst);
396 sprintf(message + strlen(message), "Subject: %s\n", subject);
397
398 /* keep original attachment if edit and no new attachment */
399 if (bedit && afile_name[0][0] == 0 && afile_name[1][0] == 0 && afile_name[2][0] == 0)
400 sprintf(message + strlen(message), "Attachment: %s", attachment);
401 else {
402 sprintf(message + strlen(message), "Attachment: %s", afile_name[0]);
403 if (afile_name[1][0])
404 sprintf(message + strlen(message), ",%s", afile_name[1]);
405 if (afile_name[2][0])
406 sprintf(message + strlen(message), ",%s", afile_name[2]);
407 }
408 sprintf(message + strlen(message), "\n");
409
410 sprintf(message + strlen(message), "Encoding: %s\n", encoding);
411 sprintf(message + strlen(message), "========================================\n");
412 strcat(message, text);
413
414 assert(strlen(message) < message_size); /* bomb out on array overrun. */
415
416 size = 0;
417 sprintf(start_str, "$Start$: %6d\n", size);
418 sprintf(end_str, "$End$: %6d\n\f", size);
419
421
422 if (tag != NULL && !bedit) {
423 sprintf(tag, "%02d%02d%02d.%d", tms.tm_year % 100, tms.tm_mon + 1, tms.tm_mday, (int) TELL(fh));
424 }
425
426 /* size has to fit in 6 digits */
427 assert(size < 999999);
428
429 sprintf(start_str, "$Start$: %6d\n", size);
430 sprintf(end_str, "$End$: %6d\n\f", size);
431
435
436 free(message);
437 message = NULL;
438 message_size = 0;
439
440 if (bedit) {
441 if (tail_size > 0) {
442 xwrite(file_name, fh, buffer, tail_size);
443 M_FREE(buffer);
444 }
445
446 /* truncate file here */
447#ifdef OS_WINNT
448 chsize(fh, TELL(fh));
449#else
451#endif
452 }
453
454 close(fh);
455
456 /* if reply, mark original message */
457 if (reply_to[0] && !bedit) {
458 strcpy(last, reply_to);
459 do {
460 char filename[256];
461 status = el_search_message(last, &fh, FALSE, filename, sizeof(filename));
462 if (status == EL_SUCCESS) {
463 /* position to next thread location */
464 lseek(fh, 72, SEEK_CUR);
465 char str[256];
466 memset(str, 0, sizeof(str));
467 xread(filename, fh, str, 16);
468 lseek(fh, -16, SEEK_CUR);
469
470 /* if no reply yet, set it */
471 if (atoi(str) == 0) {
472 sprintf(str, "%16s", tag);
473 xwrite(filename, fh, str, 16);
474 close(fh);
475 break;
476 } else {
477 /* if reply set, find last one in chain */
478 strcpy(last, strtok(str, " "));
479 close(fh);
480 }
481 } else
482 /* stop on error */
483 break;
484
485 } while (TRUE);
486 }
487
488 /* release elog semaphore */
489 ss_semaphore_release(semaphore);
490 }
491#endif /* LOCAL_ROUTINES */
492
493 return EL_SUCCESS;
494}
#define SUCCESS
Definition mcstd.h:54
#define TID_INT
Definition midas.h:338
#define RPC_EL_SUBMIT
Definition mrpc.h:111
bool rpc_is_remote(void)
Definition midas.cxx:12761
INT rpc_call(DWORD routine_id,...)
Definition midas.cxx:13663
INT run_number[2]
Definition mana.cxx:246
DWORD n[4]
Definition mana.cxx:247
DWORD BOOL
Definition midas.h:105
Here is the call graph for this function:
Here is the caller graph for this function:

◆ xread()

static int xread ( const char filename,
int  fd,
void data,
int  size 
)
static

Definition at line 76 of file elog.cxx.

77{
78 int rd = read(fd, data, size);
79 if (rd == 0) {
80 // end of file
81 } else if (rd < 0) {
82 cm_msg(MERROR, "xread", "cannot read from \'%s\', read(%d) returned %d, errno %d (%s)", filename, size, rd, errno, strerror(errno));
83 } else if (rd != size) {
84 cm_msg(MERROR, "xread", "truncated read from \'%s\', read(%d) returned %d", filename, size, rd);
85 }
86 return rd;
87}
void * data
Definition mana.cxx:268
Here is the call graph for this function:
Here is the caller graph for this function:

◆ xtruncate()

static void xtruncate ( const char filename,
int  fd 
)
static

Definition at line 89 of file elog.cxx.

90{
91 int tr = ftruncate(fd, TELL(fd));
92 if (tr != 0) {
93 cm_msg(MERROR, "xtruncate", "cannot truncate \'%s\', ftruncate() returned %d, errno %d (%s)", filename, tr, errno, strerror(errno));
94 }
95}
Here is the call graph for this function:
Here is the caller graph for this function:

◆ xwrite()

static void xwrite ( const char filename,
int  fd,
const void data,
int  size 
)
static

Definition at line 68 of file elog.cxx.

69{
70 int wr = write(fd, data, size);
71 if (wr != size) {
72 cm_msg(MERROR, "xwrite", "cannot write to \'%s\', write(%d) returned %d, errno %d (%s)", filename, size, wr, errno, strerror(errno));
73 }
74}
#define write(n, a, f, d)
Here is the call graph for this function:
Here is the caller graph for this function: