aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/misc
diff options
context:
space:
mode:
authorRussell King <rmk+kernel@arm.linux.org.uk>2010-03-08 15:21:04 -0500
committerRussell King <rmk+kernel@arm.linux.org.uk>2010-03-08 15:21:04 -0500
commit988addf82e4c03739375279de73929580a2d4a6a (patch)
tree989ae1cd4e264bbad80c65f04480486246e7b9f3 /drivers/misc
parent004c1c7096659d352b83047a7593e91d8a30e3c5 (diff)
parent25cf84cf377c0aae5dbcf937ea89bc7893db5176 (diff)
Merge branch 'origin' into devel-stable
Conflicts: arch/arm/mach-mx2/devices.c arch/arm/mach-mx2/devices.h sound/soc/pxa/pxa-ssp.c
Diffstat (limited to 'drivers/misc')
-rw-r--r--drivers/misc/Kconfig9
-rw-r--r--drivers/misc/iwmc3200top/fw-download.c50
-rw-r--r--drivers/misc/iwmc3200top/iwmc3200top.h4
-rw-r--r--drivers/misc/iwmc3200top/log.h31
-rw-r--r--drivers/misc/iwmc3200top/main.c61
-rw-r--r--drivers/misc/lkdtm.c472
-rw-r--r--drivers/misc/sgi-xp/xpnet.c2
7 files changed, 473 insertions, 156 deletions
diff --git a/drivers/misc/Kconfig b/drivers/misc/Kconfig
index e3551d20464f..d16af6a423fb 100644
--- a/drivers/misc/Kconfig
+++ b/drivers/misc/Kconfig
@@ -212,6 +212,15 @@ config CS5535_MFGPT_DEFAULT_IRQ
212 want to use a different IRQ by default. This is here for 212 want to use a different IRQ by default. This is here for
213 architectures to set as necessary. 213 architectures to set as necessary.
214 214
215config CS5535_CLOCK_EVENT_SRC
216 tristate "CS5535/CS5536 high-res timer (MFGPT) events"
217 depends on GENERIC_TIME && GENERIC_CLOCKEVENTS && CS5535_MFGPT
218 help
219 This driver provides a clock event source based on the MFGPT
220 timer(s) in the CS5535 and CS5536 companion chips.
221 MFGPTs have a better resolution and max interval than the
222 generic PIT, and are suitable for use as high-res timers.
223
215config HP_ILO 224config HP_ILO
216 tristate "Channel interface driver for HP iLO/iLO2 processor" 225 tristate "Channel interface driver for HP iLO/iLO2 processor"
217 depends on PCI 226 depends on PCI
diff --git a/drivers/misc/iwmc3200top/fw-download.c b/drivers/misc/iwmc3200top/fw-download.c
index 50d431e469f5..9dbaeb574e63 100644
--- a/drivers/misc/iwmc3200top/fw-download.c
+++ b/drivers/misc/iwmc3200top/fw-download.c
@@ -43,15 +43,14 @@ static int iwmct_fw_parser_init(struct iwmct_priv *priv, const u8 *file,
43 struct iwmct_parser *parser = &priv->parser; 43 struct iwmct_parser *parser = &priv->parser;
44 struct iwmct_fw_hdr *fw_hdr = &parser->versions; 44 struct iwmct_fw_hdr *fw_hdr = &parser->versions;
45 45
46 LOG_INFOEX(priv, INIT, "-->\n"); 46 LOG_TRACE(priv, FW_DOWNLOAD, "-->\n");
47 47
48 LOG_INFO(priv, FW_DOWNLOAD, "file_size=%zd\n", file_size); 48 LOG_INFO(priv, FW_DOWNLOAD, "file_size=%zd\n", file_size);
49 49
50 parser->file = file; 50 parser->file = file;
51 parser->file_size = file_size; 51 parser->file_size = file_size;
52 parser->cur_pos = 0; 52 parser->cur_pos = 0;
53 parser->buf = NULL; 53 parser->entry_point = 0;
54
55 parser->buf = kzalloc(block_size, GFP_KERNEL); 54 parser->buf = kzalloc(block_size, GFP_KERNEL);
56 if (!parser->buf) { 55 if (!parser->buf) {
57 LOG_ERROR(priv, FW_DOWNLOAD, "kzalloc error\n"); 56 LOG_ERROR(priv, FW_DOWNLOAD, "kzalloc error\n");
@@ -70,7 +69,7 @@ static int iwmct_fw_parser_init(struct iwmct_priv *priv, const u8 *file,
70 69
71 parser->cur_pos += sizeof(struct iwmct_fw_hdr); 70 parser->cur_pos += sizeof(struct iwmct_fw_hdr);
72 71
73 LOG_INFOEX(priv, INIT, "<--\n"); 72 LOG_TRACE(priv, FW_DOWNLOAD, "<--\n");
74 return 0; 73 return 0;
75} 74}
76 75
@@ -113,7 +112,7 @@ static int iwmct_parse_next_section(struct iwmct_priv *priv, const u8 **p_sec,
113 struct iwmct_dbg *dbg = &priv->dbg; 112 struct iwmct_dbg *dbg = &priv->dbg;
114 struct iwmct_fw_sec_hdr *sec_hdr; 113 struct iwmct_fw_sec_hdr *sec_hdr;
115 114
116 LOG_INFOEX(priv, INIT, "-->\n"); 115 LOG_TRACE(priv, FW_DOWNLOAD, "-->\n");
117 116
118 while (parser->cur_pos + sizeof(struct iwmct_fw_sec_hdr) 117 while (parser->cur_pos + sizeof(struct iwmct_fw_sec_hdr)
119 <= parser->file_size) { 118 <= parser->file_size) {
@@ -152,7 +151,7 @@ static int iwmct_parse_next_section(struct iwmct_priv *priv, const u8 **p_sec,
152 "finished with section cur_pos=%zd\n", parser->cur_pos); 151 "finished with section cur_pos=%zd\n", parser->cur_pos);
153 } 152 }
154 153
155 LOG_INFOEX(priv, INIT, "<--\n"); 154 LOG_TRACE(priv, INIT, "<--\n");
156 return 0; 155 return 0;
157} 156}
158 157
@@ -167,7 +166,7 @@ static int iwmct_download_section(struct iwmct_priv *priv, const u8 *p_sec,
167 int ret = 0; 166 int ret = 0;
168 u32 cmd = 0; 167 u32 cmd = 0;
169 168
170 LOG_INFOEX(priv, INIT, "-->\n"); 169 LOG_TRACE(priv, FW_DOWNLOAD, "-->\n");
171 LOG_INFO(priv, FW_DOWNLOAD, "Download address 0x%x size 0x%zx\n", 170 LOG_INFO(priv, FW_DOWNLOAD, "Download address 0x%x size 0x%zx\n",
172 addr, sec_size); 171 addr, sec_size);
173 172
@@ -229,7 +228,7 @@ static int iwmct_download_section(struct iwmct_priv *priv, const u8 *p_sec,
229 hdr->cmd = cpu_to_le32(cmd); 228 hdr->cmd = cpu_to_le32(cmd);
230 /* send it down */ 229 /* send it down */
231 /* TODO: add more proper sending and error checking */ 230 /* TODO: add more proper sending and error checking */
232 ret = iwmct_tx(priv, 0, parser->buf, trans_size); 231 ret = iwmct_tx(priv, parser->buf, trans_size);
233 if (ret != 0) { 232 if (ret != 0) {
234 LOG_INFO(priv, FW_DOWNLOAD, 233 LOG_INFO(priv, FW_DOWNLOAD,
235 "iwmct_tx returned %d\n", ret); 234 "iwmct_tx returned %d\n", ret);
@@ -251,7 +250,7 @@ static int iwmct_download_section(struct iwmct_priv *priv, const u8 *p_sec,
251 if (sent < sec_size) 250 if (sent < sec_size)
252 ret = -EINVAL; 251 ret = -EINVAL;
253exit: 252exit:
254 LOG_INFOEX(priv, INIT, "<--\n"); 253 LOG_TRACE(priv, FW_DOWNLOAD, "<--\n");
255 return ret; 254 return ret;
256} 255}
257 256
@@ -262,7 +261,7 @@ static int iwmct_kick_fw(struct iwmct_priv *priv, bool jump)
262 int ret; 261 int ret;
263 u32 cmd; 262 u32 cmd;
264 263
265 LOG_INFOEX(priv, INIT, "-->\n"); 264 LOG_TRACE(priv, FW_DOWNLOAD, "-->\n");
266 265
267 memset(parser->buf, 0, parser->buf_size); 266 memset(parser->buf, 0, parser->buf_size);
268 cmd = IWMC_CMD_SIGNATURE << CMD_HDR_SIGNATURE_POS; 267 cmd = IWMC_CMD_SIGNATURE << CMD_HDR_SIGNATURE_POS;
@@ -281,11 +280,11 @@ static int iwmct_kick_fw(struct iwmct_priv *priv, bool jump)
281 LOG_HEXDUMP(FW_DOWNLOAD, parser->buf, sizeof(*hdr)); 280 LOG_HEXDUMP(FW_DOWNLOAD, parser->buf, sizeof(*hdr));
282 /* send it down */ 281 /* send it down */
283 /* TODO: add more proper sending and error checking */ 282 /* TODO: add more proper sending and error checking */
284 ret = iwmct_tx(priv, 0, parser->buf, IWMC_SDIO_BLK_SIZE); 283 ret = iwmct_tx(priv, parser->buf, IWMC_SDIO_BLK_SIZE);
285 if (ret) 284 if (ret)
286 LOG_INFO(priv, FW_DOWNLOAD, "iwmct_tx returned %d", ret); 285 LOG_INFO(priv, FW_DOWNLOAD, "iwmct_tx returned %d", ret);
287 286
288 LOG_INFOEX(priv, INIT, "<--\n"); 287 LOG_TRACE(priv, FW_DOWNLOAD, "<--\n");
289 return 0; 288 return 0;
290} 289}
291 290
@@ -298,8 +297,16 @@ int iwmct_fw_load(struct iwmct_priv *priv)
298 __le32 addr; 297 __le32 addr;
299 int ret; 298 int ret;
300 299
301 /* clear parser struct */ 300
302 memset(&priv->parser, 0, sizeof(struct iwmct_parser)); 301 LOG_INFO(priv, FW_DOWNLOAD, "barker download request 0x%x is:\n",
302 priv->barker);
303 LOG_INFO(priv, FW_DOWNLOAD, "******* Top FW %s requested ********\n",
304 (priv->barker & BARKER_DNLOAD_TOP_MSK) ? "was" : "not");
305 LOG_INFO(priv, FW_DOWNLOAD, "******* GPS FW %s requested ********\n",
306 (priv->barker & BARKER_DNLOAD_GPS_MSK) ? "was" : "not");
307 LOG_INFO(priv, FW_DOWNLOAD, "******* BT FW %s requested ********\n",
308 (priv->barker & BARKER_DNLOAD_BT_MSK) ? "was" : "not");
309
303 310
304 /* get the firmware */ 311 /* get the firmware */
305 ret = request_firmware(&raw, fw_name, &priv->func->dev); 312 ret = request_firmware(&raw, fw_name, &priv->func->dev);
@@ -317,6 +324,7 @@ int iwmct_fw_load(struct iwmct_priv *priv)
317 324
318 LOG_INFO(priv, FW_DOWNLOAD, "Read firmware '%s'\n", fw_name); 325 LOG_INFO(priv, FW_DOWNLOAD, "Read firmware '%s'\n", fw_name);
319 326
327 /* clear parser struct */
320 ret = iwmct_fw_parser_init(priv, raw->data, raw->size, priv->trans_len); 328 ret = iwmct_fw_parser_init(priv, raw->data, raw->size, priv->trans_len);
321 if (ret < 0) { 329 if (ret < 0) {
322 LOG_ERROR(priv, FW_DOWNLOAD, 330 LOG_ERROR(priv, FW_DOWNLOAD,
@@ -324,7 +332,6 @@ int iwmct_fw_load(struct iwmct_priv *priv)
324 goto exit; 332 goto exit;
325 } 333 }
326 334
327 /* checksum */
328 if (!iwmct_checksum(priv)) { 335 if (!iwmct_checksum(priv)) {
329 LOG_ERROR(priv, FW_DOWNLOAD, "checksum error\n"); 336 LOG_ERROR(priv, FW_DOWNLOAD, "checksum error\n");
330 ret = -EINVAL; 337 ret = -EINVAL;
@@ -333,23 +340,18 @@ int iwmct_fw_load(struct iwmct_priv *priv)
333 340
334 /* download firmware to device */ 341 /* download firmware to device */
335 while (iwmct_parse_next_section(priv, &pdata, &len, &addr)) { 342 while (iwmct_parse_next_section(priv, &pdata, &len, &addr)) {
336 if (iwmct_download_section(priv, pdata, len, addr)) { 343 ret = iwmct_download_section(priv, pdata, len, addr);
344 if (ret) {
337 LOG_ERROR(priv, FW_DOWNLOAD, 345 LOG_ERROR(priv, FW_DOWNLOAD,
338 "%s download section failed\n", fw_name); 346 "%s download section failed\n", fw_name);
339 ret = -EIO;
340 goto exit; 347 goto exit;
341 } 348 }
342 } 349 }
343 350
344 iwmct_kick_fw(priv, !!(priv->barker & BARKER_DNLOAD_JUMP_MSK)); 351 ret = iwmct_kick_fw(priv, !!(priv->barker & BARKER_DNLOAD_JUMP_MSK));
345 352
346exit: 353exit:
347 kfree(priv->parser.buf); 354 kfree(priv->parser.buf);
348 355 release_firmware(raw);
349 if (raw)
350 release_firmware(raw);
351
352 raw = NULL;
353
354 return ret; 356 return ret;
355} 357}
diff --git a/drivers/misc/iwmc3200top/iwmc3200top.h b/drivers/misc/iwmc3200top/iwmc3200top.h
index 43bd510e1872..740ff0738ea8 100644
--- a/drivers/misc/iwmc3200top/iwmc3200top.h
+++ b/drivers/misc/iwmc3200top/iwmc3200top.h
@@ -196,9 +196,7 @@ struct iwmct_priv {
196 struct list_head read_req_list; 196 struct list_head read_req_list;
197}; 197};
198 198
199extern int iwmct_tx(struct iwmct_priv *priv, unsigned int addr, 199extern int iwmct_tx(struct iwmct_priv *priv, void *src, int count);
200 void *src, int count);
201
202extern int iwmct_fw_load(struct iwmct_priv *priv); 200extern int iwmct_fw_load(struct iwmct_priv *priv);
203 201
204extern void iwmct_dbg_init_params(struct iwmct_priv *drv); 202extern void iwmct_dbg_init_params(struct iwmct_priv *drv);
diff --git a/drivers/misc/iwmc3200top/log.h b/drivers/misc/iwmc3200top/log.h
index aba8121f978c..4434bb16cea7 100644
--- a/drivers/misc/iwmc3200top/log.h
+++ b/drivers/misc/iwmc3200top/log.h
@@ -37,13 +37,26 @@
37#define LOG_SEV_INFO 3 37#define LOG_SEV_INFO 3
38#define LOG_SEV_INFOEX 4 38#define LOG_SEV_INFOEX 4
39 39
40#define LOG_SEV_FILTER_ALL \ 40/* Log levels not defined for FW */
41 (BIT(LOG_SEV_CRITICAL) | \ 41#define LOG_SEV_TRACE 5
42 BIT(LOG_SEV_ERROR) | \ 42#define LOG_SEV_DUMP 6
43 BIT(LOG_SEV_WARNING) | \ 43
44 BIT(LOG_SEV_INFO) | \ 44#define LOG_SEV_FW_FILTER_ALL \
45 (BIT(LOG_SEV_CRITICAL) | \
46 BIT(LOG_SEV_ERROR) | \
47 BIT(LOG_SEV_WARNING) | \
48 BIT(LOG_SEV_INFO) | \
45 BIT(LOG_SEV_INFOEX)) 49 BIT(LOG_SEV_INFOEX))
46 50
51#define LOG_SEV_FILTER_ALL \
52 (BIT(LOG_SEV_CRITICAL) | \
53 BIT(LOG_SEV_ERROR) | \
54 BIT(LOG_SEV_WARNING) | \
55 BIT(LOG_SEV_INFO) | \
56 BIT(LOG_SEV_INFOEX) | \
57 BIT(LOG_SEV_TRACE) | \
58 BIT(LOG_SEV_DUMP))
59
47/* log source */ 60/* log source */
48#define LOG_SRC_INIT 0 61#define LOG_SRC_INIT 0
49#define LOG_SRC_DEBUGFS 1 62#define LOG_SRC_DEBUGFS 1
@@ -104,16 +117,16 @@ do { \
104 __func__, __LINE__, ##args); \ 117 __func__, __LINE__, ##args); \
105} while (0) 118} while (0)
106 119
107#define LOG_INFOEX(priv, src, fmt, args...) \ 120#define LOG_TRACE(priv, src, fmt, args...) \
108do { \ 121do { \
109 if (iwmct_logdefs[LOG_SRC_ ## src] & BIT(LOG_SEV_INFOEX)) \ 122 if (iwmct_logdefs[LOG_SRC_ ## src] & BIT(LOG_SEV_TRACE)) \
110 dev_dbg(priv2dev(priv), "%s %d: " fmt, \ 123 dev_dbg(priv2dev(priv), "%s %d: " fmt, \
111 __func__, __LINE__, ##args); \ 124 __func__, __LINE__, ##args); \
112} while (0) 125} while (0)
113 126
114#define LOG_HEXDUMP(src, ptr, len) \ 127#define LOG_HEXDUMP(src, ptr, len) \
115do { \ 128do { \
116 if (iwmct_logdefs[LOG_SRC_ ## src] & BIT(LOG_SEV_INFOEX)) \ 129 if (iwmct_logdefs[LOG_SRC_ ## src] & BIT(LOG_SEV_DUMP)) \
117 print_hex_dump(KERN_DEBUG, "", DUMP_PREFIX_NONE, \ 130 print_hex_dump(KERN_DEBUG, "", DUMP_PREFIX_NONE, \
118 16, 1, ptr, len, false); \ 131 16, 1, ptr, len, false); \
119} while (0) 132} while (0)
@@ -142,7 +155,7 @@ ssize_t store_iwmct_log_level_fw(struct device *d,
142#define LOG_ERROR(priv, src, fmt, args...) 155#define LOG_ERROR(priv, src, fmt, args...)
143#define LOG_WARNING(priv, src, fmt, args...) 156#define LOG_WARNING(priv, src, fmt, args...)
144#define LOG_INFO(priv, src, fmt, args...) 157#define LOG_INFO(priv, src, fmt, args...)
145#define LOG_INFOEX(priv, src, fmt, args...) 158#define LOG_TRACE(priv, src, fmt, args...)
146#define LOG_HEXDUMP(src, ptr, len) 159#define LOG_HEXDUMP(src, ptr, len)
147 160
148static inline void iwmct_log_top_message(struct iwmct_priv *priv, 161static inline void iwmct_log_top_message(struct iwmct_priv *priv,
diff --git a/drivers/misc/iwmc3200top/main.c b/drivers/misc/iwmc3200top/main.c
index fafcaa481d74..3b7292a5cea9 100644
--- a/drivers/misc/iwmc3200top/main.c
+++ b/drivers/misc/iwmc3200top/main.c
@@ -49,6 +49,20 @@ MODULE_LICENSE("GPL");
49MODULE_AUTHOR(DRIVER_COPYRIGHT); 49MODULE_AUTHOR(DRIVER_COPYRIGHT);
50MODULE_FIRMWARE(FW_NAME(FW_API_VER)); 50MODULE_FIRMWARE(FW_NAME(FW_API_VER));
51 51
52
53static inline int __iwmct_tx(struct iwmct_priv *priv, void *src, int count)
54{
55 return sdio_memcpy_toio(priv->func, IWMC_SDIO_DATA_ADDR, src, count);
56
57}
58int iwmct_tx(struct iwmct_priv *priv, void *src, int count)
59{
60 int ret;
61 sdio_claim_host(priv->func);
62 ret = __iwmct_tx(priv, src, count);
63 sdio_release_host(priv->func);
64 return ret;
65}
52/* 66/*
53 * This workers main task is to wait for OP_OPR_ALIVE 67 * This workers main task is to wait for OP_OPR_ALIVE
54 * from TOP FW until ALIVE_MSG_TIMOUT timeout is elapsed. 68 * from TOP FW until ALIVE_MSG_TIMOUT timeout is elapsed.
@@ -66,7 +80,7 @@ static void iwmct_rescan_worker(struct work_struct *ws)
66 80
67 ret = bus_rescan_devices(priv->func->dev.bus); 81 ret = bus_rescan_devices(priv->func->dev.bus);
68 if (ret < 0) 82 if (ret < 0)
69 LOG_INFO(priv, FW_DOWNLOAD, "bus_rescan_devices FAILED!!!\n"); 83 LOG_INFO(priv, INIT, "bus_rescan_devices FAILED!!!\n");
70} 84}
71 85
72static void op_top_message(struct iwmct_priv *priv, struct top_msg *msg) 86static void op_top_message(struct iwmct_priv *priv, struct top_msg *msg)
@@ -137,7 +151,7 @@ int iwmct_send_hcmd(struct iwmct_priv *priv, u8 *cmd, u16 len)
137 int ret; 151 int ret;
138 u8 *buf; 152 u8 *buf;
139 153
140 LOG_INFOEX(priv, FW_MSG, "Sending hcmd:\n"); 154 LOG_TRACE(priv, FW_MSG, "Sending hcmd:\n");
141 155
142 /* add padding to 256 for IWMC */ 156 /* add padding to 256 for IWMC */
143 ((struct top_msg *)cmd)->hdr.flags |= CMD_FLAG_PADDING_256; 157 ((struct top_msg *)cmd)->hdr.flags |= CMD_FLAG_PADDING_256;
@@ -158,27 +172,12 @@ int iwmct_send_hcmd(struct iwmct_priv *priv, u8 *cmd, u16 len)
158 } 172 }
159 173
160 memcpy(buf, cmd, len); 174 memcpy(buf, cmd, len);
161 175 ret = iwmct_tx(priv, buf, FW_HCMD_BLOCK_SIZE);
162 sdio_claim_host(priv->func);
163 ret = sdio_memcpy_toio(priv->func, IWMC_SDIO_DATA_ADDR, buf,
164 FW_HCMD_BLOCK_SIZE);
165 sdio_release_host(priv->func);
166 176
167 kfree(buf); 177 kfree(buf);
168 return ret; 178 return ret;
169} 179}
170 180
171int iwmct_tx(struct iwmct_priv *priv, unsigned int addr,
172 void *src, int count)
173{
174 int ret;
175
176 sdio_claim_host(priv->func);
177 ret = sdio_memcpy_toio(priv->func, addr, src, count);
178 sdio_release_host(priv->func);
179
180 return ret;
181}
182 181
183static void iwmct_irq_read_worker(struct work_struct *ws) 182static void iwmct_irq_read_worker(struct work_struct *ws)
184{ 183{
@@ -192,7 +191,7 @@ static void iwmct_irq_read_worker(struct work_struct *ws)
192 191
193 priv = container_of(ws, struct iwmct_priv, isr_worker); 192 priv = container_of(ws, struct iwmct_priv, isr_worker);
194 193
195 LOG_INFO(priv, IRQ, "enter iwmct_irq_read_worker %p\n", ws); 194 LOG_TRACE(priv, IRQ, "enter iwmct_irq_read_worker %p\n", ws);
196 195
197 /* --------------------- Handshake with device -------------------- */ 196 /* --------------------- Handshake with device -------------------- */
198 sdio_claim_host(priv->func); 197 sdio_claim_host(priv->func);
@@ -273,8 +272,7 @@ static void iwmct_irq_read_worker(struct work_struct *ws)
273 272
274 if (barker & BARKER_DNLOAD_SYNC_MSK) { 273 if (barker & BARKER_DNLOAD_SYNC_MSK) {
275 /* Send the same barker back */ 274 /* Send the same barker back */
276 ret = sdio_memcpy_toio(priv->func, IWMC_SDIO_DATA_ADDR, 275 ret = __iwmct_tx(priv, buf, iosize);
277 buf, iosize);
278 if (ret) { 276 if (ret) {
279 LOG_ERROR(priv, IRQ, 277 LOG_ERROR(priv, IRQ,
280 "error %d echoing barker\n", ret); 278 "error %d echoing barker\n", ret);
@@ -292,15 +290,6 @@ static void iwmct_irq_read_worker(struct work_struct *ws)
292 290
293 sdio_release_host(priv->func); 291 sdio_release_host(priv->func);
294 292
295
296 LOG_INFO(priv, IRQ, "barker download request 0x%x is:\n", priv->barker);
297 LOG_INFO(priv, IRQ, "******* Top FW %s requested ********\n",
298 (priv->barker & BARKER_DNLOAD_TOP_MSK) ? "was" : "not");
299 LOG_INFO(priv, IRQ, "******* GPS FW %s requested ********\n",
300 (priv->barker & BARKER_DNLOAD_GPS_MSK) ? "was" : "not");
301 LOG_INFO(priv, IRQ, "******* BT FW %s requested ********\n",
302 (priv->barker & BARKER_DNLOAD_BT_MSK) ? "was" : "not");
303
304 if (priv->dbg.fw_download) 293 if (priv->dbg.fw_download)
305 iwmct_fw_load(priv); 294 iwmct_fw_load(priv);
306 else 295 else
@@ -312,7 +301,7 @@ exit_release:
312 sdio_release_host(priv->func); 301 sdio_release_host(priv->func);
313exit: 302exit:
314 kfree(buf); 303 kfree(buf);
315 LOG_INFO(priv, IRQ, "exit iwmct_irq_read_worker\n"); 304 LOG_TRACE(priv, IRQ, "exit iwmct_irq_read_worker\n");
316} 305}
317 306
318static void iwmct_irq(struct sdio_func *func) 307static void iwmct_irq(struct sdio_func *func)
@@ -325,12 +314,12 @@ static void iwmct_irq(struct sdio_func *func)
325 314
326 priv = sdio_get_drvdata(func); 315 priv = sdio_get_drvdata(func);
327 316
328 LOG_INFO(priv, IRQ, "enter iwmct_irq\n"); 317 LOG_TRACE(priv, IRQ, "enter iwmct_irq\n");
329 318
330 /* read the function's status register */ 319 /* read the function's status register */
331 val = sdio_readb(func, IWMC_SDIO_INTR_STATUS_ADDR, &ret); 320 val = sdio_readb(func, IWMC_SDIO_INTR_STATUS_ADDR, &ret);
332 321
333 LOG_INFO(priv, IRQ, "iir value = %d, ret=%d\n", val, ret); 322 LOG_TRACE(priv, IRQ, "iir value = %d, ret=%d\n", val, ret);
334 323
335 if (!val) { 324 if (!val) {
336 LOG_ERROR(priv, IRQ, "iir = 0, exiting ISR\n"); 325 LOG_ERROR(priv, IRQ, "iir = 0, exiting ISR\n");
@@ -372,7 +361,7 @@ static void iwmct_irq(struct sdio_func *func)
372 361
373 queue_work(priv->wq, &priv->isr_worker); 362 queue_work(priv->wq, &priv->isr_worker);
374 363
375 LOG_INFO(priv, IRQ, "exit iwmct_irq\n"); 364 LOG_TRACE(priv, IRQ, "exit iwmct_irq\n");
376 365
377 return; 366 return;
378 367
@@ -608,8 +597,6 @@ static void iwmct_remove(struct sdio_func *func)
608 struct iwmct_work_struct *read_req; 597 struct iwmct_work_struct *read_req;
609 struct iwmct_priv *priv = sdio_get_drvdata(func); 598 struct iwmct_priv *priv = sdio_get_drvdata(func);
610 599
611 priv = sdio_get_drvdata(func);
612
613 LOG_INFO(priv, INIT, "enter\n"); 600 LOG_INFO(priv, INIT, "enter\n");
614 601
615 sdio_claim_host(func); 602 sdio_claim_host(func);
@@ -660,7 +647,7 @@ static int __init iwmct_init(void)
660 647
661 /* Default log filter settings */ 648 /* Default log filter settings */
662 iwmct_log_set_filter(LOG_SRC_ALL, LOG_SEV_FILTER_RUNTIME); 649 iwmct_log_set_filter(LOG_SRC_ALL, LOG_SEV_FILTER_RUNTIME);
663 iwmct_log_set_filter(LOG_SRC_FW_MSG, LOG_SEV_FILTER_ALL); 650 iwmct_log_set_filter(LOG_SRC_FW_MSG, LOG_SEV_FW_FILTER_ALL);
664 iwmct_log_set_fw_filter(LOG_SRC_ALL, FW_LOG_SEV_FILTER_RUNTIME); 651 iwmct_log_set_fw_filter(LOG_SRC_ALL, FW_LOG_SEV_FILTER_RUNTIME);
665 652
666 rc = sdio_register_driver(&iwmct_driver); 653 rc = sdio_register_driver(&iwmct_driver);
diff --git a/drivers/misc/lkdtm.c b/drivers/misc/lkdtm.c
index 3648b23d5c92..4a0648301fdf 100644
--- a/drivers/misc/lkdtm.c
+++ b/drivers/misc/lkdtm.c
@@ -26,21 +26,9 @@
26 * It is adapted from the Linux Kernel Dump Test Tool by 26 * It is adapted from the Linux Kernel Dump Test Tool by
27 * Fernando Luis Vazquez Cao <http://lkdtt.sourceforge.net> 27 * Fernando Luis Vazquez Cao <http://lkdtt.sourceforge.net>
28 * 28 *
29 * Usage : insmod lkdtm.ko [recur_count={>0}] cpoint_name=<> cpoint_type=<> 29 * Debugfs support added by Simon Kagstrom <simon.kagstrom@netinsight.net>
30 * [cpoint_count={>0}]
31 * 30 *
32 * recur_count : Recursion level for the stack overflow test. Default is 10. 31 * See Documentation/fault-injection/provoke-crashes.txt for instructions
33 *
34 * cpoint_name : Crash point where the kernel is to be crashed. It can be
35 * one of INT_HARDWARE_ENTRY, INT_HW_IRQ_EN, INT_TASKLET_ENTRY,
36 * FS_DEVRW, MEM_SWAPOUT, TIMERADD, SCSI_DISPATCH_CMD,
37 * IDE_CORE_CP
38 *
39 * cpoint_type : Indicates the action to be taken on hitting the crash point.
40 * It can be one of PANIC, BUG, EXCEPTION, LOOP, OVERFLOW
41 *
42 * cpoint_count : Indicates the number of times the crash point is to be hit
43 * to trigger an action. The default is 10.
44 */ 32 */
45 33
46#include <linux/kernel.h> 34#include <linux/kernel.h>
@@ -53,13 +41,12 @@
53#include <linux/interrupt.h> 41#include <linux/interrupt.h>
54#include <linux/hrtimer.h> 42#include <linux/hrtimer.h>
55#include <scsi/scsi_cmnd.h> 43#include <scsi/scsi_cmnd.h>
44#include <linux/debugfs.h>
56 45
57#ifdef CONFIG_IDE 46#ifdef CONFIG_IDE
58#include <linux/ide.h> 47#include <linux/ide.h>
59#endif 48#endif
60 49
61#define NUM_CPOINTS 8
62#define NUM_CPOINT_TYPES 5
63#define DEFAULT_COUNT 10 50#define DEFAULT_COUNT 10
64#define REC_NUM_DEFAULT 10 51#define REC_NUM_DEFAULT 10
65 52
@@ -72,7 +59,8 @@ enum cname {
72 MEM_SWAPOUT, 59 MEM_SWAPOUT,
73 TIMERADD, 60 TIMERADD,
74 SCSI_DISPATCH_CMD, 61 SCSI_DISPATCH_CMD,
75 IDE_CORE_CP 62 IDE_CORE_CP,
63 DIRECT,
76}; 64};
77 65
78enum ctype { 66enum ctype {
@@ -81,7 +69,11 @@ enum ctype {
81 BUG, 69 BUG,
82 EXCEPTION, 70 EXCEPTION,
83 LOOP, 71 LOOP,
84 OVERFLOW 72 OVERFLOW,
73 CORRUPT_STACK,
74 UNALIGNED_LOAD_STORE_WRITE,
75 OVERWRITE_ALLOCATION,
76 WRITE_AFTER_FREE,
85}; 77};
86 78
87static char* cp_name[] = { 79static char* cp_name[] = {
@@ -92,7 +84,8 @@ static char* cp_name[] = {
92 "MEM_SWAPOUT", 84 "MEM_SWAPOUT",
93 "TIMERADD", 85 "TIMERADD",
94 "SCSI_DISPATCH_CMD", 86 "SCSI_DISPATCH_CMD",
95 "IDE_CORE_CP" 87 "IDE_CORE_CP",
88 "DIRECT",
96}; 89};
97 90
98static char* cp_type[] = { 91static char* cp_type[] = {
@@ -100,7 +93,11 @@ static char* cp_type[] = {
100 "BUG", 93 "BUG",
101 "EXCEPTION", 94 "EXCEPTION",
102 "LOOP", 95 "LOOP",
103 "OVERFLOW" 96 "OVERFLOW",
97 "CORRUPT_STACK",
98 "UNALIGNED_LOAD_STORE_WRITE",
99 "OVERWRITE_ALLOCATION",
100 "WRITE_AFTER_FREE",
104}; 101};
105 102
106static struct jprobe lkdtm; 103static struct jprobe lkdtm;
@@ -193,34 +190,66 @@ int jp_generic_ide_ioctl(ide_drive_t *drive, struct file *file,
193} 190}
194#endif 191#endif
195 192
193/* Return the crashpoint number or NONE if the name is invalid */
194static enum ctype parse_cp_type(const char *what, size_t count)
195{
196 int i;
197
198 for (i = 0; i < ARRAY_SIZE(cp_type); i++) {
199 if (!strcmp(what, cp_type[i]))
200 return i + 1;
201 }
202
203 return NONE;
204}
205
206static const char *cp_type_to_str(enum ctype type)
207{
208 if (type == NONE || type < 0 || type > ARRAY_SIZE(cp_type))
209 return "None";
210
211 return cp_type[type - 1];
212}
213
214static const char *cp_name_to_str(enum cname name)
215{
216 if (name == INVALID || name < 0 || name > ARRAY_SIZE(cp_name))
217 return "INVALID";
218
219 return cp_name[name - 1];
220}
221
222
196static int lkdtm_parse_commandline(void) 223static int lkdtm_parse_commandline(void)
197{ 224{
198 int i; 225 int i;
199 226
200 if (cpoint_name == NULL || cpoint_type == NULL || 227 if (cpoint_count < 1 || recur_count < 1)
201 cpoint_count < 1 || recur_count < 1)
202 return -EINVAL; 228 return -EINVAL;
203 229
204 for (i = 0; i < NUM_CPOINTS; ++i) { 230 count = cpoint_count;
231
232 /* No special parameters */
233 if (!cpoint_type && !cpoint_name)
234 return 0;
235
236 /* Neither or both of these need to be set */
237 if (!cpoint_type || !cpoint_name)
238 return -EINVAL;
239
240 cptype = parse_cp_type(cpoint_type, strlen(cpoint_type));
241 if (cptype == NONE)
242 return -EINVAL;
243
244 for (i = 0; i < ARRAY_SIZE(cp_name); i++) {
205 if (!strcmp(cpoint_name, cp_name[i])) { 245 if (!strcmp(cpoint_name, cp_name[i])) {
206 cpoint = i + 1; 246 cpoint = i + 1;
207 break; 247 return 0;
208 }
209 }
210
211 for (i = 0; i < NUM_CPOINT_TYPES; ++i) {
212 if (!strcmp(cpoint_type, cp_type[i])) {
213 cptype = i + 1;
214 break;
215 } 248 }
216 } 249 }
217 250
218 if (cpoint == INVALID || cptype == NONE) 251 /* Could not find a valid crash point */
219 return -EINVAL; 252 return -EINVAL;
220
221 count = cpoint_count;
222
223 return 0;
224} 253}
225 254
226static int recursive_loop(int a) 255static int recursive_loop(int a)
@@ -235,53 +264,92 @@ static int recursive_loop(int a)
235 return recursive_loop(a); 264 return recursive_loop(a);
236} 265}
237 266
238void lkdtm_handler(void) 267static void lkdtm_do_action(enum ctype which)
239{ 268{
240 printk(KERN_INFO "lkdtm : Crash point %s of type %s hit\n", 269 switch (which) {
241 cpoint_name, cpoint_type); 270 case PANIC:
242 --count; 271 panic("dumptest");
272 break;
273 case BUG:
274 BUG();
275 break;
276 case EXCEPTION:
277 *((int *) 0) = 0;
278 break;
279 case LOOP:
280 for (;;)
281 ;
282 break;
283 case OVERFLOW:
284 (void) recursive_loop(0);
285 break;
286 case CORRUPT_STACK: {
287 volatile u32 data[8];
288 volatile u32 *p = data;
289
290 p[12] = 0x12345678;
291 break;
292 }
293 case UNALIGNED_LOAD_STORE_WRITE: {
294 static u8 data[5] __attribute__((aligned(4))) = {1, 2,
295 3, 4, 5};
296 u32 *p;
297 u32 val = 0x12345678;
298
299 p = (u32 *)(data + 1);
300 if (*p == 0)
301 val = 0x87654321;
302 *p = val;
303 break;
304 }
305 case OVERWRITE_ALLOCATION: {
306 size_t len = 1020;
307 u32 *data = kmalloc(len, GFP_KERNEL);
308
309 data[1024 / sizeof(u32)] = 0x12345678;
310 kfree(data);
311 break;
312 }
313 case WRITE_AFTER_FREE: {
314 size_t len = 1024;
315 u32 *data = kmalloc(len, GFP_KERNEL);
316
317 kfree(data);
318 schedule();
319 memset(data, 0x78, len);
320 break;
321 }
322 case NONE:
323 default:
324 break;
325 }
326
327}
328
329static void lkdtm_handler(void)
330{
331 count--;
332 printk(KERN_INFO "lkdtm: Crash point %s of type %s hit, trigger in %d rounds\n",
333 cp_name_to_str(cpoint), cp_type_to_str(cptype), count);
243 334
244 if (count == 0) { 335 if (count == 0) {
245 switch (cptype) { 336 lkdtm_do_action(cptype);
246 case NONE:
247 break;
248 case PANIC:
249 printk(KERN_INFO "lkdtm : PANIC\n");
250 panic("dumptest");
251 break;
252 case BUG:
253 printk(KERN_INFO "lkdtm : BUG\n");
254 BUG();
255 break;
256 case EXCEPTION:
257 printk(KERN_INFO "lkdtm : EXCEPTION\n");
258 *((int *) 0) = 0;
259 break;
260 case LOOP:
261 printk(KERN_INFO "lkdtm : LOOP\n");
262 for (;;);
263 break;
264 case OVERFLOW:
265 printk(KERN_INFO "lkdtm : OVERFLOW\n");
266 (void) recursive_loop(0);
267 break;
268 default:
269 break;
270 }
271 count = cpoint_count; 337 count = cpoint_count;
272 } 338 }
273} 339}
274 340
275static int __init lkdtm_module_init(void) 341static int lkdtm_register_cpoint(enum cname which)
276{ 342{
277 int ret; 343 int ret;
278 344
279 if (lkdtm_parse_commandline() == -EINVAL) { 345 cpoint = INVALID;
280 printk(KERN_INFO "lkdtm : Invalid command\n"); 346 if (lkdtm.entry != NULL)
281 return -EINVAL; 347 unregister_jprobe(&lkdtm);
282 }
283 348
284 switch (cpoint) { 349 switch (which) {
350 case DIRECT:
351 lkdtm_do_action(cptype);
352 return 0;
285 case INT_HARDWARE_ENTRY: 353 case INT_HARDWARE_ENTRY:
286 lkdtm.kp.symbol_name = "do_IRQ"; 354 lkdtm.kp.symbol_name = "do_IRQ";
287 lkdtm.entry = (kprobe_opcode_t*) jp_do_irq; 355 lkdtm.entry = (kprobe_opcode_t*) jp_do_irq;
@@ -315,28 +383,268 @@ static int __init lkdtm_module_init(void)
315 lkdtm.kp.symbol_name = "generic_ide_ioctl"; 383 lkdtm.kp.symbol_name = "generic_ide_ioctl";
316 lkdtm.entry = (kprobe_opcode_t*) jp_generic_ide_ioctl; 384 lkdtm.entry = (kprobe_opcode_t*) jp_generic_ide_ioctl;
317#else 385#else
318 printk(KERN_INFO "lkdtm : Crash point not available\n"); 386 printk(KERN_INFO "lkdtm: Crash point not available\n");
387 return -EINVAL;
319#endif 388#endif
320 break; 389 break;
321 default: 390 default:
322 printk(KERN_INFO "lkdtm : Invalid Crash Point\n"); 391 printk(KERN_INFO "lkdtm: Invalid Crash Point\n");
323 break; 392 return -EINVAL;
324 } 393 }
325 394
395 cpoint = which;
326 if ((ret = register_jprobe(&lkdtm)) < 0) { 396 if ((ret = register_jprobe(&lkdtm)) < 0) {
327 printk(KERN_INFO "lkdtm : Couldn't register jprobe\n"); 397 printk(KERN_INFO "lkdtm: Couldn't register jprobe\n");
328 return ret; 398 cpoint = INVALID;
399 }
400
401 return ret;
402}
403
404static ssize_t do_register_entry(enum cname which, struct file *f,
405 const char __user *user_buf, size_t count, loff_t *off)
406{
407 char *buf;
408 int err;
409
410 if (count >= PAGE_SIZE)
411 return -EINVAL;
412
413 buf = (char *)__get_free_page(GFP_KERNEL);
414 if (!buf)
415 return -ENOMEM;
416 if (copy_from_user(buf, user_buf, count)) {
417 free_page((unsigned long) buf);
418 return -EFAULT;
419 }
420 /* NULL-terminate and remove enter */
421 buf[count] = '\0';
422 strim(buf);
423
424 cptype = parse_cp_type(buf, count);
425 free_page((unsigned long) buf);
426
427 if (cptype == NONE)
428 return -EINVAL;
429
430 err = lkdtm_register_cpoint(which);
431 if (err < 0)
432 return err;
433
434 *off += count;
435
436 return count;
437}
438
439/* Generic read callback that just prints out the available crash types */
440static ssize_t lkdtm_debugfs_read(struct file *f, char __user *user_buf,
441 size_t count, loff_t *off)
442{
443 char *buf;
444 int i, n, out;
445
446 buf = (char *)__get_free_page(GFP_KERNEL);
447
448 n = snprintf(buf, PAGE_SIZE, "Available crash types:\n");
449 for (i = 0; i < ARRAY_SIZE(cp_type); i++)
450 n += snprintf(buf + n, PAGE_SIZE - n, "%s\n", cp_type[i]);
451 buf[n] = '\0';
452
453 out = simple_read_from_buffer(user_buf, count, off,
454 buf, n);
455 free_page((unsigned long) buf);
456
457 return out;
458}
459
460static int lkdtm_debugfs_open(struct inode *inode, struct file *file)
461{
462 return 0;
463}
464
465
466static ssize_t int_hardware_entry(struct file *f, const char __user *buf,
467 size_t count, loff_t *off)
468{
469 return do_register_entry(INT_HARDWARE_ENTRY, f, buf, count, off);
470}
471
472static ssize_t int_hw_irq_en(struct file *f, const char __user *buf,
473 size_t count, loff_t *off)
474{
475 return do_register_entry(INT_HW_IRQ_EN, f, buf, count, off);
476}
477
478static ssize_t int_tasklet_entry(struct file *f, const char __user *buf,
479 size_t count, loff_t *off)
480{
481 return do_register_entry(INT_TASKLET_ENTRY, f, buf, count, off);
482}
483
484static ssize_t fs_devrw_entry(struct file *f, const char __user *buf,
485 size_t count, loff_t *off)
486{
487 return do_register_entry(FS_DEVRW, f, buf, count, off);
488}
489
490static ssize_t mem_swapout_entry(struct file *f, const char __user *buf,
491 size_t count, loff_t *off)
492{
493 return do_register_entry(MEM_SWAPOUT, f, buf, count, off);
494}
495
496static ssize_t timeradd_entry(struct file *f, const char __user *buf,
497 size_t count, loff_t *off)
498{
499 return do_register_entry(TIMERADD, f, buf, count, off);
500}
501
502static ssize_t scsi_dispatch_cmd_entry(struct file *f,
503 const char __user *buf, size_t count, loff_t *off)
504{
505 return do_register_entry(SCSI_DISPATCH_CMD, f, buf, count, off);
506}
507
508static ssize_t ide_core_cp_entry(struct file *f, const char __user *buf,
509 size_t count, loff_t *off)
510{
511 return do_register_entry(IDE_CORE_CP, f, buf, count, off);
512}
513
514/* Special entry to just crash directly. Available without KPROBEs */
515static ssize_t direct_entry(struct file *f, const char __user *user_buf,
516 size_t count, loff_t *off)
517{
518 enum ctype type;
519 char *buf;
520
521 if (count >= PAGE_SIZE)
522 return -EINVAL;
523 if (count < 1)
524 return -EINVAL;
525
526 buf = (char *)__get_free_page(GFP_KERNEL);
527 if (!buf)
528 return -ENOMEM;
529 if (copy_from_user(buf, user_buf, count)) {
530 free_page((unsigned long) buf);
531 return -EFAULT;
532 }
533 /* NULL-terminate and remove enter */
534 buf[count] = '\0';
535 strim(buf);
536
537 type = parse_cp_type(buf, count);
538 free_page((unsigned long) buf);
539 if (type == NONE)
540 return -EINVAL;
541
542 printk(KERN_INFO "lkdtm: Performing direct entry %s\n",
543 cp_type_to_str(type));
544 lkdtm_do_action(type);
545 *off += count;
546
547 return count;
548}
549
550struct crash_entry {
551 const char *name;
552 const struct file_operations fops;
553};
554
555static const struct crash_entry crash_entries[] = {
556 {"DIRECT", {.read = lkdtm_debugfs_read,
557 .open = lkdtm_debugfs_open,
558 .write = direct_entry} },
559 {"INT_HARDWARE_ENTRY", {.read = lkdtm_debugfs_read,
560 .open = lkdtm_debugfs_open,
561 .write = int_hardware_entry} },
562 {"INT_HW_IRQ_EN", {.read = lkdtm_debugfs_read,
563 .open = lkdtm_debugfs_open,
564 .write = int_hw_irq_en} },
565 {"INT_TASKLET_ENTRY", {.read = lkdtm_debugfs_read,
566 .open = lkdtm_debugfs_open,
567 .write = int_tasklet_entry} },
568 {"FS_DEVRW", {.read = lkdtm_debugfs_read,
569 .open = lkdtm_debugfs_open,
570 .write = fs_devrw_entry} },
571 {"MEM_SWAPOUT", {.read = lkdtm_debugfs_read,
572 .open = lkdtm_debugfs_open,
573 .write = mem_swapout_entry} },
574 {"TIMERADD", {.read = lkdtm_debugfs_read,
575 .open = lkdtm_debugfs_open,
576 .write = timeradd_entry} },
577 {"SCSI_DISPATCH_CMD", {.read = lkdtm_debugfs_read,
578 .open = lkdtm_debugfs_open,
579 .write = scsi_dispatch_cmd_entry} },
580 {"IDE_CORE_CP", {.read = lkdtm_debugfs_read,
581 .open = lkdtm_debugfs_open,
582 .write = ide_core_cp_entry} },
583};
584
585static struct dentry *lkdtm_debugfs_root;
586
587static int __init lkdtm_module_init(void)
588{
589 int ret = -EINVAL;
590 int n_debugfs_entries = 1; /* Assume only the direct entry */
591 int i;
592
593 /* Register debugfs interface */
594 lkdtm_debugfs_root = debugfs_create_dir("provoke-crash", NULL);
595 if (!lkdtm_debugfs_root) {
596 printk(KERN_ERR "lkdtm: creating root dir failed\n");
597 return -ENODEV;
598 }
599
600#ifdef CONFIG_KPROBES
601 n_debugfs_entries = ARRAY_SIZE(crash_entries);
602#endif
603
604 for (i = 0; i < n_debugfs_entries; i++) {
605 const struct crash_entry *cur = &crash_entries[i];
606 struct dentry *de;
607
608 de = debugfs_create_file(cur->name, 0644, lkdtm_debugfs_root,
609 NULL, &cur->fops);
610 if (de == NULL) {
611 printk(KERN_ERR "lkdtm: could not create %s\n",
612 cur->name);
613 goto out_err;
614 }
615 }
616
617 if (lkdtm_parse_commandline() == -EINVAL) {
618 printk(KERN_INFO "lkdtm: Invalid command\n");
619 goto out_err;
620 }
621
622 if (cpoint != INVALID && cptype != NONE) {
623 ret = lkdtm_register_cpoint(cpoint);
624 if (ret < 0) {
625 printk(KERN_INFO "lkdtm: Invalid crash point %d\n",
626 cpoint);
627 goto out_err;
628 }
629 printk(KERN_INFO "lkdtm: Crash point %s of type %s registered\n",
630 cpoint_name, cpoint_type);
631 } else {
632 printk(KERN_INFO "lkdtm: No crash points registered, enable through debugfs\n");
329 } 633 }
330 634
331 printk(KERN_INFO "lkdtm : Crash point %s of type %s registered\n",
332 cpoint_name, cpoint_type);
333 return 0; 635 return 0;
636
637out_err:
638 debugfs_remove_recursive(lkdtm_debugfs_root);
639 return ret;
334} 640}
335 641
336static void __exit lkdtm_module_exit(void) 642static void __exit lkdtm_module_exit(void)
337{ 643{
338 unregister_jprobe(&lkdtm); 644 debugfs_remove_recursive(lkdtm_debugfs_root);
339 printk(KERN_INFO "lkdtm : Crash point unregistered\n"); 645
646 unregister_jprobe(&lkdtm);
647 printk(KERN_INFO "lkdtm: Crash point unregistered\n");
340} 648}
341 649
342module_init(lkdtm_module_init); 650module_init(lkdtm_module_init);
diff --git a/drivers/misc/sgi-xp/xpnet.c b/drivers/misc/sgi-xp/xpnet.c
index 16f0abda1423..57b152f8d1b9 100644
--- a/drivers/misc/sgi-xp/xpnet.c
+++ b/drivers/misc/sgi-xp/xpnet.c
@@ -475,7 +475,7 @@ xpnet_dev_hard_start_xmit(struct sk_buff *skb, struct net_device *dev)
475 475
476 if (skb->data[0] == 0xff) { 476 if (skb->data[0] == 0xff) {
477 /* we are being asked to broadcast to all partitions */ 477 /* we are being asked to broadcast to all partitions */
478 for_each_bit(dest_partid, xpnet_broadcast_partitions, 478 for_each_set_bit(dest_partid, xpnet_broadcast_partitions,
479 xp_max_npartitions) { 479 xp_max_npartitions) {
480 480
481 xpnet_send(skb, queued_msg, start_addr, end_addr, 481 xpnet_send(skb, queued_msg, start_addr, end_addr,