File: syslog.py

package info (click to toggle)
pypy 2.4.0%2Bdfsg-3
  • links: PTS, VCS
  • area: main
  • in suites: jessie, jessie-kfreebsd
  • size: 86,992 kB
  • ctags: 170,715
  • sloc: python: 1,030,417; ansic: 43,437; cpp: 5,241; asm: 5,169; sh: 458; makefile: 408; xml: 231; lisp: 45
file content (161 lines) | stat: -rw-r--r-- 3,606 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
# this cffi version was rewritten based on the
# ctypes implementation: Victor Stinner, 2008-05-08
"""
This module provides an interface to the Unix syslog library routines.
Refer to the Unix manual pages for a detailed description of the
syslog facility.
"""

import sys
if sys.platform == 'win32':
    raise ImportError("No syslog on Windows")

from cffi import FFI

try: from __pypy__ import builtinify
except ImportError: builtinify = lambda f: f

ffi = FFI()

ffi.cdef("""
/* mandatory constants */
#define LOG_EMERG ...
#define LOG_ALERT ...
#define LOG_CRIT ...
#define LOG_ERR ...
#define LOG_WARNING ...
#define LOG_NOTICE ...
#define LOG_INFO ...
#define LOG_DEBUG ...

#define LOG_PID ...
#define LOG_CONS ...
#define LOG_NDELAY ...

#define LOG_KERN ...
#define LOG_USER ...
#define LOG_MAIL ...
#define LOG_DAEMON ...
#define LOG_AUTH ...
#define LOG_LPR ...
#define LOG_LOCAL0 ...
#define LOG_LOCAL1 ...
#define LOG_LOCAL2 ...
#define LOG_LOCAL3 ...
#define LOG_LOCAL4 ...
#define LOG_LOCAL5 ...
#define LOG_LOCAL6 ...
#define LOG_LOCAL7 ...

/* optional constants, gets defined to -919919 if missing */
#define LOG_NOWAIT ...
#define LOG_PERROR ...

/* aliased constants, gets defined as some other constant if missing */
#define LOG_SYSLOG ...
#define LOG_CRON ...
#define LOG_UUCP ...
#define LOG_NEWS ...

/* functions */
void openlog(const char *ident, int option, int facility);
void syslog(int priority, const char *format, const char *string);
// NB. the signature of syslog() is specialized to the only case we use
void closelog(void);
int setlogmask(int mask);
""")

lib = ffi.verify("""
#include <syslog.h>

#ifndef LOG_NOWAIT
#define LOG_NOWAIT -919919
#endif
#ifndef LOG_PERROR
#define LOG_PERROR -919919
#endif
#ifndef LOG_SYSLOG
#define LOG_SYSLOG LOG_DAEMON
#endif
#ifndef LOG_CRON
#define LOG_CRON LOG_DAEMON
#endif
#ifndef LOG_UUCP
#define LOG_UUCP LOG_MAIL
#endif
#ifndef LOG_NEWS
#define LOG_NEWS LOG_MAIL
#endif
""")


_S_log_open = False
_S_ident_o = None

def _get_argv():
    try:
        import sys
        script = sys.argv[0]
        if isinstance(script, str):
            return script[script.rfind('/')+1:] or None
    except Exception:
        pass
    return None

@builtinify
def openlog(ident=None, logoption=0, facility=lib.LOG_USER):
    global _S_ident_o, _S_log_open
    if ident is None:
        ident = _get_argv()
    if ident is None:
        _S_ident_o = ffi.NULL
    elif isinstance(ident, str):
        _S_ident_o = ffi.new("char[]", ident)    # keepalive
    else:
        raise TypeError("'ident' must be a string or None")
    lib.openlog(_S_ident_o, logoption, facility)
    _S_log_open = True

@builtinify
def syslog(arg1, arg2=None):
    if arg2 is not None:
        priority, message = arg1, arg2
    else:
        priority, message = LOG_INFO, arg1
    # if log is not opened, open it now
    if not _S_log_open:
        openlog()
    lib.syslog(priority, "%s", message)

@builtinify
def closelog():
    global _S_log_open, S_ident_o
    if _S_log_open:
        lib.closelog()
        _S_log_open = False
        _S_ident_o = None

@builtinify
def setlogmask(mask):
    return lib.setlogmask(mask)

@builtinify
def LOG_MASK(pri):
    return (1 << pri)

@builtinify
def LOG_UPTO(pri):
    return (1 << (pri + 1)) - 1

__all__ = []

for name in sorted(lib.__dict__):
    if name.startswith('LOG_'):
        value = getattr(lib, name)
        if value != -919919:
            globals()[name] = value
            __all__.append(name)

__all__ = tuple(__all__) + (
    'openlog', 'syslog', 'closelog', 'setlogmask',
    'LOG_MASK', 'LOG_UPTO')