Coverage Report

Created: 2025-10-10 06:06

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/mhd2/src/mhd2/response_destroy.c
Line
Count
Source
1
/* SPDX-License-Identifier: LGPL-2.1-or-later OR (GPL-2.0-or-later WITH eCos-exception-2.0) */
2
/*
3
  This file is part of GNU libmicrohttpd.
4
  Copyright (C) 2024 Evgeny Grin (Karlson2k)
5
6
  GNU libmicrohttpd is free software; you can redistribute it and/or
7
  modify it under the terms of the GNU Lesser General Public
8
  License as published by the Free Software Foundation; either
9
  version 2.1 of the License, or (at your option) any later version.
10
11
  GNU libmicrohttpd is distributed in the hope that it will be useful,
12
  but WITHOUT ANY WARRANTY; without even the implied warranty of
13
  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14
  Lesser General Public License for more details.
15
16
  Alternatively, you can redistribute GNU libmicrohttpd and/or
17
  modify it under the terms of the GNU General Public License as
18
  published by the Free Software Foundation; either version 2 of
19
  the License, or (at your option) any later version, together
20
  with the eCos exception, as follows:
21
22
    As a special exception, if other files instantiate templates or
23
    use macros or inline functions from this file, or you compile this
24
    file and link it with other works to produce a work based on this
25
    file, this file does not by itself cause the resulting work to be
26
    covered by the GNU General Public License. However the source code
27
    for this file must still be made available in accordance with
28
    section (3) of the GNU General Public License v2.
29
30
    This exception does not invalidate any other reasons why a work
31
    based on this file might be covered by the GNU General Public
32
    License.
33
34
  You should have received copies of the GNU Lesser General Public
35
  License and the GNU General Public License along with this library;
36
  if not, see <https://www.gnu.org/licenses/>.
37
*/
38
39
/**
40
 * @file src/mhd2/response_destroy.c
41
 * @brief  The declarations of internal functions for response deletion
42
 * @author Karlson2k (Evgeny Grin)
43
 */
44
45
#include "mhd_sys_options.h"
46
#include "response_destroy.h"
47
#include "mhd_response.h"
48
49
#include "mhd_assert.h"
50
#include "mhd_panic.h"
51
#include "mhd_atomic_counter.h"
52
53
#include "sys_malloc.h"
54
55
#include "mhd_public_api.h"
56
57
#include "response_add_header.h"
58
#include "response_funcs.h"
59
#include "response_from.h"
60
61
#ifdef MHD_SUPPORT_AUTH_DIGEST
62
#  include "response_auth_digest.h"
63
#endif
64
65
#define mhd_RESPONSE_DESTOYED "Attempt to use destroyed response, " \
66
        "re-use non-reusable response or wrong MHD_Response pointer"
67
68
/**
69
 * Perform full response de-initialisation, with cleaning-up / freeing
70
 * all content data and headers.
71
 * The response settings (if any) must be already freed.
72
 * @param r the response to free
73
 */
74
static MHD_FN_PAR_NONNULL_ (1) void
75
response_full_deinit (struct MHD_Response *restrict r)
76
4.76k
{
77
4.76k
#ifdef MHD_SUPPORT_AUTH_DIGEST
78
4.76k
  mhd_response_remove_auth_digest_headers (r);
79
4.76k
#endif
80
4.76k
  mhd_response_remove_all_headers (r);
81
4.76k
  if (NULL != r->special_resp.spec_hdr)
82
0
    free (r->special_resp.spec_hdr);
83
4.76k
  if (r->reuse.reusable)
84
380
    mhd_response_deinit_reusable (r);
85
4.76k
  mhd_response_deinit_content_data (r);
86
87
4.76k
  r->was_destroyed = true;
88
4.76k
  free (r);
89
4.76k
}
90
91
92
MHD_INTERNAL MHD_FN_PAR_NONNULL_ALL_ void
93
mhd_response_dec_use_count (struct MHD_Response *restrict r)
94
574
{
95
574
  mhd_assert (r->frozen);
96
574
  if (r->was_destroyed)
97
0
    MHD_PANIC (mhd_RESPONSE_DESTOYED);
98
99
574
  if (r->reuse.reusable)
100
0
  {
101
0
    if (1 != mhd_atomic_counter_get_dec (&(r->reuse.counter)))
102
0
      return; /* The response is still used somewhere */
103
0
  }
104
105
574
  response_full_deinit (r);
106
574
}
107
108
109
MHD_INTERNAL MHD_FN_PAR_NONNULL_ALL_ void
110
mhd_response_inc_use_count (struct MHD_Response *restrict r)
111
0
{
112
0
  mhd_assert (r->frozen);
113
0
  if (r->was_destroyed)
114
0
    MHD_PANIC (mhd_RESPONSE_DESTOYED);
115
116
0
  if (! r->reuse.reusable)
117
0
    return;
118
119
0
  mhd_atomic_counter_inc (&(r->reuse.counter));
120
0
}
121
122
123
MHD_EXTERN_
124
MHD_FN_PAR_NONNULL_ (1) void
125
MHD_response_destroy (struct MHD_Response *response)
126
4.76k
{
127
4.76k
  if (response->was_destroyed)
128
0
    MHD_PANIC (mhd_RESPONSE_DESTOYED);
129
130
4.76k
  if (! response->frozen)
131
4.19k
  {
132
    /* This response has been never used for actions */
133
4.19k
    mhd_assert (NULL != response->settings);
134
4.19k
    free (response->settings);
135
#ifndef NDEBUG
136
    /* Decrement counter to avoid triggering assert in deinit function */
137
    if (response->reuse.reusable)
138
      mhd_assert (1 == mhd_atomic_counter_get_dec (&(response->reuse.counter)));
139
#endif
140
4.19k
    response_full_deinit (response);
141
4.19k
    return;
142
4.19k
  }
143
144
574
  mhd_response_dec_use_count (response);
145
574
}