#define _LGPL_SOURCE
#include <urcu-bp.h>
#include <urcu/rculist.h>
+#include <urcu/hlist.h>
#include <ust/core.h>
#include <ust/marker.h>
+#include <ust/tracepoint.h>
#include "usterr.h"
#include "channels.h"
__thread long ust_reg_stack[500];
volatile __thread long *ust_reg_stack_ptr = (long *) 0;
-extern struct marker __start___markers[] __attribute__((visibility("hidden")));
-extern struct marker __stop___markers[] __attribute__((visibility("hidden")));
+extern struct marker * const __start___markers[] __attribute__((visibility("hidden")));
+extern struct marker * const __stop___markers[] __attribute__((visibility("hidden")));
/* Set to 1 to enable marker debug output */
static const int marker_debug;
*/
#define MARKER_HASH_BITS 6
#define MARKER_TABLE_SIZE (1 << MARKER_HASH_BITS)
-static struct hlist_head marker_table[MARKER_TABLE_SIZE];
+static struct cds_hlist_head marker_table[MARKER_TABLE_SIZE];
/*
* Note about RCU :
* marker entries modifications are protected by the markers_mutex.
*/
struct marker_entry {
- struct hlist_node hlist;
+ struct cds_hlist_node hlist;
char *format;
char *name;
/* Probe wrapper */
*/
static struct marker_entry *get_marker(const char *channel, const char *name)
{
- struct hlist_head *head;
- struct hlist_node *node;
+ struct cds_hlist_head *head;
+ struct cds_hlist_node *node;
struct marker_entry *e;
size_t channel_len = strlen(channel) + 1;
size_t name_len = strlen(name) + 1;
hash = jhash(channel, channel_len-1, 0) ^ jhash(name, name_len-1, 0);
head = &marker_table[hash & ((1 << MARKER_HASH_BITS)-1)];
- hlist_for_each_entry(e, node, head, hlist) {
+ cds_hlist_for_each_entry(e, node, head, hlist) {
if (!strcmp(channel, e->channel) && !strcmp(name, e->name))
return e;
}
static struct marker_entry *add_marker(const char *channel, const char *name,
const char *format)
{
- struct hlist_head *head;
- struct hlist_node *node;
+ struct cds_hlist_head *head;
+ struct cds_hlist_node *node;
struct marker_entry *e;
size_t channel_len = strlen(channel) + 1;
size_t name_len = strlen(name) + 1;
if (format)
format_len = strlen(format) + 1;
head = &marker_table[hash & ((1 << MARKER_HASH_BITS)-1)];
- hlist_for_each_entry(e, node, head, hlist) {
+ cds_hlist_for_each_entry(e, node, head, hlist) {
if (!strcmp(channel, e->channel) && !strcmp(name, e->name)) {
DBG("Marker %s.%s busy", channel, name);
return ERR_PTR(-EBUSY); /* Already there */
e->format_allocated = 0;
e->refcount = 0;
e->rcu_pending = 0;
- hlist_add_head(&e->hlist, head);
+ cds_hlist_add_head(&e->hlist, head);
return e;
}
*/
static int remove_marker(const char *channel, const char *name)
{
- struct hlist_head *head;
- struct hlist_node *node;
+ struct cds_hlist_head *head;
+ struct cds_hlist_node *node;
struct marker_entry *e;
int found = 0;
size_t channel_len = strlen(channel) + 1;
hash = jhash(channel, channel_len-1, 0) ^ jhash(name, name_len-1, 0);
head = &marker_table[hash & ((1 << MARKER_HASH_BITS)-1)];
- hlist_for_each_entry(e, node, head, hlist) {
+ cds_hlist_for_each_entry(e, node, head, hlist) {
if (!strcmp(channel, e->channel) && !strcmp(name, e->name)) {
found = 1;
break;
return -ENOENT;
if (e->single.func != __mark_empty_function)
return -EBUSY;
- hlist_del(&e->hlist);
+ cds_hlist_del(&e->hlist);
if (e->format_allocated)
free(e->format);
ret = ltt_channels_unregister(e->channel);
*
* Updates the probe callback corresponding to a range of markers.
*/
-void marker_update_probe_range(struct marker *begin,
- struct marker *end)
+void marker_update_probe_range(struct marker * const *begin,
+ struct marker * const *end)
{
- struct marker *iter;
+ struct marker * const *iter;
struct marker_entry *mark_entry;
pthread_mutex_lock(&markers_mutex);
for (iter = begin; iter < end; iter++) {
- mark_entry = get_marker(iter->channel, iter->name);
+ mark_entry = get_marker((*iter)->channel, (*iter)->name);
if (mark_entry) {
- set_marker(mark_entry, iter, !!mark_entry->refcount);
+ set_marker(mark_entry, *iter, !!mark_entry->refcount);
/*
* ignore error, continue
*/
"channel %s name %s event_id %hu "
"int #1u%zu long #1u%zu pointer #1u%zu "
"size_t #1u%zu alignment #1u%u",
- iter->channel, iter->name, mark_entry->event_id,
+ (*iter)->channel, (*iter)->name, mark_entry->event_id,
sizeof(int), sizeof(long), sizeof(void *),
sizeof(size_t), ltt_get_alignment());
} else {
- disable_marker(iter);
+ disable_marker(*iter);
}
}
pthread_mutex_unlock(&markers_mutex);
{
struct marker_entry *entry;
unsigned int i;
- struct hlist_head *head;
- struct hlist_node *node;
+ struct cds_hlist_head *head;
+ struct cds_hlist_node *node;
for (i = 0; i < MARKER_TABLE_SIZE; i++) {
head = &marker_table[i];
- hlist_for_each_entry(entry, node, head, hlist) {
+ cds_hlist_for_each_entry(entry, node, head, hlist) {
if (!entry->ptype) {
if (entry->single.func == probe
&& entry->single.probe_private
void *marker_get_private_data(const char *channel, const char *name,
marker_probe_func *probe, int num)
{
- struct hlist_head *head;
- struct hlist_node *node;
+ struct cds_hlist_head *head;
+ struct cds_hlist_node *node;
struct marker_entry *e;
size_t channel_len = strlen(channel) + 1;
size_t name_len = strlen(name) + 1;
hash = jhash(channel, channel_len-1, 0) ^ jhash(name, name_len-1, 0);
head = &marker_table[hash & ((1 << MARKER_HASH_BITS)-1)];
- hlist_for_each_entry(e, node, head, hlist) {
+ cds_hlist_for_each_entry(e, node, head, hlist) {
if (!strcmp(channel, e->channel) && !strcmp(name, e->name)) {
if (!e->ptype) {
if (num == 0 && e->single.func == probe)
* Returns whether a next marker has been found (1) or not (0).
* Will return the first marker in the range if the input marker is NULL.
*/
-int marker_get_iter_range(struct marker **marker, struct marker *begin,
- struct marker *end)
+int marker_get_iter_range(struct marker * const **marker,
+ struct marker * const *begin,
+ struct marker * const *end)
{
if (!*marker && begin != end) {
*marker = begin;
/*
* must be called with current->user_markers_mutex held
*/
-static void free_user_marker(char __user *state, struct hlist_head *head)
+static void free_user_marker(char __user *state, struct cds_hlist_head *head)
{
struct user_marker *umark;
- struct hlist_node *pos, *n;
+ struct cds_hlist_node *pos, *n;
- hlist_for_each_entry_safe(umark, pos, n, head, hlist) {
+ cds_hlist_for_each_entry_safe(umark, pos, n, head, hlist) {
if (umark->state == state) {
- hlist_del(&umark->hlist);
+ cds_hlist_del(&umark->hlist);
free(umark);
}
}
void exit_user_markers(struct task_struct *p)
{
struct user_marker *umark;
- struct hlist_node *pos, *n;
+ struct cds_hlist_node *pos, *n;
if (thread_group_leader(p)) {
pthread_mutex_lock(&markers_mutex);
pthread_mutex_lock(&p->user_markers_mutex);
- hlist_for_each_entry_safe(umark, pos, n, &p->user_markers,
+ cds_hlist_for_each_entry_safe(umark, pos, n, &p->user_markers,
hlist)
free(umark);
INIT_HLIST_HEAD(&p->user_markers);
{
struct marker_entry *entry;
struct ltt_probe_private_data call_data;
- struct hlist_head *head;
- struct hlist_node *node;
+ struct cds_hlist_head *head;
+ struct cds_hlist_node *node;
unsigned int i;
pthread_mutex_lock(&markers_mutex);
for (i = 0; i < MARKER_TABLE_SIZE; i++) {
head = &marker_table[i];
- hlist_for_each_entry(entry, node, head, hlist) {
+ cds_hlist_for_each_entry(entry, node, head, hlist) {
__trace_mark(0, metadata, core_marker_id,
&call_data,
"channel %s name %s event_id %hu "
new_marker_cb = cb;
}
-static void new_markers(struct marker *start, struct marker *end)
+static void new_markers(struct marker * const *start, struct marker * const *end)
{
- if(new_marker_cb) {
- struct marker *m;
+ if (new_marker_cb) {
+ struct marker * const *m;
for(m=start; m < end; m++) {
- new_marker_cb(m);
+ new_marker_cb(*m);
}
}
}
-int marker_register_lib(struct marker *markers_start, int markers_count)
+int marker_register_lib(struct marker * const *markers_start, int markers_count)
{
struct lib *pl;
return 0;
}
-int marker_unregister_lib(struct marker *markers_start)
+int marker_unregister_lib(struct marker * const *markers_start)
{
struct lib *lib;
void __attribute__((constructor)) init_markers(void)
{
if(!initialized) {
- marker_register_lib(__start___markers, (((long)__stop___markers)-((long)__start___markers))/sizeof(struct marker));
+ marker_register_lib(__start___markers,
+ (((long)__stop___markers) - ((long)__start___markers))
+ / sizeof(*__start___markers));
initialized = 1;
}
}