Coverage Report

Created: 2025-07-11 06:59

/src/dovecot/src/lib/hostpid.c
Line
Count
Source (jump to first uncovered line)
1
/* Copyright (c) 2002-2018 Dovecot authors, see the included COPYING file */
2
3
#include "lib.h"
4
#include "hostpid.h"
5
6
#include <unistd.h>
7
#include <netdb.h>
8
9
1
#define HOSTNAME_DISALLOWED_CHARS "/\r\n\t"
10
11
const char *my_hostname = NULL;
12
const char *my_pid = NULL;
13
14
static char *my_hostname_dup = NULL;
15
static char *my_domain = NULL;
16
17
void hostpid_init(void)
18
1
{
19
1
  static char pid[MAX_INT_STRLEN];
20
1
  char hostname[256];
21
1
  const char *value;
22
23
  /* allow calling hostpid_init() multiple times to reset hostname */
24
1
  i_free_and_null(my_hostname_dup);
25
1
  i_free_and_null(my_domain);
26
27
1
  value = getenv(MY_HOSTNAME_ENV);
28
1
  if (value == NULL) {
29
1
    if (gethostname(hostname, sizeof(hostname)-1) < 0)
30
0
      i_fatal("gethostname() failed: %m");
31
1
    hostname[sizeof(hostname)-1] = '\0';
32
1
    value = hostname;
33
1
  }
34
35
1
  if (value[0] == '\0' ||
36
1
      strcspn(value, HOSTNAME_DISALLOWED_CHARS) != strlen(value))
37
0
    i_fatal("Invalid system hostname: '%s'", value);
38
1
  my_hostname_dup = i_strdup(value);
39
1
  my_hostname = my_hostname_dup;
40
41
1
  i_snprintf(pid, sizeof(pid), "%lld", (long long)getpid());
42
1
  my_pid = pid;
43
1
}
44
45
void hostpid_deinit(void)
46
0
{
47
0
  i_free(my_hostname_dup);
48
0
  i_free(my_domain);
49
0
}
50
51
const char *my_hostdomain(void)
52
5.86k
{
53
5.86k
  const char *name;
54
5.86k
  const struct addrinfo hints = {
55
5.86k
    .ai_family = AF_UNSPEC,
56
5.86k
    .ai_socktype = SOCK_STREAM,
57
5.86k
    .ai_flags = AI_CANONNAME,
58
5.86k
  };
59
5.86k
  struct addrinfo *res;
60
61
5.86k
  if (my_domain != NULL)
62
5.86k
    return my_domain;
63
64
1
  name = getenv(MY_HOSTDOMAIN_ENV);
65
1
  if (name != NULL) {
66
0
    my_domain = i_strdup(name);
67
0
    return my_domain;
68
0
  }
69
70
1
  if (getaddrinfo(my_hostname, NULL, &hints, &res) == 0) {
71
1
    my_domain = i_strdup(res->ai_canonname);
72
1
    freeaddrinfo(res);
73
1
    return my_domain;
74
1
  }
75
76
  /* failed, use just the hostname */
77
0
  my_domain = i_strdup(my_hostname);
78
0
  return my_domain;
79
1
}