1 | |
---|
2 | /* |
---|
3 | * annosbr.c -- prepend annotation to messages |
---|
4 | * |
---|
5 | * $Id: annosbr.c,v 1.1.1.1 1999-02-07 18:14:12 danw Exp $ |
---|
6 | */ |
---|
7 | |
---|
8 | #include <h/mh.h> |
---|
9 | #include <zotnet/tws/tws.h> |
---|
10 | #include <fcntl.h> |
---|
11 | #include <errno.h> |
---|
12 | |
---|
13 | extern int errno; |
---|
14 | |
---|
15 | /* |
---|
16 | * static prototypes |
---|
17 | */ |
---|
18 | static int annosbr (int, char *, char *, char *, int, int); |
---|
19 | |
---|
20 | |
---|
21 | int |
---|
22 | annotate (char *file, char *comp, char *text, int inplace, int datesw) |
---|
23 | { |
---|
24 | int i, fd; |
---|
25 | |
---|
26 | /* open and lock the file to be annotated */ |
---|
27 | if ((fd = lkopen (file, O_RDWR, 0)) == NOTOK) { |
---|
28 | switch (errno) { |
---|
29 | case ENOENT: |
---|
30 | break; |
---|
31 | |
---|
32 | default: |
---|
33 | admonish (file, "unable to lock and open"); |
---|
34 | break; |
---|
35 | } |
---|
36 | return 1; |
---|
37 | } |
---|
38 | |
---|
39 | i = annosbr (fd, file, comp, text, inplace, datesw); |
---|
40 | lkclose (fd, file); |
---|
41 | return i; |
---|
42 | } |
---|
43 | |
---|
44 | |
---|
45 | static int |
---|
46 | annosbr (int fd, char *file, char *comp, char *text, int inplace, int datesw) |
---|
47 | { |
---|
48 | int mode, tmpfd; |
---|
49 | char *cp, *sp; |
---|
50 | char buffer[BUFSIZ], tmpfil[BUFSIZ]; |
---|
51 | struct stat st; |
---|
52 | FILE *tmp; |
---|
53 | |
---|
54 | mode = fstat (fd, &st) != NOTOK ? (st.st_mode & 0777) : m_gmprot (); |
---|
55 | |
---|
56 | strncpy (tmpfil, m_scratch (file, "annotate"), sizeof(tmpfil)); |
---|
57 | |
---|
58 | if ((tmp = fopen (tmpfil, "w")) == NULL) { |
---|
59 | admonish (tmpfil, "unable to create"); |
---|
60 | return 1; |
---|
61 | } |
---|
62 | chmod (tmpfil, mode); |
---|
63 | |
---|
64 | if (datesw) |
---|
65 | fprintf (tmp, "%s: %s\n", comp, dtimenow (0)); |
---|
66 | if ((cp = text)) { |
---|
67 | do { |
---|
68 | while (*cp == ' ' || *cp == '\t') |
---|
69 | cp++; |
---|
70 | sp = cp; |
---|
71 | while (*cp && *cp++ != '\n') |
---|
72 | continue; |
---|
73 | if (cp - sp) |
---|
74 | fprintf (tmp, "%s: %*.*s", comp, cp - sp, cp - sp, sp); |
---|
75 | } while (*cp); |
---|
76 | if (cp[-1] != '\n' && cp != text) |
---|
77 | putc ('\n', tmp); |
---|
78 | } |
---|
79 | fflush (tmp); |
---|
80 | cpydata (fd, fileno (tmp), file, tmpfil); |
---|
81 | fclose (tmp); |
---|
82 | |
---|
83 | if (inplace) { |
---|
84 | if ((tmpfd = open (tmpfil, O_RDONLY)) == NOTOK) |
---|
85 | adios (tmpfil, "unable to open for re-reading"); |
---|
86 | lseek (fd, (off_t) 0, SEEK_SET); |
---|
87 | cpydata (tmpfd, fd, tmpfil, file); |
---|
88 | close (tmpfd); |
---|
89 | unlink (tmpfil); |
---|
90 | } else { |
---|
91 | strncpy (buffer, m_backup (file), sizeof(buffer)); |
---|
92 | if (rename (file, buffer) == NOTOK) { |
---|
93 | switch (errno) { |
---|
94 | case ENOENT: /* unlinked early - no annotations */ |
---|
95 | unlink (tmpfil); |
---|
96 | break; |
---|
97 | |
---|
98 | default: |
---|
99 | admonish (buffer, "unable to rename %s to", file); |
---|
100 | break; |
---|
101 | } |
---|
102 | return 1; |
---|
103 | } |
---|
104 | if (rename (tmpfil, file) == NOTOK) { |
---|
105 | admonish (file, "unable to rename %s to", tmpfil); |
---|
106 | return 1; |
---|
107 | } |
---|
108 | } |
---|
109 | |
---|
110 | return 0; |
---|
111 | } |
---|