sd-journal.c revision 38a6db16dc6f3ac6e6f497c90e51fb9904d785ba
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara/*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara This file is part of systemd.
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara Copyright 2011 Lennart Poettering
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara systemd is free software; you can redistribute it and/or modify it
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara under the terms of the GNU Lesser General Public License as published by
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara the Free Software Foundation; either version 2.1 of the License, or
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara (at your option) any later version.
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara systemd is distributed in the hope that it will be useful, but
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara WITHOUT ANY WARRANTY; without even the implied warranty of
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara Lesser General Public License for more details.
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara You should have received a copy of the GNU Lesser General Public License
c9d984b0d2c0fda320e79eb3868dd6fbeb1ffa34jvergara along with systemd; If not, see <http://www.gnu.org/licenses/>.
27f8adec83293fb8bd3bfa37175322b0ee3bb933jvergarastatic void init_location(Location *l, JournalFile *f, Object *o) {
37f9a536593b696e5a3dcec443e1475f22fb5afdjvergara l->seqnum_set = l->realtime_set = l->monotonic_set = l->xor_hash_set = true;
37f9a536593b696e5a3dcec443e1475f22fb5afdjvergarastatic void set_location(sd_journal *j, JournalFile *f, Object *o, uint64_t offset) {
assert(f);
assert(o);
j->current_file = f;
j->current_field = 0;
size_t j;
a_good = true;
b_good = true;
different = true;
return -EINVAL;
return -EINVAL;
if (!data)
return -EINVAL;
return -EINVAL;
return -EINVAL;
return -EINVAL;
if (j->matches)
return -ENOTSUP;
after = m;
return -ENOMEM;
if (!m->data) {
free(m);
return -ENOMEM;
j->n_matches ++;
detach_location(j);
while (j->matches) {
free(m);
j->n_matches = 0;
detach_location(j);
uint64_t a, b;
uint64_t a;
assert(l);
if (l->monotonic_set &&
l->realtime_set &&
l->xor_hash_set &&
if (l->seqnum_set &&
if (a < l->seqnum)
if (a > l->seqnum)
if (l->monotonic_set &&
if (a < l->monotonic)
if (a > l->monotonic)
if (l->realtime_set) {
if (a < l->realtime)
if (a > l->realtime)
if (l->xor_hash_set) {
if (a < l->xor_hash)
if (a > l->xor_hash)
static int find_location(sd_journal *j, JournalFile *f, direction_t direction, Object **ret, uint64_t *offset) {
uint64_t p = 0;
assert(j);
if (!j->matches) {
r = journal_file_move_to_entry_by_monotonic(f, j->current_location.boot_id, j->current_location.monotonic, direction, &o, &p);
if (r == -ENOENT) {
r = journal_file_move_to_entry_by_monotonic(f, j->current_location.boot_id, j->current_location.monotonic, direction, &o, &p);
return r == -ENOENT ? 0 : r;
Object *c, *d;
r = journal_file_move_to_entry_by_seqnum_for_data(f, dp, j->current_location.seqnum, direction, &c, &cp);
r = journal_file_move_to_entry_by_realtime_for_data(f, dp, j->current_location.realtime, direction, &c, &cp);
if (!term_match) {
term_match = m;
to = c;
if (!to ||
to = c;
if (!to)
o = to;
p = tp;
term_match = m;
to = c;
tp = 0;
if (!to)
o = to;
p = tp;
if (ret)
*ret = o;
if (offset)
*offset = p;
static int next_with_matches(sd_journal *j, JournalFile *f, direction_t direction, Object **ret, uint64_t *offset) {
Object *c;
assert(j);
assert(f);
c = *ret;
if (!j->matches) {
if (ret)
*ret = c;
if (offset)
n = journal_file_entry_n_items(c);
np = 0;
uint64_t q, k;
if (!term_match) {
term_match = m;
term_result = false;
if (!term_result)
found = false;
term_match = m;
term_result = false;
term_result = true;
r = journal_file_next_entry_for_data(f, c, cp, le64toh(c->entry.items[k].object_offset), direction, &qo, &q);
c = NULL;
if (q > np) {
np = q;
np = q;
found = false;
if (found) {
if (ret) {
if (c == NULL) {
*ret = c;
if (offset)
if (np == 0)
c = npo;
static int next_beyond_location(sd_journal *j, JournalFile *f, direction_t direction, Object **ret, uint64_t *offset) {
Object *c;
int compare_value, r;
assert(j);
assert(f);
if (f->current_offset > 0) {
compare_value = 0;
bool found;
found = true;
if (found) {
if (ret)
*ret = c;
if (offset)
Iterator i;
return -EINVAL;
Object *o;
uint64_t p;
bool found;
if (!new_current)
found = true;
found = k < 0;
found = k > 0;
if (found) {
new_current = f;
new_entry = o;
new_offset = p;
if (!new_current)
return -EINVAL;
if (skip == 0) {
skip--;
} while (skip > 0);
Object *o;
return -EINVAL;
if (!cursor)
return -EINVAL;
return -EADDRNOTAVAIL;
r = journal_file_move_to_object(j->current_file, OBJECT_ENTRY, j->current_file->current_offset, &o);
return -ENOMEM;
size_t l;
char *state;
seqnum_id_set = false,
seqnum_set = false,
boot_id_set = false,
monotonic_set = false,
realtime_set = false,
xor_hash_set = false;
return -EINVAL;
if (!cursor)
return -EINVAL;
char *item;
return -EINVAL;
if (!item)
return -ENOMEM;
seqnum_id_set = true;
seqnum_set = true;
k = -EINVAL;
boot_id_set = true;
monotonic_set = true;
k = -EINVAL;
realtime_set = true;
k = -EINVAL;
xor_hash_set = true;
k = -EINVAL;
return -EINVAL;
reset_location(j);
if (realtime_set) {
if (xor_hash_set) {
return -EINVAL;
reset_location(j);
return -EINVAL;
reset_location(j);
return -EINVAL;
reset_location(j);
return -EINVAL;
reset_location(j);
char *fn;
JournalFile *f;
assert(j);
if (dir)
if (!fn)
return -ENOMEM;
char *fn;
JournalFile *f;
assert(j);
if (dir)
if (!fn)
return -ENOMEM;
char *fn;
DIR *d;
int wd;
assert(j);
if (!fn)
return -ENOMEM;
return -errno;
if (wd > 0) {
if (r != 0 || !de)
closedir(d);
assert(j);
if (j->inotify_fd >= 0)
free(p);
int wd;
assert(j);
assert(p);
if (wd <= 0)
k = strdup(p);
free(k);
assert(j);
if (j->inotify_fd >= 0)
free(p);
sd_journal *j;
const char search_paths[] =
if (!ret)
return -EINVAL;
return -EINVAL;
return -ENOMEM;
if (j->inotify_fd < 0) {
r = -errno;
goto fail;
if (!j->files) {
r = -ENOMEM;
goto fail;
r = -ENOMEM;
goto fail;
DIR *d;
d = opendir(p);
add_root_wd(j, p);
if (r != 0 || !de)
closedir(d);
*ret = j;
fail:
sd_journal_close(j);
if (j->inotify_wd_dirs) {
if (j->inotify_wd_roots) {
if (j->files) {
JournalFile *f;
if (j->inotify_fd >= 0)
free(j);
Object *o;
JournalFile *f;
return -EINVAL;
if (!ret)
return -EINVAL;
f = j->current_file;
return -EADDRNOTAVAIL;
if (f->current_offset <= 0)
return -EADDRNOTAVAIL;
Object *o;
JournalFile *f;
return -EINVAL;
if (!ret)
return -EINVAL;
f = j->current_file;
return -EADDRNOTAVAIL;
if (f->current_offset <= 0)
return -EADDRNOTAVAIL;
if (ret_boot_id)
return -ESTALE;
_public_ int sd_journal_get_data(sd_journal *j, const char *field, const void **data, size_t *size) {
JournalFile *f;
uint64_t i, n;
Object *o;
return -EINVAL;
if (!field)
return -EINVAL;
if (!data)
return -EINVAL;
if (!size)
return -EINVAL;
return -EINVAL;
f = j->current_file;
return -EADDRNOTAVAIL;
if (f->current_offset <= 0)
return -EADDRNOTAVAIL;
n = journal_file_entry_n_items(o);
uint64_t p, l;
size_t t;
return -EBADMSG;
#ifdef HAVE_XZ
return -EBADMSG;
return -EPROTONOSUPPORT;
t = (size_t) l;
if ((uint64_t) t != l)
return -E2BIG;
*size = t;
return -ENOENT;
JournalFile *f;
uint64_t p, l, n;
Object *o;
size_t t;
return -EINVAL;
if (!data)
return -EINVAL;
if (!size)
return -EINVAL;
f = j->current_file;
return -EADDRNOTAVAIL;
if (f->current_offset <= 0)
return -EADDRNOTAVAIL;
n = journal_file_entry_n_items(o);
if (j->current_field >= n)
return -EBADMSG;
t = (size_t) l;
if ((uint64_t) t != l)
return -E2BIG;
#ifdef HAVE_XZ
return -EBADMSG;
return -EPROTONOSUPPORT;
*size = t;
j->current_field ++;
j->current_field = 0;
return -EINVAL;
return j->inotify_fd;
assert(j);
assert(e);
} else if (e->len == 0) {
return -EINVAL;
struct inotify_event *e;
ssize_t l;
return -errno;
process_inotify_event(j, e);
l -= step;
Iterator i;
JournalFile *f;
bool first = true;
return -EINVAL;
return -EINVAL;
if (first) {
if (from)
if (to)
*to = t;
first = false;
if (from)
if (to)
_public_ int sd_journal_get_cutoff_monotonic_usec(sd_journal *j, sd_id128_t boot_id, uint64_t *from, uint64_t *to) {
Iterator i;
JournalFile *f;
bool first = true;
return -EINVAL;
return -EINVAL;
if (first) {
if (from)
if (to)
*to = t;
first = false;
if (from)
if (to)