/[gnats]/gnats/gnats/misc.c
ViewVC logotype

Diff of /gnats/gnats/misc.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.38.2.1 by chewie, Wed Nov 10 17:24:43 2004 UTC revision 1.38.2.2 by chewie, Thu Aug 25 03:26:36 2005 UTC
# Line 78  log_msg (int severity, int num_arg, va_d Line 78  log_msg (int severity, int num_arg, va_d
78                
79        message = va_arg (args, char *);        message = va_arg (args, char *);
80        /* The following is incredibly stupid and broken, but I don't know how to        /* The following is incredibly stupid and broken, but I don't know how to
81           do it better in C. */           do it better in C. */
82        if (num_arg > 0)        if (num_arg > 0)
83          {          {
84            char *message2 = va_arg (args, char *);            char *message2 = va_arg (args, char *);
85            asprintf (&buf, "%s: %s %s\n", program_name, message, message2);            asprintf (&buf, "%s: %s %s\n", program_name, message, message2);
86          }          }
87        else        else
88          {          {
89            asprintf (&buf, "%s: %s\n", program_name, message);            asprintf (&buf, "%s: %s\n", program_name, message);
90          }          }
91    
92        switch (log_method)        switch (log_method)
93          {          {
94  #ifdef HAVE_SYSLOG_H  #ifdef HAVE_SYSLOG_H
95          case SYSLOG:          case SYSLOG:
96            syslog (severity, "%s", buf);            syslog (severity, "%s", buf);
97            break;            break;
98  #endif  #endif
99          case MAIL:          case MAIL:
100            /* This is currently not used, because it could send a lot of mails            /* This is currently not used, because it could send a lot of mails
101               to someone. */               to someone. */
102            program_error (__FILE__, __LINE__);            program_error (__FILE__, __LINE__);
103            break;            break;
104          case LOGFILE:          case LOGFILE:
105            if (gnats_logfile != (FILE *)NULL)            if (gnats_logfile != (FILE *)NULL)
106              {              {
107                fprintf (gnats_logfile, "%s", buf);                fprintf (gnats_logfile, "%s", buf);
108                break;                break;
109              }              }
110            /* No log file, log to stderr. */            /* No log file, log to stderr. */
111          case STDERR:          case STDERR:
112            fprintf (stderr, "%s", buf);            fprintf (stderr, "%s", buf);
113            break;            break;
114          case NOLOG:          case NOLOG:
115            /* Do nothing. */            /* Do nothing. */
116            break;            break;
117          default:          default:
118            program_error (__FILE__, __LINE__);            program_error (__FILE__, __LINE__);
119          }          }
120    
121        free (buf);        free (buf);
122      }      }
# Line 136  init_logging (const char *logfile) Line 136  init_logging (const char *logfile)
136        /* A log file explicitly requested.  Let's try to open it. */        /* A log file explicitly requested.  Let's try to open it. */
137        gnats_logfile = fopen (logfile, "at");        gnats_logfile = fopen (logfile, "at");
138        if (gnats_logfile != NULL)        if (gnats_logfile != NULL)
139          {          {
140            log_method = LOGFILE;            log_method = LOGFILE;
141            return;            return;
142          }          }
143      }      }
144        
145    if (isatty (fileno (stderr)))    if (isatty (fileno (stderr)))
# Line 186  open_mail_file (const DatabaseInfo datab Line 186  open_mail_file (const DatabaseInfo datab
186        free (mailAgentPath);        free (mailAgentPath);
187    
188        if (debugMode (database))        if (debugMode (database))
189          {          {
190            fprintf (fp, "From: %s (GNATS Management)\n",            fprintf (fp, "From: %s (GNATS Management)\n",
191                     gnatsAdminMailAddr (database));                     gnatsAdminMailAddr (database));
192            fprintf (fp, "To: %s\n", gnatsAdminMailAddr (database));            fprintf (fp, "To: %s\n", gnatsAdminMailAddr (database));
193            fprintf (fp, "Subject: mail output from %s\n", program_name);            fprintf (fp, "Subject: mail output from %s\n", program_name);
194            fprintf (fp, "\n\n");            fprintf (fp, "\n\n");
195          }          }
196      }      }
197    
198    return fp;    return fp;
# Line 228  program_error (const char *filename, int Line 228  program_error (const char *filename, int
228     If any error occurs, NULL is returned and `err' is set appropriately. */     If any error occurs, NULL is returned and `err' is set appropriately. */
229  DatabaseInfo  DatabaseInfo
230  init_gnats (const char *program_name, const char *database_name,  init_gnats (const char *program_name, const char *database_name,
231              ErrorDesc *err)              ErrorDesc *err)
232  {  {
233    init_logging (NULL);    init_logging (NULL);
234    re_set_syntax ((RE_SYNTAX_POSIX_EXTENDED | RE_BK_PLUS_QM) & ~RE_DOT_NEWLINE);    re_set_syntax ((RE_SYNTAX_POSIX_EXTENDED | RE_BK_PLUS_QM) & ~RE_DOT_NEWLINE);
# Line 303  quote_string (const char *string) Line 303  quote_string (const char *string)
303    for (p = string; *p != '\0'; p++)    for (p = string; *p != '\0'; p++)
304      {      {
305        if (*p == '"')        if (*p == '"')
306          {          {
307            len++;            len++;
308          }          }
309      }      }
310    
311    res = xmalloc (len + 1);    res = xmalloc (len + 1);
# Line 318  quote_string (const char *string) Line 318  quote_string (const char *string)
318    for (p = string; *p != '\0'; p++)    for (p = string; *p != '\0'; p++)
319      {      {
320        if (*p == '"')        if (*p == '"')
321          {          {
322            *(rp++) = '\\';            *(rp++) = '\\';
323          }          }
324        *(rp++) = *p;        *(rp++) = *p;
325      }      }
326    return res;    return res;
# Line 347  read_line (FILE *input, size_t *max_len_ Line 347  read_line (FILE *input, size_t *max_len_
347    char *res = xmalloc (max_len>0 ? max_len+1 : default_len);    char *res = xmalloc (max_len>0 ? max_len+1 : default_len);
348    
349    while (fgets (res+len, (max_len>0 ? max_len : default_len), input)    while (fgets (res+len, (max_len>0 ? max_len : default_len), input)
350           != NULL)           != NULL)
351      {      {
352        size_t slen = strlen (res + len);        size_t slen = strlen (res + len);
353        len += slen;        len += slen;
354        if (res[len - 1] == '\n')        if (res[len - 1] == '\n')
355          break;          break;
356                
357        if (max_len > 0)        if (max_len > 0)
358          {          {
359            max_len -= slen;            max_len -= slen;
360            if (max_len == 0)            if (max_len == 0)
361              break;              break;
362          }          }
363        else        else
364          {          {
365            res = xrealloc (res, len + default_len);            res = xrealloc (res, len + default_len);
366          }          }
367      }      }
368        
369    if (len == 0)    if (len == 0)
# Line 409  xstrndup (const char *str, size_t len) Line 409  xstrndup (const char *str, size_t len)
409     (sdcsvax!rmr or rmr@@uscd).  If you want it, it's yours.     (sdcsvax!rmr or rmr@@uscd).  If you want it, it's yours.
410    
411     Severely hacked over by John Gilmore to make a 4.2BSD compatible     Severely hacked over by John Gilmore to make a 4.2BSD compatible
412     subroutine.  11Mar86; hoptoad!gnu     subroutine.  11Mar86; hoptoad!gnu
413    
414     Modified by rmtodd@@uokmax 6-28-87 -- when making an already existing dir,     Modified by rmtodd@@uokmax 6-28-87 -- when making an already existing dir,
415     subroutine didn't return EEXIST.  It does now.  */     subroutine didn't return EEXIST.  It does now.  */
# Line 424  mkdir (dpath, dmode) Line 424  mkdir (dpath, dmode)
424    
425    if (stat (dpath, &statbuf) == 0)    if (stat (dpath, &statbuf) == 0)
426      {      {
427        errno = EEXIST;           /* stat worked, so it already exists.  */        errno = EEXIST;           /* stat worked, so it already exists.  */
428        return -1;        return -1;
429      }      }
430    
# Line 435  mkdir (dpath, dmode) Line 435  mkdir (dpath, dmode)
435    cpid = fork ();    cpid = fork ();
436    switch (cpid)    switch (cpid)
437      {      {
438      case -1:                    /* Cannot fork.  */      case -1:                    /* Cannot fork.  */
439        return -1;                /* errno is set already.  */        return -1;                /* errno is set already.  */
440    
441      case 0:                     /* Child process.  */      case 0:                     /* Child process.  */
442        /* Cheap hack to set mode of new directory.  Since this child        /* Cheap hack to set mode of new directory.  Since this child
443           process is going away anyway, we zap its umask.           process is going away anyway, we zap its umask.
444           This won't suffice to set SUID, SGID, etc. on this           This won't suffice to set SUID, SGID, etc. on this
445           directory, so the parent process calls chmod afterward.  */           directory, so the parent process calls chmod afterward.  */
446        status = umask (0);       /* Get current umask.  */        status = umask (0);       /* Get current umask.  */
447        umask (status | (0777 & ~dmode)); /* Set for mkdir.  */        umask (status | (0777 & ~dmode)); /* Set for mkdir.  */
448        execl ("/bin/mkdir", "mkdir", dpath, (char *) 0);        execl ("/bin/mkdir", "mkdir", dpath, (char *) 0);
449        _exit (1);        _exit (1);
450    
451      default:                    /* Parent process.  */      default:                    /* Parent process.  */
452        while (wait (&status) != cpid) /* Wait for kid to finish.  */        while (wait (&status) != cpid) /* Wait for kid to finish.  */
453          /* Do nothing.  */ ;          /* Do nothing.  */ ;
454    
455        if (status & 0xFFFF)        if (status & 0xFFFF)
456          {          {
457            errno = EIO;          /* /bin/mkdir failed.  */            errno = EIO;          /* /bin/mkdir failed.  */
458            return -1;            return -1;
459          }          }
460        return chmod (dpath, dmode);        return chmod (dpath, dmode);
461      }      }
462  }  }
# Line 481  int open_temporary_file (char *template, Line 481  int open_temporary_file (char *template,
481      for (i = 0; i < NUMBER_OF_TRIALS && fd < 0; i++)      for (i = 0; i < NUMBER_OF_TRIALS && fd < 0; i++)
482        {          {  
483  #ifdef HAVE_MKTEMP  #ifdef HAVE_MKTEMP
484          mktemp (template);          mktemp (template);
485  #else  #else
486          mkstemps (template, 0);          mkstemps (template, 0);
487  #endif  #endif
488          fd = open (template, O_RDWR | O_CREAT | O_EXCL, mode);          fd = open (template, O_RDWR | O_CREAT | O_EXCL, mode);
489        }        }
490    }    }
491  #endif  #endif
# Line 535  minutes_gmt_offset (const struct tm *loc Line 535  minutes_gmt_offset (const struct tm *loc
535    
536    /* mktime() not portably reliable; calculate minutes offset ourselves */    /* mktime() not portably reliable; calculate minutes offset ourselves */
537    offset = ((local.tm_hour - gmt.tm_hour) * 60 +    offset = ((local.tm_hour - gmt.tm_hour) * 60 +
538              (local.tm_min  - gmt.tm_min));              (local.tm_min  - gmt.tm_min));
539    
540    /* Adjust backwards/forwards if the day is different */    /* Adjust backwards/forwards if the day is different */
541    if      (local.tm_year < gmt.tm_year) offset -= MINUTES_PER_DAY;    if      (local.tm_year < gmt.tm_year) offset -= MINUTES_PER_DAY;
# Line 550  minutes_gmt_offset (const struct tm *loc Line 550  minutes_gmt_offset (const struct tm *loc
550     by libc. */     by libc. */
551  size_t  size_t
552  gnats_strftime (char *s, size_t size, const char *template,  gnats_strftime (char *s, size_t size, const char *template,
553                  const struct tm *brokentime)                  const struct tm *brokentime)
554  {  {
555    static short have_strftime_with_z = -1;      static short have_strftime_with_z = -1;  
556    if (have_strftime_with_z < 0)    if (have_strftime_with_z < 0)
# Line 563  gnats_strftime (char *s, size_t size, co Line 563  gnats_strftime (char *s, size_t size, co
563        ** return from get_curr_date() cannot be parsed by get_date().        ** return from get_curr_date() cannot be parsed by get_date().
564        */        */
565        have_strftime_with_z = ((int)buf[0] == '+' || (int)buf[0] == '-') &&        have_strftime_with_z = ((int)buf[0] == '+' || (int)buf[0] == '-') &&
566                isdigit ((int)(buf[1]));                isdigit ((int)(buf[1]));
567      }      }
568        
569    if (have_strftime_with_z)    if (have_strftime_with_z)
# Line 585  gnats_strftime (char *s, size_t size, co Line 585  gnats_strftime (char *s, size_t size, co
585         * As we are going to replace each "%z" by "+hhmm" (sign, hours,         * As we are going to replace each "%z" by "+hhmm" (sign, hours,
586         * minutes), this is 3 extra chars for each %z. */         * minutes), this is 3 extra chars for each %z. */
587        while (*in)        while (*in)
588          {          {
589            if (*in == '%' && *(in+1) == 'z')            if (*in == '%' && *(in+1) == 'z')
590              {              {
591                in += 2;                in += 2;
592                padding += 3;  /* 3 extra chars for each %z */                padding += 3;  /* 3 extra chars for each %z */
593              }              }
594            else            else
595              {              {
596                in++;                in++;
597              }              }
598          }          }
599    
600        /* Now allocate enough space. */        /* Now allocate enough space. */
601        fixed_template = (char*)xmalloc (strlen(template)+padding+1);        fixed_template = (char*)xmalloc (strlen(template)+padding+1);
# Line 603  gnats_strftime (char *s, size_t size, co Line 603  gnats_strftime (char *s, size_t size, co
603        out = fixed_template;        out = fixed_template;
604            
605        while (*in != '\0')        while (*in != '\0')
606          {          {
607            char c = *in++;            char c = *in++;
608            if (c != '%')            if (c != '%')
609              {              {
610                *out++ = c;                *out++ = c;
611              }              }
612            else if (*in != 'z')            else if (*in != 'z')
613              {              {
614                *out++ = c;  /* the '%' */                *out++ = c;  /* the '%' */
615                *out++ = *in++;                *out++ = *in++;
616              }              }
617            else            else
618              {              {
619                int offset = minutes_gmt_offset (brokentime);                int offset = minutes_gmt_offset (brokentime);
620                char offset_buf[6];                char offset_buf[6];
621                char sign = '+';                char sign = '+';
622                unsigned int i, hours, minutes;                unsigned int i, hours, minutes;
623    
624                if (offset < 0)                if (offset < 0)
625                  {                  {
626                    sign = '-';                    sign = '-';
627                    offset = -offset;                    offset = -offset;
628                  }                  }
629                hours = offset / 60;                hours = offset / 60;
630                minutes = offset % 60;                minutes = offset % 60;
631                sprintf (offset_buf, "%c%02d%02d", sign, hours, minutes);                sprintf (offset_buf, "%c%02d%02d", sign, hours, minutes);
632                for (i = 0; i < strlen (offset_buf); i++)                for (i = 0; i < strlen (offset_buf); i++)
633                  *out++ = offset_buf[i];                  *out++ = offset_buf[i];
634                in++; /* skip over 'z' */                in++; /* skip over 'z' */
635              }              }
636          }          }
637        *out = '\0';        *out = '\0';
638            
639        result = strftime (s, size, fixed_template, &btime);        result = strftime (s, size, fixed_template, &btime);
# Line 676  value_is_empty (const char *string) Line 676  value_is_empty (const char *string)
676      unsigned int i;      unsigned int i;
677      for (i = 0; i < strlen (string); i++)      for (i = 0; i < strlen (string); i++)
678        if (! isspace ((int)(unsigned char)(string[i])))        if (! isspace ((int)(unsigned char)(string[i])))
679          return FALSE;          return FALSE;
680      return TRUE;      return TRUE;
681    }    }
682  }  }
683    
684    #ifndef HAVE_UNSETENV
685    #define __environ       environ
686    extern char **environ;
687    
688    void
689    unsetenv (name)
690         const char *name;
691    {
692      const size_t len = strlen (name);
693      char **ep;
694    
695      for (ep = __environ; *ep; ++ep)
696        if (!strncmp (*ep, name, len) && (*ep)[len] == '=')
697          {
698            /* Found it.  Remove this pointer by moving later ones back.  */
699            char **dp = ep;
700            do
701              dp[0] = dp[1];
702            while (*dp++);
703            /* Continue the loop in case NAME appears again.  */
704          }
705    
706    }
707    #endif /* !HAVE_UNSETENV */

Legend:
Removed from v.1.38.2.1  
changed lines
  Added in v.1.38.2.2

savannah-hackers-public@gnu.org
ViewVC Help
Powered by ViewVC 1.1.26