2 * @file opd_sample_files.c
3 * Management of sample files
5 * @remark Copyright 2002 OProfile authors
6 * @remark Read the file COPYING
9 * @author Philippe Elie
12 #include <sys/types.h>
14 #include "opd_sample_files.h"
15 #include "opd_image.h"
16 #include "opd_printf.h"
17 #include "opd_events.h"
18 #include "oprofiled.h"
20 #include "op_sample_file.h"
22 #include "op_config.h"
23 #include "op_mangle.h"
24 #include "op_events.h"
31 /** All sfiles are on this list. */
32 static LIST_HEAD(lru_list);
34 /* this value probably doesn't matter too much */
35 #define LRU_AMOUNT 1000
36 static int opd_24_sfile_lru_clear(void)
38 struct list_head * pos;
39 struct list_head * pos2;
40 struct opd_24_sfile * sfile;
41 int amount = LRU_AMOUNT;
43 verbprintf(vsfile, "image lru clear\n");
45 if (list_empty(&lru_list))
48 list_for_each_safe(pos, pos2, &lru_list) {
51 sfile = list_entry(pos, struct opd_24_sfile, lru_next);
52 odb_close(&sfile->sample_file);
53 list_del_init(&sfile->lru_next);
60 void opd_24_sfile_lru(struct opd_24_sfile * sfile)
62 list_del(&sfile->lru_next);
63 list_add_tail(&sfile->lru_next, &lru_list);
67 static char * opd_mangle_filename(struct opd_image const * image, int counter,
71 struct mangle_values values;
72 struct opd_event * event = find_counter_event(counter);
76 values.flags |= MANGLE_KERNEL;
78 if (separate_thread) {
79 values.flags |= MANGLE_TGID | MANGLE_TID;
80 values.tid = image->tid;
81 values.tgid = image->tgid;
85 values.flags |= MANGLE_CPU;
89 values.event_name = event->name;
90 values.count = event->count;
91 values.unit_mask = event->um;
93 values.image_name = image->name;
94 values.dep_name = separate_lib && image->app_name
95 ? image->app_name : image->name;
97 mangled = op_mangle_filename(&values);
103 int opd_open_24_sample_file(struct opd_image * image, int counter, int cpu_nr)
106 struct opd_24_sfile * sfile;
109 mangled = opd_mangle_filename(image, counter, cpu_nr);
111 verbprintf(vsfile, "Opening \"%s\"\n", mangled);
113 create_path(mangled);
115 sfile = image->sfiles[cpu_nr][counter];
117 sfile = malloc(sizeof(struct opd_24_sfile));
118 list_init(&sfile->lru_next);
119 odb_init(&sfile->sample_file);
120 image->sfiles[cpu_nr][counter] = sfile;
123 list_del(&sfile->lru_next);
124 list_add_tail(&sfile->lru_next, &lru_list);
127 err = odb_open(&sfile->sample_file, mangled, ODB_RDWR,
128 sizeof(struct opd_header));
130 /* This can naturally happen when racing against opcontrol --reset. */
133 if (opd_24_sfile_lru_clear()) {
134 printf("LRU cleared but odb_open() fails for %s.\n", mangled);
140 fprintf(stderr, "oprofiled: open of %s failed: %s\n",
141 mangled, strerror(err));
145 fill_header(odb_get_data(&sfile->sample_file), counter, 0, 0,
146 image->kernel, 0, 0, 0, image->mtime);
154 void opd_sync_samples_files(void)
156 struct list_head * pos;
157 struct opd_24_sfile * sfile;
159 list_for_each(pos, &lru_list) {
160 sfile = list_entry(pos, struct opd_24_sfile, lru_next);
161 odb_sync(&sfile->sample_file);
166 void opd_close_image_samples_files(struct opd_image * image)
169 for (i = 0 ; i < op_nr_counters ; ++i) {
170 for (j = 0; j < NR_CPUS; ++j) {
171 if (image->sfiles[j] && image->sfiles[j][i]) {
172 odb_close(&image->sfiles[j][i]->sample_file);
173 list_del(&image->sfiles[j][i]->lru_next);
174 free(image->sfiles[j][i]);
175 image->sfiles[j][i] = 0;