printk.cc (4046:ef34b290091e) printk.cc (4429:74351f86f49a)
1/*
2 * Copyright (c) 2004-2005 The Regents of The University of Michigan
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are
7 * met: redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer;
9 * redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution;
12 * neither the name of the copyright holders nor the names of its
13 * contributors may be used to endorse or promote products derived from
14 * this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
17 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
18 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
19 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
20 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 *
28 * Authors: Nathan Binkert
29 * Ali Saidi
30 */
31
32#include <sys/types.h>
33#include <algorithm>
34
1/*
2 * Copyright (c) 2004-2005 The Regents of The University of Michigan
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are
7 * met: redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer;
9 * redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution;
12 * neither the name of the copyright holders nor the names of its
13 * contributors may be used to endorse or promote products derived from
14 * this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
17 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
18 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
19 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
20 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 *
28 * Authors: Nathan Binkert
29 * Ali Saidi
30 */
31
32#include <sys/types.h>
33#include <algorithm>
34
35#include "base/trace.hh"
36#include "arch/arguments.hh"
35#include "arch/arguments.hh"
36#include "base/trace.hh"
37#include "kern/linux/printk.hh"
37
38using namespace std;
39
40
41void
38
39using namespace std;
40
41
42void
42Printk(TheISA::Arguments args)
43Printk(stringstream &out, TheISA::Arguments args)
43{
44{
44 std::ostream &out = Trace::output();
45 char *p = (char *)args++;
46
45 char *p = (char *)args++;
46
47 ios::fmtflags saved_flags = out.flags();
48 char old_fill = out.fill();
49 int old_precision = out.precision();
50
51 while (*p) {
52 switch (*p) {
53 case '%': {
54 bool more = true;
55 bool islong = false;
56 bool leftjustify = false;
57 bool format = false;
58 bool zero = false;
59 int width = 0;
60 while (more && *++p) {
61 switch (*p) {
62 case 'l':
63 case 'L':
64 islong = true;
65 break;
66 case '-':
67 leftjustify = true;
68 break;
69 case '#':
70 format = true;
71 break;
72 case '0':
73 if (width)
74 width *= 10;
75 else
76 zero = true;
77 break;
78 default:
79 if (*p >= '1' && *p <= '9')
80 width = 10 * width + *p - '0';
81 else
82 more = false;
83 break;
84 }
85 }
86
87 bool hexnum = false;
88 bool octal = false;
89 bool sign = false;
90 switch (*p) {
91 case 'X':
92 case 'x':
93 hexnum = true;
94 break;
95 case 'O':
96 case 'o':
97 octal = true;
98 break;
99 case 'D':
100 case 'd':
101 sign = true;
102 break;
103 case 'P':
104 format = true;
105 case 'p':
106 hexnum = true;
107 break;
108 }
109
110 switch (*p) {
111 case 'D':
112 case 'd':
113 case 'U':
114 case 'u':
115 case 'X':
116 case 'x':
117 case 'O':
118 case 'o':
119 case 'P':
120 case 'p': {
121 if (hexnum)
122 out << hex;
123
124 if (octal)
125 out << oct;
126
127 if (format) {
128 if (!zero)
129 out.setf(ios::showbase);
130 else {
131 if (hexnum) {
132 out << "0x";
133 width -= 2;
134 } else if (octal) {
135 out << "0";
136 width -= 1;
137 }
138 }
139 }
140
141 if (zero)
142 out.fill('0');
143
144 if (width > 0)
145 out.width(width);
146
147 if (leftjustify && !zero)
148 out.setf(ios::left);
149
150 if (sign) {
151 if (islong)
152 out << (int64_t)args;
153 else
154 out << (int32_t)args;
155 } else {
156 if (islong)
157 out << (uint64_t)args;
158 else
159 out << (uint32_t)args;
160 }
161
162 if (zero)
163 out.fill(' ');
164
165 if (width > 0)
166 out.width(0);
167
168 out << dec;
169
170 ++args;
171 }
172 break;
173
174 case 's': {
175 char *s = (char *)args;
176 if (!s)
177 s = "<NULL>";
178
179 if (width > 0)
180 out.width(width);
181 if (leftjustify)
182 out.setf(ios::left);
183
184 out << s;
185 ++args;
186 }
187 break;
188 case 'C':
189 case 'c': {
190 uint64_t mask = (*p == 'C') ? 0xffL : 0x7fL;
191 uint64_t num;
192 int width;
193
194 if (islong) {
195 num = (uint64_t)args;
196 width = sizeof(uint64_t);
197 } else {
198 num = (uint32_t)args;
199 width = sizeof(uint32_t);
200 }
201
202 while (width-- > 0) {
203 char c = (char)(num & mask);
204 if (c)
205 out << c;
206 num >>= 8;
207 }
208
209 ++args;
210 }
211 break;
212 case 'b': {
213 uint64_t n = (uint64_t)args++;
214 char *s = (char *)args++;
215 out << s << ": " << n;
216 }
217 break;
218 case 'n':
219 case 'N': {
220 args += 2;
221#if 0
222 uint64_t n = (uint64_t)args++;
223 struct reg_values *rv = (struct reg_values *)args++;
224#endif
225 }
226 break;
227 case 'r':
228 case 'R': {
229 args += 2;
230#if 0
231 uint64_t n = (uint64_t)args++;
232 struct reg_desc *rd = (struct reg_desc *)args++;
233#endif
234 }
235 break;
236 case '%':
237 out << '%';
238 break;
239 }
240 ++p;
241 }
242 break;
243 case '\n':
244 out << endl;
245 ++p;
246 break;
247 case '\r':
248 ++p;
249 if (*p != '\n')
250 out << endl;
251 break;
252
253 default: {
254 size_t len = strcspn(p, "%\n\r\0");
255 out.write(p, len);
256 p += len;
257 }
258 }
259 }
260
47 while (*p) {
48 switch (*p) {
49 case '%': {
50 bool more = true;
51 bool islong = false;
52 bool leftjustify = false;
53 bool format = false;
54 bool zero = false;
55 int width = 0;
56 while (more && *++p) {
57 switch (*p) {
58 case 'l':
59 case 'L':
60 islong = true;
61 break;
62 case '-':
63 leftjustify = true;
64 break;
65 case '#':
66 format = true;
67 break;
68 case '0':
69 if (width)
70 width *= 10;
71 else
72 zero = true;
73 break;
74 default:
75 if (*p >= '1' && *p <= '9')
76 width = 10 * width + *p - '0';
77 else
78 more = false;
79 break;
80 }
81 }
82
83 bool hexnum = false;
84 bool octal = false;
85 bool sign = false;
86 switch (*p) {
87 case 'X':
88 case 'x':
89 hexnum = true;
90 break;
91 case 'O':
92 case 'o':
93 octal = true;
94 break;
95 case 'D':
96 case 'd':
97 sign = true;
98 break;
99 case 'P':
100 format = true;
101 case 'p':
102 hexnum = true;
103 break;
104 }
105
106 switch (*p) {
107 case 'D':
108 case 'd':
109 case 'U':
110 case 'u':
111 case 'X':
112 case 'x':
113 case 'O':
114 case 'o':
115 case 'P':
116 case 'p': {
117 if (hexnum)
118 out << hex;
119
120 if (octal)
121 out << oct;
122
123 if (format) {
124 if (!zero)
125 out.setf(ios::showbase);
126 else {
127 if (hexnum) {
128 out << "0x";
129 width -= 2;
130 } else if (octal) {
131 out << "0";
132 width -= 1;
133 }
134 }
135 }
136
137 if (zero)
138 out.fill('0');
139
140 if (width > 0)
141 out.width(width);
142
143 if (leftjustify && !zero)
144 out.setf(ios::left);
145
146 if (sign) {
147 if (islong)
148 out << (int64_t)args;
149 else
150 out << (int32_t)args;
151 } else {
152 if (islong)
153 out << (uint64_t)args;
154 else
155 out << (uint32_t)args;
156 }
157
158 if (zero)
159 out.fill(' ');
160
161 if (width > 0)
162 out.width(0);
163
164 out << dec;
165
166 ++args;
167 }
168 break;
169
170 case 's': {
171 char *s = (char *)args;
172 if (!s)
173 s = "<NULL>";
174
175 if (width > 0)
176 out.width(width);
177 if (leftjustify)
178 out.setf(ios::left);
179
180 out << s;
181 ++args;
182 }
183 break;
184 case 'C':
185 case 'c': {
186 uint64_t mask = (*p == 'C') ? 0xffL : 0x7fL;
187 uint64_t num;
188 int width;
189
190 if (islong) {
191 num = (uint64_t)args;
192 width = sizeof(uint64_t);
193 } else {
194 num = (uint32_t)args;
195 width = sizeof(uint32_t);
196 }
197
198 while (width-- > 0) {
199 char c = (char)(num & mask);
200 if (c)
201 out << c;
202 num >>= 8;
203 }
204
205 ++args;
206 }
207 break;
208 case 'b': {
209 uint64_t n = (uint64_t)args++;
210 char *s = (char *)args++;
211 out << s << ": " << n;
212 }
213 break;
214 case 'n':
215 case 'N': {
216 args += 2;
217#if 0
218 uint64_t n = (uint64_t)args++;
219 struct reg_values *rv = (struct reg_values *)args++;
220#endif
221 }
222 break;
223 case 'r':
224 case 'R': {
225 args += 2;
226#if 0
227 uint64_t n = (uint64_t)args++;
228 struct reg_desc *rd = (struct reg_desc *)args++;
229#endif
230 }
231 break;
232 case '%':
233 out << '%';
234 break;
235 }
236 ++p;
237 }
238 break;
239 case '\n':
240 out << endl;
241 ++p;
242 break;
243 case '\r':
244 ++p;
245 if (*p != '\n')
246 out << endl;
247 break;
248
249 default: {
250 size_t len = strcspn(p, "%\n\r\0");
251 out.write(p, len);
252 p += len;
253 }
254 }
255 }
256
261 out.flags(saved_flags);
262 out.fill(old_fill);
263 out.precision(old_precision);
264}
265
257}
258