1static int prism2_enable_aux_port(struct net_device *dev, int enable) 2{ 3 u16 val, reg; 4 int i, tries; 5 unsigned long flags; 6 struct hostap_interface *iface; 7 local_info_t *local; 8 9 iface = netdev_priv(dev); 10 local = iface->local; 11 12 if (local->no_pri) { 13 if (enable) { 14 PDEBUG(DEBUG_EXTRA2, "%s: no PRI f/w - assuming Aux " 15 "port is already enabled\n", dev->name); 16 } 17 return 0; 18 } 19 20 spin_lock_irqsave(&local->cmdlock, flags); 21 22 /* wait until busy bit is clear */ 23 tries = HFA384X_CMD_BUSY_TIMEOUT; 24 while (HFA384X_INW(HFA384X_CMD_OFF) & HFA384X_CMD_BUSY && tries > 0) { 25 tries--; 26 udelay(1); 27 } 28 if (tries == 0) { 29 reg = HFA384X_INW(HFA384X_CMD_OFF); 30 spin_unlock_irqrestore(&local->cmdlock, flags); 31 printk("%s: prism2_enable_aux_port - timeout - reg=0x%04x\n", 32 dev->name, reg); 33 return -ETIMEDOUT; 34 } 35 36 val = HFA384X_INW(HFA384X_CONTROL_OFF); 37 38 if (enable) { 39 HFA384X_OUTW(HFA384X_AUX_MAGIC0, HFA384X_PARAM0_OFF); 40 HFA384X_OUTW(HFA384X_AUX_MAGIC1, HFA384X_PARAM1_OFF); 41 HFA384X_OUTW(HFA384X_AUX_MAGIC2, HFA384X_PARAM2_OFF); 42 43 if ((val & HFA384X_AUX_PORT_MASK) != HFA384X_AUX_PORT_DISABLED) 44 printk("prism2_enable_aux_port: was not disabled!?\n"); 45 val &= ~HFA384X_AUX_PORT_MASK; 46 val |= HFA384X_AUX_PORT_ENABLE; 47 } else { 48 HFA384X_OUTW(0, HFA384X_PARAM0_OFF); 49 HFA384X_OUTW(0, HFA384X_PARAM1_OFF); 50 HFA384X_OUTW(0, HFA384X_PARAM2_OFF); 51 52 if ((val & HFA384X_AUX_PORT_MASK) != HFA384X_AUX_PORT_ENABLED) 53 printk("prism2_enable_aux_port: was not enabled!?\n"); 54 val &= ~HFA384X_AUX_PORT_MASK; 55 val |= HFA384X_AUX_PORT_DISABLE; 56 } 57 HFA384X_OUTW(val, HFA384X_CONTROL_OFF); 58 59 udelay(5); 60 61 i = 10000; 62 while (i > 0) { 63 val = HFA384X_INW(HFA384X_CONTROL_OFF); 64 val &= HFA384X_AUX_PORT_MASK; 65 66 if ((enable && val == HFA384X_AUX_PORT_ENABLED) || 67 (!enable && val == HFA384X_AUX_PORT_DISABLED)) 68 break; 69 70 udelay(10); 71 i--; 72 } 73 74 spin_unlock_irqrestore(&local->cmdlock, flags); 75 76 if (i == 0) { 77 printk("prism2_enable_aux_port(%d) timed out\n", 78 enable); 79 return -ETIMEDOUT; 80 } 81 82 return 0; 83} 84 85 86static int hfa384x_from_aux(struct net_device *dev, unsigned int addr, int len, 87 void *buf) 88{ 89 u16 page, offset; 90 if (addr & 1 || len & 1) 91 return -1; 92 93 page = addr >> 7; 94 offset = addr & 0x7f; 95 96 HFA384X_OUTW(page, HFA384X_AUXPAGE_OFF); 97 HFA384X_OUTW(offset, HFA384X_AUXOFFSET_OFF); 98 99 udelay(5); 100 101#ifdef PRISM2_PCI 102 { 103 __le16 *pos = (__le16 *) buf; 104 while (len > 0) { 105 *pos++ = HFA384X_INW_DATA(HFA384X_AUXDATA_OFF); 106 len -= 2; 107 } 108 } 109#else /* PRISM2_PCI */ 110 HFA384X_INSW(HFA384X_AUXDATA_OFF, buf, len / 2); 111#endif /* PRISM2_PCI */ 112 113 return 0; 114} 115 116 117static int hfa384x_to_aux(struct net_device *dev, unsigned int addr, int len, 118 void *buf) 119{ 120 u16 page, offset; 121 if (addr & 1 || len & 1) 122 return -1; 123 124 page = addr >> 7; 125 offset = addr & 0x7f; 126 127 HFA384X_OUTW(page, HFA384X_AUXPAGE_OFF); 128 HFA384X_OUTW(offset, HFA384X_AUXOFFSET_OFF); 129 130 udelay(5); 131 132#ifdef PRISM2_PCI 133 { 134 __le16 *pos = (__le16 *) buf; 135 while (len > 0) { 136 HFA384X_OUTW_DATA(*pos++, HFA384X_AUXDATA_OFF); 137 len -= 2; 138 } 139 } 140#else /* PRISM2_PCI */ 141 HFA384X_OUTSW(HFA384X_AUXDATA_OFF, buf, len / 2); 142#endif /* PRISM2_PCI */ 143 144 return 0; 145} 146 147 148static int prism2_pda_ok(u8 *buf) 149{ 150 __le16 *pda = (__le16 *) buf; 151 int pos; 152 u16 len, pdr; 153 154 if (buf[0] == 0xff && buf[1] == 0x00 && buf[2] == 0xff && 155 buf[3] == 0x00) 156 return 0; 157 158 pos = 0; 159 while (pos + 1 < PRISM2_PDA_SIZE / 2) { 160 len = le16_to_cpu(pda[pos]); 161 pdr = le16_to_cpu(pda[pos + 1]); 162 if (len == 0 || pos + len > PRISM2_PDA_SIZE / 2) 163 return 0; 164 165 if (pdr == 0x0000 && len == 2) { 166 /* PDA end found */ 167 return 1; 168 } 169 170 pos += len + 1; 171 } 172 173 return 0; 174} 175 176 177static int prism2_download_aux_dump(struct net_device *dev, 178 unsigned int addr, int len, u8 *buf) 179{ 180 int res; 181 182 prism2_enable_aux_port(dev, 1); 183 res = hfa384x_from_aux(dev, addr, len, buf); 184 prism2_enable_aux_port(dev, 0); 185 if (res) 186 return -1; 187 188 return 0; 189} 190 191 192static u8 * prism2_read_pda(struct net_device *dev) 193{ 194 u8 *buf; 195 int res, i, found = 0; 196#define NUM_PDA_ADDRS 4 197 unsigned int pda_addr[NUM_PDA_ADDRS] = { 198 0x7f0000 /* others than HFA3841 */, 199 0x3f0000 /* HFA3841 */, 200 0x390000 /* apparently used in older cards */, 201 0x7f0002 /* Intel PRO/Wireless 2011B (PCI) */, 202 }; 203 204 buf = kmalloc(PRISM2_PDA_SIZE, GFP_KERNEL); 205 if (buf == NULL) 206 return NULL; 207 208 /* Note: wlan card should be in initial state (just after init cmd) 209 * and no other operations should be performed concurrently. */ 210 211 prism2_enable_aux_port(dev, 1); 212 213 for (i = 0; i < NUM_PDA_ADDRS; i++) { 214 PDEBUG(DEBUG_EXTRA2, "%s: trying to read PDA from 0x%08x", 215 dev->name, pda_addr[i]); 216 res = hfa384x_from_aux(dev, pda_addr[i], PRISM2_PDA_SIZE, buf); 217 if (res) 218 continue; 219 if (res == 0 && prism2_pda_ok(buf)) { 220 PDEBUG2(DEBUG_EXTRA2, ": OK\n"); 221 found = 1; 222 break; 223 } else { 224 PDEBUG2(DEBUG_EXTRA2, ": failed\n"); 225 } 226 } 227 228 prism2_enable_aux_port(dev, 0); 229 230 if (!found) { 231 printk(KERN_DEBUG "%s: valid PDA not found\n", dev->name); 232 kfree(buf); 233 buf = NULL; 234 } 235 236 return buf; 237} 238 239 240static int prism2_download_volatile(local_info_t *local, 241 struct prism2_download_data *param) 242{ 243 struct net_device *dev = local->dev; 244 int ret = 0, i; 245 u16 param0, param1; 246 247 if (local->hw_downloading) { 248 printk(KERN_WARNING "%s: Already downloading - aborting new " 249 "request\n", dev->name); 250 return -1; 251 } 252 253 local->hw_downloading = 1; 254 if (local->pri_only) { 255 hfa384x_disable_interrupts(dev); 256 } else { 257 prism2_hw_shutdown(dev, 0); 258 259 if (prism2_hw_init(dev, 0)) { 260 printk(KERN_WARNING "%s: Could not initialize card for" 261 " download\n", dev->name); 262 ret = -1; 263 goto out; 264 } 265 } 266 267 if (prism2_enable_aux_port(dev, 1)) { 268 printk(KERN_WARNING "%s: Could not enable AUX port\n", 269 dev->name); 270 ret = -1; 271 goto out; 272 } 273 274 param0 = param->start_addr & 0xffff; 275 param1 = param->start_addr >> 16; 276 277 HFA384X_OUTW(0, HFA384X_PARAM2_OFF); 278 HFA384X_OUTW(param1, HFA384X_PARAM1_OFF); 279 if (hfa384x_cmd_wait(dev, HFA384X_CMDCODE_DOWNLOAD | 280 (HFA384X_PROGMODE_ENABLE_VOLATILE << 8), 281 param0)) { 282 printk(KERN_WARNING "%s: Download command execution failed\n", 283 dev->name); 284 ret = -1; 285 goto out; 286 } 287 288 for (i = 0; i < param->num_areas; i++) { 289 PDEBUG(DEBUG_EXTRA2, "%s: Writing %d bytes at 0x%08x\n", 290 dev->name, param->data[i].len, param->data[i].addr); 291 if (hfa384x_to_aux(dev, param->data[i].addr, 292 param->data[i].len, param->data[i].data)) { 293 printk(KERN_WARNING "%s: RAM download at 0x%08x " 294 "(len=%d) failed\n", dev->name, 295 param->data[i].addr, param->data[i].len); 296 ret = -1; 297 goto out; 298 } 299 } 300 301 HFA384X_OUTW(param1, HFA384X_PARAM1_OFF); 302 HFA384X_OUTW(0, HFA384X_PARAM2_OFF); 303 if (hfa384x_cmd_no_wait(dev, HFA384X_CMDCODE_DOWNLOAD | 304 (HFA384X_PROGMODE_DISABLE << 8), param0)) { 305 printk(KERN_WARNING "%s: Download command execution failed\n", 306 dev->name); 307 ret = -1; 308 goto out; 309 } 310 /* ProgMode disable causes the hardware to restart itself from the 311 * given starting address. Give hw some time and ACK command just in 312 * case restart did not happen. */ 313 mdelay(5); 314 HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_EVACK_OFF); 315 316 if (prism2_enable_aux_port(dev, 0)) { 317 printk(KERN_DEBUG "%s: Disabling AUX port failed\n", 318 dev->name); 319 /* continue anyway.. restart should have taken care of this */ 320 } 321 322 mdelay(5); 323 local->hw_downloading = 0; 324 if (prism2_hw_config(dev, 2)) { 325 printk(KERN_WARNING "%s: Card configuration after RAM " 326 "download failed\n", dev->name); 327 ret = -1; 328 goto out; 329 } 330 331 out: 332 local->hw_downloading = 0; 333 return ret; 334} 335 336 337static int prism2_enable_genesis(local_info_t *local, int hcr) 338{ 339 struct net_device *dev = local->dev; 340 u8 initseq[4] = { 0x00, 0xe1, 0xa1, 0xff }; 341 u8 readbuf[4]; 342 343 printk(KERN_DEBUG "%s: test Genesis mode with HCR 0x%02x\n", 344 dev->name, hcr); 345 local->func->cor_sreset(local); 346 hfa384x_to_aux(dev, 0x7e0038, sizeof(initseq), initseq); 347 local->func->genesis_reset(local, hcr); 348 349 /* Readback test */ 350 hfa384x_from_aux(dev, 0x7e0038, sizeof(readbuf), readbuf); 351 hfa384x_to_aux(dev, 0x7e0038, sizeof(initseq), initseq); 352 hfa384x_from_aux(dev, 0x7e0038, sizeof(readbuf), readbuf); 353 354 if (memcmp(initseq, readbuf, sizeof(initseq)) == 0) { 355 printk(KERN_DEBUG "Readback test succeeded, HCR 0x%02x\n", 356 hcr); 357 return 0; 358 } else { 359 printk(KERN_DEBUG "Readback test failed, HCR 0x%02x " 360 "write %02x %02x %02x %02x read %02x %02x %02x %02x\n", 361 hcr, initseq[0], initseq[1], initseq[2], initseq[3], 362 readbuf[0], readbuf[1], readbuf[2], readbuf[3]); 363 return 1; 364 } 365} 366 367 368static int prism2_get_ram_size(local_info_t *local) 369{ 370 int ret; 371 372 /* Try to enable genesis mode; 0x1F for x8 SRAM or 0x0F for x16 SRAM */ 373 if (prism2_enable_genesis(local, 0x1f) == 0) 374 ret = 8; 375 else if (prism2_enable_genesis(local, 0x0f) == 0) 376 ret = 16; 377 else 378 ret = -1; 379 380 /* Disable genesis mode */ 381 local->func->genesis_reset(local, ret == 16 ? 0x07 : 0x17); 382 383 return ret; 384} 385 386 387static int prism2_download_genesis(local_info_t *local, 388 struct prism2_download_data *param) 389{ 390 struct net_device *dev = local->dev; 391 int ram16 = 0, i; 392 int ret = 0; 393 394 if (local->hw_downloading) { 395 printk(KERN_WARNING "%s: Already downloading - aborting new " 396 "request\n", dev->name); 397 return -EBUSY; 398 } 399 400 if (!local->func->genesis_reset || !local->func->cor_sreset) { 401 printk(KERN_INFO "%s: Genesis mode downloading not supported " 402 "with this hwmodel\n", dev->name); 403 return -EOPNOTSUPP; 404 } 405 406 local->hw_downloading = 1; 407 408 if (prism2_enable_aux_port(dev, 1)) { 409 printk(KERN_DEBUG "%s: failed to enable AUX port\n", 410 dev->name); 411 ret = -EIO; 412 goto out; 413 } 414 415 if (local->sram_type == -1) { 416 /* 0x1F for x8 SRAM or 0x0F for x16 SRAM */ 417 if (prism2_enable_genesis(local, 0x1f) == 0) { 418 ram16 = 0; 419 PDEBUG(DEBUG_EXTRA2, "%s: Genesis mode OK using x8 " 420 "SRAM\n", dev->name); 421 } else if (prism2_enable_genesis(local, 0x0f) == 0) { 422 ram16 = 1; 423 PDEBUG(DEBUG_EXTRA2, "%s: Genesis mode OK using x16 " 424 "SRAM\n", dev->name); 425 } else { 426 printk(KERN_DEBUG "%s: Could not initiate genesis " 427 "mode\n", dev->name); 428 ret = -EIO; 429 goto out; 430 } 431 } else { 432 if (prism2_enable_genesis(local, local->sram_type == 8 ? 433 0x1f : 0x0f)) { 434 printk(KERN_DEBUG "%s: Failed to set Genesis " 435 "mode (sram_type=%d)\n", dev->name, 436 local->sram_type); 437 ret = -EIO; 438 goto out; 439 } 440 ram16 = local->sram_type != 8; 441 } 442 443 for (i = 0; i < param->num_areas; i++) { 444 PDEBUG(DEBUG_EXTRA2, "%s: Writing %d bytes at 0x%08x\n", 445 dev->name, param->data[i].len, param->data[i].addr); 446 if (hfa384x_to_aux(dev, param->data[i].addr, 447 param->data[i].len, param->data[i].data)) { 448 printk(KERN_WARNING "%s: RAM download at 0x%08x " 449 "(len=%d) failed\n", dev->name, 450 param->data[i].addr, param->data[i].len); 451 ret = -EIO; 452 goto out; 453 } 454 } 455 456 PDEBUG(DEBUG_EXTRA2, "Disable genesis mode\n"); 457 local->func->genesis_reset(local, ram16 ? 0x07 : 0x17); 458 if (prism2_enable_aux_port(dev, 0)) { 459 printk(KERN_DEBUG "%s: Failed to disable AUX port\n", 460 dev->name); 461 } 462 463 mdelay(5); 464 local->hw_downloading = 0; 465 466 PDEBUG(DEBUG_EXTRA2, "Trying to initialize card\n"); 467 /* 468 * Make sure the INIT command does not generate a command completion 469 * event by disabling interrupts. 470 */ 471 hfa384x_disable_interrupts(dev); 472 if (prism2_hw_init(dev, 1)) { 473 printk(KERN_DEBUG "%s: Initialization after genesis mode " 474 "download failed\n", dev->name); 475 ret = -EIO; 476 goto out; 477 } 478 479 PDEBUG(DEBUG_EXTRA2, "Card initialized - running PRI only\n"); 480 if (prism2_hw_init2(dev, 1)) { 481 printk(KERN_DEBUG "%s: Initialization(2) after genesis mode " 482 "download failed\n", dev->name); 483 ret = -EIO; 484 goto out; 485 } 486 487 out: 488 local->hw_downloading = 0; 489 return ret; 490} 491 492 493#ifdef PRISM2_NON_VOLATILE_DOWNLOAD 494/* Note! Non-volatile downloading functionality has not yet been tested 495 * thoroughly and it may corrupt flash image and effectively kill the card that 496 * is being updated. You have been warned. */ 497 498static inline int prism2_download_block(struct net_device *dev, 499 u32 addr, u8 *data, 500 u32 bufaddr, int rest_len) 501{ 502 u16 param0, param1; 503 int block_len; 504 505 block_len = rest_len < 4096 ? rest_len : 4096; 506 507 param0 = addr & 0xffff; 508 param1 = addr >> 16; 509 510 HFA384X_OUTW(block_len, HFA384X_PARAM2_OFF); 511 HFA384X_OUTW(param1, HFA384X_PARAM1_OFF); 512 513 if (hfa384x_cmd_wait(dev, HFA384X_CMDCODE_DOWNLOAD | 514 (HFA384X_PROGMODE_ENABLE_NON_VOLATILE << 8), 515 param0)) { 516 printk(KERN_WARNING "%s: Flash download command execution " 517 "failed\n", dev->name); 518 return -1; 519 } 520 521 if (hfa384x_to_aux(dev, bufaddr, block_len, data)) { 522 printk(KERN_WARNING "%s: flash download at 0x%08x " 523 "(len=%d) failed\n", dev->name, addr, block_len); 524 return -1; 525 } 526 527 HFA384X_OUTW(0, HFA384X_PARAM2_OFF); 528 HFA384X_OUTW(0, HFA384X_PARAM1_OFF); 529 if (hfa384x_cmd_wait(dev, HFA384X_CMDCODE_DOWNLOAD | 530 (HFA384X_PROGMODE_PROGRAM_NON_VOLATILE << 8), 531 0)) { 532 printk(KERN_WARNING "%s: Flash write command execution " 533 "failed\n", dev->name); 534 return -1; 535 } 536 537 return block_len; 538} 539 540 541static int prism2_download_nonvolatile(local_info_t *local, 542 struct prism2_download_data *dl) 543{ 544 struct net_device *dev = local->dev; 545 int ret = 0, i; 546 struct { 547 __le16 page; 548 __le16 offset; 549 __le16 len; 550 } dlbuffer; 551 u32 bufaddr; 552 553 if (local->hw_downloading) { 554 printk(KERN_WARNING "%s: Already downloading - aborting new " 555 "request\n", dev->name); 556 return -1; 557 } 558 559 ret = local->func->get_rid(dev, HFA384X_RID_DOWNLOADBUFFER, 560 &dlbuffer, 6, 0); 561 562 if (ret < 0) { 563 printk(KERN_WARNING "%s: Could not read download buffer " 564 "parameters\n", dev->name); 565 goto out; 566 } 567 568 printk(KERN_DEBUG "Download buffer: %d bytes at 0x%04x:0x%04x\n", 569 le16_to_cpu(dlbuffer.len), 570 le16_to_cpu(dlbuffer.page), 571 le16_to_cpu(dlbuffer.offset)); 572 573 bufaddr = (le16_to_cpu(dlbuffer.page) << 7) + le16_to_cpu(dlbuffer.offset); 574 575 local->hw_downloading = 1; 576 577 if (!local->pri_only) { 578 prism2_hw_shutdown(dev, 0); 579 580 if (prism2_hw_init(dev, 0)) { 581 printk(KERN_WARNING "%s: Could not initialize card for" 582 " download\n", dev->name); 583 ret = -1; 584 goto out; 585 } 586 } 587 588 hfa384x_disable_interrupts(dev); 589 590 if (prism2_enable_aux_port(dev, 1)) { 591 printk(KERN_WARNING "%s: Could not enable AUX port\n", 592 dev->name); 593 ret = -1; 594 goto out; 595 } 596 597 printk(KERN_DEBUG "%s: starting flash download\n", dev->name); 598 for (i = 0; i < dl->num_areas; i++) { 599 int rest_len = dl->data[i].len; 600 int data_off = 0; 601 602 while (rest_len > 0) { 603 int block_len; 604 605 block_len = prism2_download_block( 606 dev, dl->data[i].addr + data_off, 607 dl->data[i].data + data_off, bufaddr, 608 rest_len); 609 610 if (block_len < 0) { 611 ret = -1; 612 goto out; 613 } 614 615 rest_len -= block_len; 616 data_off += block_len; 617 } 618 } 619 620 HFA384X_OUTW(0, HFA384X_PARAM1_OFF); 621 HFA384X_OUTW(0, HFA384X_PARAM2_OFF); 622 if (hfa384x_cmd_wait(dev, HFA384X_CMDCODE_DOWNLOAD | 623 (HFA384X_PROGMODE_DISABLE << 8), 0)) { 624 printk(KERN_WARNING "%s: Download command execution failed\n", 625 dev->name); 626 ret = -1; 627 goto out; 628 } 629 630 if (prism2_enable_aux_port(dev, 0)) { 631 printk(KERN_DEBUG "%s: Disabling AUX port failed\n", 632 dev->name); 633 /* continue anyway.. restart should have taken care of this */ 634 } 635 636 mdelay(5); 637 638 local->func->hw_reset(dev); 639 local->hw_downloading = 0; 640 if (prism2_hw_config(dev, 2)) { 641 printk(KERN_WARNING "%s: Card configuration after flash " 642 "download failed\n", dev->name); 643 ret = -1; 644 } else { 645 printk(KERN_INFO "%s: Card initialized successfully after " 646 "flash download\n", dev->name); 647 } 648 649 out: 650 local->hw_downloading = 0; 651 return ret; 652} 653#endif /* PRISM2_NON_VOLATILE_DOWNLOAD */ 654 655 656static void prism2_download_free_data(struct prism2_download_data *dl) 657{ 658 int i; 659 660 if (dl == NULL) 661 return; 662 663 for (i = 0; i < dl->num_areas; i++) 664 kfree(dl->data[i].data); 665 kfree(dl); 666} 667 668 669static int prism2_download(local_info_t *local, 670 struct prism2_download_param *param) 671{ 672 int ret = 0; 673 int i; 674 u32 total_len = 0; 675 struct prism2_download_data *dl = NULL; 676 677 printk(KERN_DEBUG "prism2_download: dl_cmd=%d start_addr=0x%08x " 678 "num_areas=%d\n", 679 param->dl_cmd, param->start_addr, param->num_areas); 680 681 if (param->num_areas > 100) { 682 ret = -EINVAL; 683 goto out; 684 } 685 686 dl = kzalloc(sizeof(*dl) + param->num_areas * 687 sizeof(struct prism2_download_data_area), GFP_KERNEL); 688 if (dl == NULL) { 689 ret = -ENOMEM; 690 goto out; 691 } 692 dl->dl_cmd = param->dl_cmd; 693 dl->start_addr = param->start_addr; 694 dl->num_areas = param->num_areas; 695 for (i = 0; i < param->num_areas; i++) { 696 PDEBUG(DEBUG_EXTRA2, 697 " area %d: addr=0x%08x len=%d ptr=0x%p\n", 698 i, param->data[i].addr, param->data[i].len, 699 param->data[i].ptr); 700 701 dl->data[i].addr = param->data[i].addr; 702 dl->data[i].len = param->data[i].len; 703 704 total_len += param->data[i].len; 705 if (param->data[i].len > PRISM2_MAX_DOWNLOAD_AREA_LEN || 706 total_len > PRISM2_MAX_DOWNLOAD_LEN) { 707 ret = -E2BIG; 708 goto out; 709 } 710 711 dl->data[i].data = kmalloc(dl->data[i].len, GFP_KERNEL); 712 if (dl->data[i].data == NULL) { 713 ret = -ENOMEM; 714 goto out; 715 } 716 717 if (copy_from_user(dl->data[i].data, param->data[i].ptr, 718 param->data[i].len)) { 719 ret = -EFAULT; 720 goto out; 721 } 722 } 723 724 switch (param->dl_cmd) { 725 case PRISM2_DOWNLOAD_VOLATILE: 726 case PRISM2_DOWNLOAD_VOLATILE_PERSISTENT: 727 ret = prism2_download_volatile(local, dl); 728 break; 729 case PRISM2_DOWNLOAD_VOLATILE_GENESIS: 730 case PRISM2_DOWNLOAD_VOLATILE_GENESIS_PERSISTENT: 731 ret = prism2_download_genesis(local, dl); 732 break; 733 case PRISM2_DOWNLOAD_NON_VOLATILE: 734#ifdef PRISM2_NON_VOLATILE_DOWNLOAD 735 ret = prism2_download_nonvolatile(local, dl); 736#else /* PRISM2_NON_VOLATILE_DOWNLOAD */ 737 printk(KERN_INFO "%s: non-volatile downloading not enabled\n", 738 local->dev->name); 739 ret = -EOPNOTSUPP; 740#endif /* PRISM2_NON_VOLATILE_DOWNLOAD */ 741 break; 742 default: 743 printk(KERN_DEBUG "%s: unsupported download command %d\n", 744 local->dev->name, param->dl_cmd); 745 ret = -EINVAL; 746 break; 747 } 748 749 out: 750 if (ret == 0 && dl && 751 param->dl_cmd == PRISM2_DOWNLOAD_VOLATILE_GENESIS_PERSISTENT) { 752 prism2_download_free_data(local->dl_pri); 753 local->dl_pri = dl; 754 } else if (ret == 0 && dl && 755 param->dl_cmd == PRISM2_DOWNLOAD_VOLATILE_PERSISTENT) { 756 prism2_download_free_data(local->dl_sec); 757 local->dl_sec = dl; 758 } else 759 prism2_download_free_data(dl); 760 761 return ret; 762} 763