line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
1
|
|
|
|
|
|
|
###########################################################################
|
2
|
|
|
|
|
|
|
#
|
3
|
|
|
|
|
|
|
# Driver.pm
|
4
|
|
|
|
|
|
|
#
|
5
|
|
|
|
|
|
|
# Copyright (C) 1999 Raphael Manfredi.
|
6
|
|
|
|
|
|
|
# Copyright (C) 2002-2017 Mark Rogaski, mrogaski@cpan.org;
|
7
|
|
|
|
|
|
|
# all rights reserved.
|
8
|
|
|
|
|
|
|
#
|
9
|
|
|
|
|
|
|
# See the README file included with the
|
10
|
|
|
|
|
|
|
# distribution for license information.
|
11
|
|
|
|
|
|
|
#
|
12
|
|
|
|
|
|
|
##########################################################################
|
13
|
|
|
|
|
|
|
|
14
|
14
|
|
|
14
|
|
104
|
use strict;
|
|
14
|
|
|
|
|
30
|
|
|
14
|
|
|
|
|
18339
|
|
15
|
|
|
|
|
|
|
|
16
|
|
|
|
|
|
|
########################################################################
|
17
|
|
|
|
|
|
|
package Log::Agent::Driver;
|
18
|
|
|
|
|
|
|
|
19
|
|
|
|
|
|
|
#
|
20
|
|
|
|
|
|
|
# Ancestor for all Log::Agent drivers.
|
21
|
|
|
|
|
|
|
#
|
22
|
|
|
|
|
|
|
|
23
|
|
|
|
|
|
|
#
|
24
|
|
|
|
|
|
|
# Common attribute acccess, initialized via _init().
|
25
|
|
|
|
|
|
|
#
|
26
|
|
|
|
|
|
|
# prefix the common (static) string info to prepend to messages
|
27
|
|
|
|
|
|
|
# penalty the skip Carp penalty to offset to the fixed one
|
28
|
|
|
|
|
|
|
#
|
29
|
|
|
|
|
|
|
|
30
|
93
|
|
|
93
|
0
|
709
|
sub prefix { $_[0]->{'prefix'} }
|
31
|
37
|
|
|
37
|
0
|
93
|
sub penalty { $_[0]->{'penalty'} }
|
32
|
|
|
|
|
|
|
|
33
|
|
|
|
|
|
|
#
|
34
|
|
|
|
|
|
|
# is_deferred
|
35
|
|
|
|
|
|
|
#
|
36
|
|
|
|
|
|
|
# Report routine as being deferred
|
37
|
|
|
|
|
|
|
#
|
38
|
|
|
|
|
|
|
sub is_deferred {
|
39
|
0
|
|
|
0
|
0
|
0
|
require Carp;
|
40
|
0
|
|
|
|
|
0
|
Carp::confess("deferred");
|
41
|
|
|
|
|
|
|
}
|
42
|
|
|
|
|
|
|
|
43
|
|
|
|
|
|
|
#
|
44
|
|
|
|
|
|
|
# ->make -- deferred
|
45
|
|
|
|
|
|
|
#
|
46
|
|
|
|
|
|
|
# Creation routine.
|
47
|
|
|
|
|
|
|
#
|
48
|
|
|
|
|
|
|
sub make {
|
49
|
0
|
|
|
0
|
1
|
0
|
&is_deferred;
|
50
|
|
|
|
|
|
|
}
|
51
|
|
|
|
|
|
|
|
52
|
|
|
|
|
|
|
#
|
53
|
|
|
|
|
|
|
# ->channel_eq
|
54
|
|
|
|
|
|
|
#
|
55
|
|
|
|
|
|
|
# Compare two channels and return true if they go to the same output.
|
56
|
|
|
|
|
|
|
#
|
57
|
|
|
|
|
|
|
sub channel_eq {
|
58
|
0
|
|
|
0
|
1
|
0
|
&is_deferred;
|
59
|
|
|
|
|
|
|
}
|
60
|
|
|
|
|
|
|
|
61
|
|
|
|
|
|
|
#
|
62
|
|
|
|
|
|
|
# ->_init
|
63
|
|
|
|
|
|
|
#
|
64
|
|
|
|
|
|
|
# Common initilization routine
|
65
|
|
|
|
|
|
|
#
|
66
|
|
|
|
|
|
|
sub _init {
|
67
|
29
|
|
|
29
|
|
53
|
my $self = shift;
|
68
|
29
|
|
|
|
|
62
|
my ($prefix, $penalty) = @_;
|
69
|
29
|
|
|
|
|
106
|
$self->{'prefix'} = $prefix; # Prefix info to prepend
|
70
|
29
|
|
|
|
|
75
|
$self->{'penalty'} = $penalty; # Carp stack skip penalty
|
71
|
|
|
|
|
|
|
}
|
72
|
|
|
|
|
|
|
|
73
|
|
|
|
|
|
|
#
|
74
|
|
|
|
|
|
|
# ->add_penalty -- "exported" only to Log::Agent::Driver::Datum
|
75
|
|
|
|
|
|
|
#
|
76
|
|
|
|
|
|
|
# Add offset to current driver penalty
|
77
|
|
|
|
|
|
|
#
|
78
|
|
|
|
|
|
|
sub add_penalty {
|
79
|
0
|
|
|
0
|
0
|
0
|
my $self = shift;
|
80
|
0
|
|
|
|
|
0
|
my ($offset) = @_;
|
81
|
0
|
|
|
|
|
0
|
$self->{penalty} += $offset;
|
82
|
|
|
|
|
|
|
}
|
83
|
|
|
|
|
|
|
|
84
|
|
|
|
|
|
|
my %level = (
|
85
|
|
|
|
|
|
|
'c' => 1,
|
86
|
|
|
|
|
|
|
'e' => 2,
|
87
|
|
|
|
|
|
|
'w' => 4,
|
88
|
|
|
|
|
|
|
'n' => 6,
|
89
|
|
|
|
|
|
|
);
|
90
|
|
|
|
|
|
|
|
91
|
|
|
|
|
|
|
#
|
92
|
|
|
|
|
|
|
# ->priority -- frozen
|
93
|
|
|
|
|
|
|
#
|
94
|
|
|
|
|
|
|
# Return proper priority for emit() based on one of the following strings:
|
95
|
|
|
|
|
|
|
# "critical", "error", "warning", "notice". Those correspond to the hardwired
|
96
|
|
|
|
|
|
|
# strings for logconfess()/logdie(), logerr(), logwarn() and logsay().
|
97
|
|
|
|
|
|
|
#
|
98
|
|
|
|
|
|
|
# This routine is intended to be "frozen", i.e. it MUST NOT be redefined.
|
99
|
|
|
|
|
|
|
# Redefine map_pri() if needed, or don't call it in the first place.
|
100
|
|
|
|
|
|
|
#
|
101
|
|
|
|
|
|
|
sub priority {
|
102
|
68
|
|
|
68
|
1
|
133
|
my $self = shift;
|
103
|
68
|
|
|
|
|
119
|
my ($prio) = @_;
|
104
|
68
|
|
50
|
|
|
280
|
my $level = $level{lc(substr($prio, 0, 1))} || 8;
|
105
|
68
|
|
|
|
|
203
|
return $self->map_pri($prio, $level);
|
106
|
|
|
|
|
|
|
}
|
107
|
|
|
|
|
|
|
|
108
|
|
|
|
|
|
|
#
|
109
|
|
|
|
|
|
|
# ->write -- deferred
|
110
|
|
|
|
|
|
|
#
|
111
|
|
|
|
|
|
|
# Write log entry, physically.
|
112
|
|
|
|
|
|
|
# A trailing "\n" is to be added if needed.
|
113
|
|
|
|
|
|
|
#
|
114
|
|
|
|
|
|
|
# $channel is one of 'debug', 'output', 'error' and can be used to determine
|
115
|
|
|
|
|
|
|
# where the emission of the log message should be done.
|
116
|
|
|
|
|
|
|
#
|
117
|
|
|
|
|
|
|
sub write {
|
118
|
0
|
|
|
0
|
1
|
0
|
my $self = shift;
|
119
|
0
|
|
|
|
|
0
|
my ($channel, $priority, $logstring) = @_;
|
120
|
0
|
|
|
|
|
0
|
&is_deferred;
|
121
|
|
|
|
|
|
|
}
|
122
|
|
|
|
|
|
|
|
123
|
|
|
|
|
|
|
#
|
124
|
|
|
|
|
|
|
# ->emit -- may be redefined
|
125
|
|
|
|
|
|
|
#
|
126
|
|
|
|
|
|
|
# Routine to call to emit log, resolve priority and prefix logstring.
|
127
|
|
|
|
|
|
|
# Ulitimately calls ->write() to perform the physical write.
|
128
|
|
|
|
|
|
|
#
|
129
|
|
|
|
|
|
|
sub emit {
|
130
|
68
|
|
|
68
|
1
|
131
|
my $self = shift;
|
131
|
68
|
|
|
|
|
143
|
my ($channel, $prio, $msg) = @_;
|
132
|
68
|
|
|
|
|
172
|
$self->write($channel, $self->priority($prio), $self->prefix_msg($msg));
|
133
|
68
|
|
|
|
|
408
|
return;
|
134
|
|
|
|
|
|
|
}
|
135
|
|
|
|
|
|
|
|
136
|
|
|
|
|
|
|
|
137
|
|
|
|
|
|
|
#
|
138
|
|
|
|
|
|
|
# ->map_pri -- may be redefined
|
139
|
|
|
|
|
|
|
#
|
140
|
|
|
|
|
|
|
# Convert a ("priority", level) tupple to a single priority token suitable
|
141
|
|
|
|
|
|
|
# for `emit'.
|
142
|
|
|
|
|
|
|
#
|
143
|
|
|
|
|
|
|
# This is driver-specific: drivers may ignore priority altogether thanks to
|
144
|
|
|
|
|
|
|
# the previous level-based filtering done (-trace and -debug switches in the
|
145
|
|
|
|
|
|
|
# Log::Agent configuration), choose to give precedence to levels over priority
|
146
|
|
|
|
|
|
|
# when "priority:level" was specified, or always ignore levels and only use
|
147
|
|
|
|
|
|
|
# "priority".
|
148
|
|
|
|
|
|
|
#
|
149
|
|
|
|
|
|
|
# The default is to ignore "priority" and "levels", which is suitable to basic
|
150
|
|
|
|
|
|
|
# drivers. Only those (ala syslog) which rely on post-filtering need to be
|
151
|
|
|
|
|
|
|
# concerned.
|
152
|
|
|
|
|
|
|
#
|
153
|
|
|
|
|
|
|
sub map_pri {
|
154
|
73
|
|
|
73
|
1
|
107
|
my $self = shift;
|
155
|
73
|
|
|
|
|
132
|
my ($priority, $level) = @_;
|
156
|
73
|
|
|
|
|
242
|
return ''; # ignored for basic drivers
|
157
|
|
|
|
|
|
|
}
|
158
|
|
|
|
|
|
|
|
159
|
|
|
|
|
|
|
#
|
160
|
|
|
|
|
|
|
# ->prefix_msg -- deferred
|
161
|
|
|
|
|
|
|
#
|
162
|
|
|
|
|
|
|
# Prefix message with driver-specific string, if necessary.
|
163
|
|
|
|
|
|
|
#
|
164
|
|
|
|
|
|
|
# This routine may or may not use common attributes like the fixed
|
165
|
|
|
|
|
|
|
# static prefix or the process's pid.
|
166
|
|
|
|
|
|
|
#
|
167
|
|
|
|
|
|
|
sub prefix_msg {
|
168
|
0
|
|
|
0
|
1
|
0
|
my $self = shift;
|
169
|
0
|
|
|
|
|
0
|
my ($str) = @_;
|
170
|
0
|
|
|
|
|
0
|
&is_deferred;
|
171
|
|
|
|
|
|
|
}
|
172
|
|
|
|
|
|
|
|
173
|
|
|
|
|
|
|
#
|
174
|
|
|
|
|
|
|
# ->carpmess
|
175
|
|
|
|
|
|
|
#
|
176
|
|
|
|
|
|
|
# Utility routine for logconfess and logcroak which builds the "die" message
|
177
|
|
|
|
|
|
|
# by calling the appropriate routine in Carp, and offseting the stack
|
178
|
|
|
|
|
|
|
# according to our call stack configuration, plus any offset.
|
179
|
|
|
|
|
|
|
#
|
180
|
|
|
|
|
|
|
sub carpmess {
|
181
|
37
|
|
|
37
|
0
|
98
|
my $self = shift;
|
182
|
37
|
|
|
|
|
71
|
my ($offset, $str, $fn) = @_;
|
183
|
|
|
|
|
|
|
|
184
|
|
|
|
|
|
|
#
|
185
|
|
|
|
|
|
|
# While confessing, we have basically tell $fn() to skip 2 stack frames:
|
186
|
|
|
|
|
|
|
# this call, and our caller chain back to Log::Agent (calls within the
|
187
|
|
|
|
|
|
|
# same hierarchy are automatically stripped by Carp).
|
188
|
|
|
|
|
|
|
#
|
189
|
|
|
|
|
|
|
# To that, we add any additional penalty level, as told us by the creation
|
190
|
|
|
|
|
|
|
# routine of each driver, which accounts for extra levels used before
|
191
|
|
|
|
|
|
|
# calling us.
|
192
|
|
|
|
|
|
|
#
|
193
|
|
|
|
|
|
|
|
194
|
37
|
|
|
|
|
133
|
require Carp;
|
195
|
|
|
|
|
|
|
|
196
|
37
|
|
|
|
|
119
|
my $skip = $offset + 2 + $self->penalty;
|
197
|
37
|
|
|
|
|
61
|
$Carp::CarpLevel += $skip;
|
198
|
37
|
|
|
|
|
94
|
my $original = $str->str; # Original user message
|
199
|
37
|
|
|
|
|
6045
|
my $msg = &$fn('__MESSAGE__');
|
200
|
37
|
|
|
|
|
1720
|
$Carp::CarpLevel -= $skip;
|
201
|
|
|
|
|
|
|
|
202
|
|
|
|
|
|
|
#
|
203
|
|
|
|
|
|
|
# If we have a newline in the message, we have a full stack trace.
|
204
|
|
|
|
|
|
|
# Replace the original message string with the first line, and
|
205
|
|
|
|
|
|
|
# append the remaining.
|
206
|
|
|
|
|
|
|
#
|
207
|
|
|
|
|
|
|
|
208
|
37
|
|
|
|
|
81
|
chomp($msg); # Remove final "\n" added
|
209
|
|
|
|
|
|
|
|
210
|
37
|
100
|
|
|
|
194
|
if ($msg =~ s/^(.*?)\n//) {
|
211
|
10
|
|
|
|
|
34
|
my $first = $1;
|
212
|
|
|
|
|
|
|
|
213
|
|
|
|
|
|
|
#
|
214
|
|
|
|
|
|
|
# Patch incorrect computation by Carp, which occurs when we request
|
215
|
|
|
|
|
|
|
# a short message and we get a long one. In that case, what we
|
216
|
|
|
|
|
|
|
# want is the first line of the extra message.
|
217
|
|
|
|
|
|
|
#
|
218
|
|
|
|
|
|
|
# This bug manifests when the whole call chain above Log::Agent
|
219
|
|
|
|
|
|
|
# lies in "main". When objects are involved, it seems to work
|
220
|
|
|
|
|
|
|
# correctly.
|
221
|
|
|
|
|
|
|
#
|
222
|
|
|
|
|
|
|
# The kludge here is valid for perl 5.005_03. If some day Carp is
|
223
|
|
|
|
|
|
|
# fixed, we will have to test for the Perl version. The right fix,
|
224
|
|
|
|
|
|
|
# I believe, would be to have Carp skip frame first, and not last
|
225
|
|
|
|
|
|
|
# as it currently does.
|
226
|
|
|
|
|
|
|
# -- RAM, 30/09/2000
|
227
|
|
|
|
|
|
|
#
|
228
|
|
|
|
|
|
|
|
229
|
10
|
50
|
|
|
|
36
|
if ($fn == \&Carp::shortmess) { # Kludge alert!!
|
230
|
|
|
|
|
|
|
|
231
|
|
|
|
|
|
|
#
|
232
|
|
|
|
|
|
|
# And things just got a little uglier with 5.8.0
|
233
|
|
|
|
|
|
|
#
|
234
|
|
|
|
|
|
|
# -- mrogaski, 1 Aug 2002
|
235
|
|
|
|
|
|
|
#
|
236
|
10
|
50
|
|
|
|
29
|
my $index = $] >= 5.008 ? 1 : 0;
|
237
|
|
|
|
|
|
|
|
238
|
10
|
|
|
|
|
67
|
$first =~ s/(at (.+) line \d+)$//;
|
239
|
10
|
|
|
|
|
26
|
my $bad = $1;
|
240
|
10
|
|
|
|
|
37
|
my @stack = split(/\n/, $msg);
|
241
|
10
|
100
|
|
|
|
95
|
my ($at) = $stack[$index] =~ /(at \S+ line \d+)$/
|
242
|
|
|
|
|
|
|
if defined $stack[$index];
|
243
|
10
|
100
|
|
|
|
37
|
$at = "$bad (Log::Agent could not fix it)" unless $at;
|
244
|
10
|
|
|
|
|
78
|
$first .= $at;
|
245
|
10
|
|
|
|
|
40
|
$str->set_str($first);
|
246
|
|
|
|
|
|
|
} else {
|
247
|
0
|
|
|
|
|
0
|
$str->set_str($first);
|
248
|
0
|
|
|
|
|
0
|
$str->append_last("\n");
|
249
|
0
|
|
|
|
|
0
|
$str->append_last($msg); # Stack at the very tail of message
|
250
|
|
|
|
|
|
|
}
|
251
|
|
|
|
|
|
|
} else {
|
252
|
27
|
|
|
|
|
83
|
$str->set_str($msg); # Change original message inplace
|
253
|
|
|
|
|
|
|
}
|
254
|
|
|
|
|
|
|
|
255
|
37
|
|
|
|
|
95
|
$msg = $str->str;
|
256
|
|
|
|
|
|
|
|
257
|
|
|
|
|
|
|
# Another Carp workaround kludge.
|
258
|
37
|
|
|
|
|
125
|
$msg =~ s/ at .*\d\.at / at /;
|
259
|
|
|
|
|
|
|
|
260
|
37
|
|
|
|
|
125
|
$msg =~ s/__MESSAGE__/$original/;
|
261
|
37
|
|
|
|
|
109
|
$str->set_str($msg);
|
262
|
|
|
|
|
|
|
|
263
|
37
|
|
|
|
|
170
|
return $str;
|
264
|
|
|
|
|
|
|
}
|
265
|
|
|
|
|
|
|
|
266
|
|
|
|
|
|
|
#
|
267
|
|
|
|
|
|
|
# ->logconfess
|
268
|
|
|
|
|
|
|
#
|
269
|
|
|
|
|
|
|
# Confess fatal error
|
270
|
|
|
|
|
|
|
# Error is logged, and then we confess.
|
271
|
|
|
|
|
|
|
#
|
272
|
|
|
|
|
|
|
sub logconfess {
|
273
|
0
|
|
|
0
|
1
|
0
|
my $self = shift;
|
274
|
0
|
|
|
|
|
0
|
my ($str) = @_;
|
275
|
0
|
|
|
|
|
0
|
my $msg = $self->carpmess(0, $str, \&Carp::longmess);
|
276
|
0
|
|
|
|
|
0
|
$self->emit('error', 'critical', $msg);
|
277
|
0
|
|
|
|
|
0
|
die "$msg\n";
|
278
|
|
|
|
|
|
|
}
|
279
|
|
|
|
|
|
|
|
280
|
|
|
|
|
|
|
#
|
281
|
|
|
|
|
|
|
# ->logxcroak
|
282
|
|
|
|
|
|
|
#
|
283
|
|
|
|
|
|
|
# Fatal error, from the perspective of the caller.
|
284
|
|
|
|
|
|
|
# Error is logged, and then we confess.
|
285
|
|
|
|
|
|
|
#
|
286
|
|
|
|
|
|
|
sub logxcroak {
|
287
|
0
|
|
|
0
|
1
|
0
|
my $self = shift;
|
288
|
0
|
|
|
|
|
0
|
my ($offset, $str) = @_;
|
289
|
0
|
|
|
|
|
0
|
my $msg = $self->carpmess($offset, $str, \&Carp::shortmess);
|
290
|
0
|
|
|
|
|
0
|
$self->emit('error', 'critical', $msg);
|
291
|
0
|
|
|
|
|
0
|
die "$msg\n";
|
292
|
|
|
|
|
|
|
}
|
293
|
|
|
|
|
|
|
|
294
|
|
|
|
|
|
|
#
|
295
|
|
|
|
|
|
|
# ->logdie
|
296
|
|
|
|
|
|
|
#
|
297
|
|
|
|
|
|
|
# Fatal error
|
298
|
|
|
|
|
|
|
# Error is logged, and then we die.
|
299
|
|
|
|
|
|
|
#
|
300
|
|
|
|
|
|
|
sub logdie {
|
301
|
2
|
|
|
2
|
1
|
5
|
my $self = shift;
|
302
|
2
|
|
|
|
|
4
|
my ($str) = @_;
|
303
|
2
|
|
|
|
|
6
|
$self->emit('error', 'critical', $str);
|
304
|
2
|
|
|
|
|
8
|
die "$str\n";
|
305
|
|
|
|
|
|
|
}
|
306
|
|
|
|
|
|
|
|
307
|
|
|
|
|
|
|
#
|
308
|
|
|
|
|
|
|
# logerr
|
309
|
|
|
|
|
|
|
#
|
310
|
|
|
|
|
|
|
# Log error
|
311
|
|
|
|
|
|
|
#
|
312
|
|
|
|
|
|
|
sub logerr {
|
313
|
12
|
|
|
12
|
1
|
32
|
my $self = shift;
|
314
|
12
|
|
|
|
|
23
|
my ($str) = @_;
|
315
|
12
|
|
|
|
|
44
|
$self->emit('error', 'error', $str);
|
316
|
|
|
|
|
|
|
}
|
317
|
|
|
|
|
|
|
|
318
|
|
|
|
|
|
|
#
|
319
|
|
|
|
|
|
|
# ->logxcarp
|
320
|
|
|
|
|
|
|
#
|
321
|
|
|
|
|
|
|
# Log warning, from the perspective of the caller.
|
322
|
|
|
|
|
|
|
#
|
323
|
|
|
|
|
|
|
sub logxcarp {
|
324
|
0
|
|
|
0
|
1
|
0
|
my $self = shift;
|
325
|
0
|
|
|
|
|
0
|
my ($offset, $str) = @_;
|
326
|
0
|
|
|
|
|
0
|
my $msg = $self->carpmess($offset, $str, \&Carp::shortmess);
|
327
|
0
|
|
|
|
|
0
|
$self->emit('error', 'warning', $msg);
|
328
|
|
|
|
|
|
|
}
|
329
|
|
|
|
|
|
|
|
330
|
|
|
|
|
|
|
#
|
331
|
|
|
|
|
|
|
# logwarn
|
332
|
|
|
|
|
|
|
#
|
333
|
|
|
|
|
|
|
# Log warning
|
334
|
|
|
|
|
|
|
#
|
335
|
|
|
|
|
|
|
sub logwarn {
|
336
|
17
|
|
|
17
|
1
|
31
|
my $self = shift;
|
337
|
17
|
|
|
|
|
33
|
my ($str) = @_;
|
338
|
17
|
|
|
|
|
47
|
$self->emit('error', 'warning', $str);
|
339
|
|
|
|
|
|
|
}
|
340
|
|
|
|
|
|
|
|
341
|
|
|
|
|
|
|
#
|
342
|
|
|
|
|
|
|
# logsay
|
343
|
|
|
|
|
|
|
#
|
344
|
|
|
|
|
|
|
# Log message at the "notice" level.
|
345
|
|
|
|
|
|
|
#
|
346
|
|
|
|
|
|
|
sub logsay {
|
347
|
18
|
|
|
18
|
1
|
37
|
my $self = shift;
|
348
|
18
|
|
|
|
|
36
|
my ($str) = @_;
|
349
|
18
|
|
|
|
|
56
|
$self->emit('output', 'notice', $str);
|
350
|
|
|
|
|
|
|
}
|
351
|
|
|
|
|
|
|
|
352
|
|
|
|
|
|
|
#
|
353
|
|
|
|
|
|
|
# logwrite
|
354
|
|
|
|
|
|
|
#
|
355
|
|
|
|
|
|
|
# Emit the message to the specified channel
|
356
|
|
|
|
|
|
|
#
|
357
|
|
|
|
|
|
|
sub logwrite {
|
358
|
5
|
|
|
5
|
1
|
11
|
my $self = shift;
|
359
|
5
|
|
|
|
|
14
|
my ($chan, $prio, $level, $str) = @_;
|
360
|
5
|
|
|
|
|
19
|
$self->write($chan, $self->map_pri($prio, $level),
|
361
|
|
|
|
|
|
|
$self->prefix_msg($str));
|
362
|
|
|
|
|
|
|
}
|
363
|
|
|
|
|
|
|
|
364
|
|
|
|
|
|
|
1; # for require
|
365
|
|
|
|
|
|
|
__END__
|