assert-pre-internal.h: add BT_ASSERT_PRE_VALID_INDEX()
[babeltrace.git] / lib / ctf-ir / stream.c
CommitLineData
273b65be
JG
1/*
2 * stream.c
3 *
d2dc44b6 4 * Babeltrace CTF IR - Stream
273b65be 5 *
de9dd397 6 * Copyright 2013, 2014 Jérémie Galarneau <jeremie.galarneau@efficios.com>
273b65be
JG
7 *
8 * Author: Jérémie Galarneau <jeremie.galarneau@efficios.com>
9 *
10 * Permission is hereby granted, free of charge, to any person obtaining a copy
11 * of this software and associated documentation files (the "Software"), to deal
12 * in the Software without restriction, including without limitation the rights
13 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
14 * copies of the Software, and to permit persons to whom the Software is
15 * furnished to do so, subject to the following conditions:
16 *
17 * The above copyright notice and this permission notice shall be included in
18 * all copies or substantial portions of the Software.
19 *
20 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
21 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
22 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
23 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
24 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
25 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
26 * SOFTWARE.
27 */
28
19abc2c6
PP
29#define BT_LOG_TAG "STREAM"
30#include <babeltrace/lib-logging-internal.h>
31
44ea72c5 32#include <babeltrace/assert-pre-internal.h>
8deee039
PP
33#include <babeltrace/ctf-ir/stream.h>
34#include <babeltrace/ctf-ir/stream-internal.h>
35#include <babeltrace/ctf-ir/stream-class.h>
36#include <babeltrace/ctf-ir/stream-class-internal.h>
37#include <babeltrace/ctf-ir/trace.h>
38#include <babeltrace/ctf-ir/trace-internal.h>
a6918753 39#include <babeltrace/ctf-ir/packet-internal.h>
8deee039
PP
40#include <babeltrace/ref.h>
41#include <babeltrace/compiler-internal.h>
42#include <babeltrace/align-internal.h>
43#include <babeltrace/assert-internal.h>
44#include <inttypes.h>
45#include <unistd.h>
12c8a1a3 46
18acc6f8
PP
47static inline
48void bt_stream_finalize(struct bt_stream *stream)
263a7df5 49{
18acc6f8
PP
50 BT_LOGD("Finalizing stream object: addr=%p, name=\"%s\"",
51 stream, bt_stream_get_name(stream));
263a7df5 52
8deee039
PP
53 if (stream->name) {
54 g_string_free(stream->name, TRUE);
b3376dd9 55 }
263a7df5
JG
56}
57
c9af50d1 58static
8deee039 59void bt_stream_destroy(struct bt_object *obj)
c9af50d1 60{
8deee039 61 struct bt_stream *stream = (void *) obj;
c9af50d1 62
8deee039
PP
63 BT_LOGD("Destroying stream object: addr=%p, name=\"%s\"",
64 stream, bt_stream_get_name(stream));
a6918753 65 bt_object_pool_finalize(&stream->packet_pool);
18acc6f8 66 bt_stream_finalize((void *) obj);
8deee039 67 g_free(stream);
c9af50d1
JG
68}
69
18acc6f8
PP
70static inline
71int bt_stream_initialize(
72 struct bt_stream *stream,
73 struct bt_stream_class *stream_class, const char *name,
8deee039 74 uint64_t id, bt_object_release_func release_func)
273b65be
JG
75{
76 int ret = 0;
18acc6f8 77 struct bt_trace *trace = NULL;
98edd02c 78
1d7bf349 79 bt_object_init_shared_with_parent(&stream->base, release_func);
273b65be 80
8deee039
PP
81 if (!stream_class) {
82 BT_LOGW_STR("Invalid parameter: stream class is NULL.");
83 goto error;
b3376dd9 84 }
12c8a1a3 85
18acc6f8 86 BT_LOGD("Initializing stream object: stream-class-addr=%p, "
8deee039
PP
87 "stream-class-name=\"%s\", stream-name=\"%s\", "
88 "stream-id=%" PRIu64,
18acc6f8 89 stream_class, bt_stream_class_get_name(stream_class),
8deee039 90 name, id);
18acc6f8 91 trace = bt_stream_class_borrow_trace(stream_class);
8deee039
PP
92 if (!trace) {
93 BT_LOGW("Invalid parameter: cannot create stream from a stream class which is not part of trace: "
94 "stream-class-addr=%p, stream-class-name=\"%s\", "
95 "stream-name=\"%s\"",
96 stream_class,
18acc6f8 97 bt_stream_class_get_name(stream_class), name);
8deee039 98 goto error;
12c8a1a3
JG
99 }
100
8deee039
PP
101 if (id != -1ULL) {
102 /*
103 * Validate that the given ID is unique amongst all the
104 * existing trace's streams created from the same stream
105 * class.
106 */
107 size_t i;
19abc2c6 108
8deee039 109 for (i = 0; i < trace->streams->len; i++) {
18acc6f8 110 struct bt_stream *trace_stream =
8deee039 111 g_ptr_array_index(trace->streams, i);
273b65be 112
8deee039
PP
113 if (trace_stream->stream_class != (void *) stream_class) {
114 continue;
93872409 115 }
273b65be 116
8deee039
PP
117 if (trace_stream->id == id) {
118 BT_LOGW_STR("Invalid parameter: another stream in the same trace already has this ID.");
119 goto error;
8bfa3f9c
JG
120 }
121 }
daaa1851
JD
122 }
123
daaa1851 124 /*
8deee039
PP
125 * Acquire reference to parent since stream will become publicly
126 * reachable; it needs its parent to remain valid.
daaa1851 127 */
1d7bf349 128 bt_object_set_parent(&stream->base, &trace->base);
8deee039
PP
129 stream->stream_class = stream_class;
130 stream->id = (int64_t) id;
273b65be 131
8deee039
PP
132 if (name) {
133 stream->name = g_string_new(name);
134 if (!stream->name) {
135 BT_LOGE_STR("Failed to allocate a GString.");
136 goto error;
98edd02c 137 }
273b65be
JG
138 }
139
18acc6f8 140 BT_LOGD("Set stream's trace parent: trace-addr=%p", trace);
daaa1851 141
8deee039 142 /* Add this stream to the trace's streams */
18acc6f8 143 BT_LOGD("Created stream object: addr=%p", stream);
8deee039 144 goto end;
cd7d8fb7 145
8deee039
PP
146error:
147 ret = -1;
058bbc58 148
8deee039 149end:
273b65be
JG
150 return ret;
151}
152
a6918753
PP
153static
154void bt_stream_free_packet(struct bt_packet *packet, struct bt_stream *stream)
155{
156 bt_packet_destroy(packet);
157}
158
273b65be 159static
8deee039
PP
160struct bt_stream *bt_stream_create_with_id_no_check(
161 struct bt_stream_class *stream_class,
162 const char *name, uint64_t id)
273b65be 163{
8deee039
PP
164 int ret;
165 struct bt_stream *stream = NULL;
166 struct bt_trace *trace = NULL;
3230ee6b 167
8deee039
PP
168 BT_LOGD("Creating stream object: stream-class-addr=%p, "
169 "stream-class-name=\"%s\", stream-name=\"%s\", "
170 "stream-id=%" PRIu64,
171 stream_class, bt_stream_class_get_name(stream_class),
172 name, id);
3230ee6b 173
18acc6f8 174 trace = bt_stream_class_borrow_trace(stream_class);
8deee039
PP
175 if (!trace) {
176 BT_LOGW("Invalid parameter: cannot create stream from a stream class which is not part of trace: "
177 "stream-class-addr=%p, stream-class-name=\"%s\", "
178 "stream-name=\"%s\"",
179 stream_class, bt_stream_class_get_name(stream_class),
180 name);
181 goto error;
3230ee6b
PP
182 }
183
8deee039 184 if (bt_trace_is_static(trace)) {
0686ef94 185 /*
8deee039
PP
186 * A static trace has the property that all its stream
187 * classes, clock classes, and streams are definitive:
188 * no more can be added, and each object is also frozen.
0686ef94 189 */
8deee039
PP
190 BT_LOGW("Invalid parameter: cannot create stream from a stream class which is part of a static trace: "
191 "stream-class-addr=%p, stream-class-name=\"%s\", "
192 "stream-name=\"%s\", trace-addr=%p",
193 stream_class, bt_stream_class_get_name(stream_class),
194 name, trace);
195 goto error;
9f56e450 196 }
12c8a1a3 197
8deee039
PP
198 stream = g_new0(struct bt_stream, 1);
199 if (!stream) {
200 BT_LOGE_STR("Failed to allocate one stream.");
201 goto error;
12c8a1a3 202 }
b71d7298 203
18acc6f8
PP
204 ret = bt_stream_initialize(stream, stream_class, name,
205 id, bt_stream_destroy);
8deee039 206 if (ret) {
18acc6f8 207 /* bt_stream_initialize() logs errors */
8deee039 208 goto error;
b71d7298 209 }
41ac640a 210
a6918753
PP
211 ret = bt_object_pool_initialize(&stream->packet_pool,
212 (bt_object_pool_new_object_func) bt_packet_new,
213 (bt_object_pool_destroy_object_func) bt_stream_free_packet,
214 stream);
215 if (ret) {
216 BT_LOGE("Failed to initialize packet pool: ret=%d", ret);
217 goto error;
218 }
219
18acc6f8 220 g_ptr_array_add(trace->streams, stream);
8deee039
PP
221 BT_LOGD("Created stream object: addr=%p", stream);
222 goto end;
3230ee6b 223
8deee039
PP
224error:
225 BT_PUT(stream);
226
227end:
228 return stream;
273b65be
JG
229}
230
8deee039
PP
231struct bt_stream *bt_stream_create(struct bt_stream_class *stream_class,
232 const char *name, uint64_t id_param)
273b65be 233{
8deee039
PP
234 struct bt_stream *stream = NULL;
235 int64_t id = (int64_t) id_param;
273b65be 236
8deee039
PP
237 if (!stream_class) {
238 BT_LOGW_STR("Invalid parameter: stream class is NULL.");
12c8a1a3
JG
239 goto end;
240 }
241
8deee039
PP
242 if (id < 0) {
243 BT_LOGW("Invalid parameter: invalid stream's ID: "
244 "name=\"%s\", id=%" PRIu64,
245 name, id_param);
12c8a1a3
JG
246 goto end;
247 }
248
8deee039
PP
249 stream = bt_stream_create_with_id_no_check(stream_class,
250 name, id_param);
d7b1ea66 251
273b65be 252end:
8deee039 253 return stream;
273b65be 254}
b71d7298 255
5fe68922 256struct bt_stream_class *bt_stream_borrow_class(struct bt_stream *stream)
af9296f3 257{
18acc6f8
PP
258 BT_ASSERT(stream);
259 return stream->stream_class;
af9296f3
JG
260}
261
839d52a5 262const char *bt_stream_get_name(struct bt_stream *stream)
b71d7298 263{
18acc6f8
PP
264 BT_ASSERT_PRE_NON_NULL(stream, "Stream");
265 return stream->name ? stream->name->str : NULL;
b71d7298 266}
98a4cbef 267
8deee039 268int64_t bt_stream_get_id(struct bt_stream *stream)
98a4cbef 269{
18acc6f8
PP
270 int64_t ret;
271
272 BT_ASSERT_PRE_NON_NULL(stream, "Stream");
273 ret = stream->id;
274 if (ret < 0) {
275 BT_LOGV("Stream's ID is not set: addr=%p, name=\"%s\"",
276 stream, bt_stream_get_name(stream));
277 }
278
279 return ret;
98a4cbef 280}
This page took 0.069973 seconds and 4 git commands to generate.