Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

at v3.5 2049 lines 63 kB view raw
1#include <linux/fs.h> 2 3#include "headers.h" 4/*************************************************************** 5* Function - bcm_char_open() 6* 7* Description - This is the "open" entry point for the character 8* driver. 9* 10* Parameters - inode: Pointer to the Inode structure of char device 11* filp : File pointer of the char device 12* 13* Returns - Zero(Success) 14****************************************************************/ 15 16static int bcm_char_open(struct inode *inode, struct file * filp) 17{ 18 PMINI_ADAPTER Adapter = NULL; 19 PPER_TARANG_DATA pTarang = NULL; 20 21 Adapter = GET_BCM_ADAPTER(gblpnetdev); 22 pTarang = kzalloc(sizeof(PER_TARANG_DATA), GFP_KERNEL); 23 if (!pTarang) 24 return -ENOMEM; 25 26 pTarang->Adapter = Adapter; 27 pTarang->RxCntrlMsgBitMask = 0xFFFFFFFF & ~(1 << 0xB); 28 29 down(&Adapter->RxAppControlQueuelock); 30 pTarang->next = Adapter->pTarangs; 31 Adapter->pTarangs = pTarang; 32 up(&Adapter->RxAppControlQueuelock); 33 34 /* Store the Adapter structure */ 35 filp->private_data = pTarang; 36 37 /* Start Queuing the control response Packets */ 38 atomic_inc(&Adapter->ApplicationRunning); 39 40 nonseekable_open(inode, filp); 41 return 0; 42} 43 44static int bcm_char_release(struct inode *inode, struct file *filp) 45{ 46 PPER_TARANG_DATA pTarang, tmp, ptmp; 47 PMINI_ADAPTER Adapter = NULL; 48 struct sk_buff *pkt, *npkt; 49 50 pTarang = (PPER_TARANG_DATA)filp->private_data; 51 52 if (pTarang == NULL) { 53 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, 54 "ptarang is null\n"); 55 return 0; 56 } 57 58 Adapter = pTarang->Adapter; 59 60 down(&Adapter->RxAppControlQueuelock); 61 62 tmp = Adapter->pTarangs; 63 for (ptmp = NULL; tmp; ptmp = tmp, tmp = tmp->next) { 64 if (tmp == pTarang) 65 break; 66 } 67 68 if (tmp) { 69 if (!ptmp) 70 Adapter->pTarangs = tmp->next; 71 else 72 ptmp->next = tmp->next; 73 } else { 74 up(&Adapter->RxAppControlQueuelock); 75 return 0; 76 } 77 78 pkt = pTarang->RxAppControlHead; 79 while (pkt) { 80 npkt = pkt->next; 81 kfree_skb(pkt); 82 pkt = npkt; 83 } 84 85 up(&Adapter->RxAppControlQueuelock); 86 87 /* Stop Queuing the control response Packets */ 88 atomic_dec(&Adapter->ApplicationRunning); 89 90 kfree(pTarang); 91 92 /* remove this filp from the asynchronously notified filp's */ 93 filp->private_data = NULL; 94 return 0; 95} 96 97static ssize_t bcm_char_read(struct file *filp, char __user *buf, size_t size, 98 loff_t *f_pos) 99{ 100 PPER_TARANG_DATA pTarang = filp->private_data; 101 PMINI_ADAPTER Adapter = pTarang->Adapter; 102 struct sk_buff *Packet = NULL; 103 ssize_t PktLen = 0; 104 int wait_ret_val = 0; 105 unsigned long ret = 0; 106 107 wait_ret_val = wait_event_interruptible(Adapter->process_read_wait_queue, 108 (pTarang->RxAppControlHead || 109 Adapter->device_removed)); 110 if ((wait_ret_val == -ERESTARTSYS)) { 111 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, 112 "Exiting as i've been asked to exit!!!\n"); 113 return wait_ret_val; 114 } 115 116 if (Adapter->device_removed) { 117 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, 118 "Device Removed... Killing the Apps...\n"); 119 return -ENODEV; 120 } 121 122 if (FALSE == Adapter->fw_download_done) 123 return -EACCES; 124 125 down(&Adapter->RxAppControlQueuelock); 126 127 if (pTarang->RxAppControlHead) { 128 Packet = pTarang->RxAppControlHead; 129 DEQUEUEPACKET(pTarang->RxAppControlHead, 130 pTarang->RxAppControlTail); 131 pTarang->AppCtrlQueueLen--; 132 } 133 134 up(&Adapter->RxAppControlQueuelock); 135 136 if (Packet) { 137 PktLen = Packet->len; 138 ret = copy_to_user(buf, Packet->data, 139 min_t(size_t, PktLen, size)); 140 if (ret) { 141 dev_kfree_skb(Packet); 142 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, 143 "Returning from copy to user failure\n"); 144 return -EFAULT; 145 } 146 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, 147 "Read %zd Bytes From Adapter packet = %p by process %d!\n", 148 PktLen, Packet, current->pid); 149 dev_kfree_skb(Packet); 150 } 151 152 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "<\n"); 153 return PktLen; 154} 155 156static long bcm_char_ioctl(struct file *filp, UINT cmd, ULONG arg) 157{ 158 PPER_TARANG_DATA pTarang = filp->private_data; 159 void __user *argp = (void __user *)arg; 160 PMINI_ADAPTER Adapter = pTarang->Adapter; 161 INT Status = STATUS_FAILURE; 162 int timeout = 0; 163 IOCTL_BUFFER IoBuffer; 164 int bytes; 165 166 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Parameters Passed to control IOCTL cmd=0x%X arg=0x%lX", cmd, arg); 167 168 if (_IOC_TYPE(cmd) != BCM_IOCTL) 169 return -EFAULT; 170 if (_IOC_DIR(cmd) & _IOC_READ) 171 Status = !access_ok(VERIFY_WRITE, argp, _IOC_SIZE(cmd)); 172 else if (_IOC_DIR(cmd) & _IOC_WRITE) 173 Status = !access_ok(VERIFY_READ, argp, _IOC_SIZE(cmd)); 174 else if (_IOC_NONE == (_IOC_DIR(cmd) & _IOC_NONE)) 175 Status = STATUS_SUCCESS; 176 177 if (Status) 178 return -EFAULT; 179 180 if (Adapter->device_removed) 181 return -EFAULT; 182 183 if (FALSE == Adapter->fw_download_done) { 184 switch (cmd) { 185 case IOCTL_MAC_ADDR_REQ: 186 case IOCTL_LINK_REQ: 187 case IOCTL_CM_REQUEST: 188 case IOCTL_SS_INFO_REQ: 189 case IOCTL_SEND_CONTROL_MESSAGE: 190 case IOCTL_IDLE_REQ: 191 case IOCTL_BCM_GPIO_SET_REQUEST: 192 case IOCTL_BCM_GPIO_STATUS_REQUEST: 193 return -EACCES; 194 default: 195 break; 196 } 197 } 198 199 Status = vendorextnIoctl(Adapter, cmd, arg); 200 if (Status != CONTINUE_COMMON_PATH) 201 return Status; 202 203 switch (cmd) { 204 /* Rdms for Swin Idle... */ 205 case IOCTL_BCM_REGISTER_READ_PRIVATE: { 206 RDM_BUFFER sRdmBuffer = {0}; 207 PCHAR temp_buff; 208 UINT Bufflen; 209 u16 temp_value; 210 211 /* Copy Ioctl Buffer structure */ 212 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 213 return -EFAULT; 214 215 if (IoBuffer.InputLength > sizeof(sRdmBuffer)) 216 return -EINVAL; 217 218 if (copy_from_user(&sRdmBuffer, IoBuffer.InputBuffer, IoBuffer.InputLength)) 219 return -EFAULT; 220 221 if (IoBuffer.OutputLength > USHRT_MAX || 222 IoBuffer.OutputLength == 0) { 223 return -EINVAL; 224 } 225 226 Bufflen = IoBuffer.OutputLength; 227 temp_value = 4 - (Bufflen % 4); 228 Bufflen += temp_value % 4; 229 230 temp_buff = kmalloc(Bufflen, GFP_KERNEL); 231 if (!temp_buff) 232 return -ENOMEM; 233 234 bytes = rdmalt(Adapter, (UINT)sRdmBuffer.Register, 235 (PUINT)temp_buff, Bufflen); 236 if (bytes > 0) { 237 Status = STATUS_SUCCESS; 238 if (copy_to_user(IoBuffer.OutputBuffer, temp_buff, bytes)) { 239 kfree(temp_buff); 240 return -EFAULT; 241 } 242 } else { 243 Status = bytes; 244 } 245 246 kfree(temp_buff); 247 break; 248 } 249 250 case IOCTL_BCM_REGISTER_WRITE_PRIVATE: { 251 WRM_BUFFER sWrmBuffer = {0}; 252 UINT uiTempVar = 0; 253 /* Copy Ioctl Buffer structure */ 254 255 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 256 return -EFAULT; 257 258 if (IoBuffer.InputLength > sizeof(sWrmBuffer)) 259 return -EINVAL; 260 261 /* Get WrmBuffer structure */ 262 if (copy_from_user(&sWrmBuffer, IoBuffer.InputBuffer, IoBuffer.InputLength)) 263 return -EFAULT; 264 265 uiTempVar = sWrmBuffer.Register & EEPROM_REJECT_MASK; 266 if (!((Adapter->pstargetparams->m_u32Customize) & VSG_MODE) && 267 ((uiTempVar == EEPROM_REJECT_REG_1) || 268 (uiTempVar == EEPROM_REJECT_REG_2) || 269 (uiTempVar == EEPROM_REJECT_REG_3) || 270 (uiTempVar == EEPROM_REJECT_REG_4))) { 271 272 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "EEPROM Access Denied, not in VSG Mode\n"); 273 return -EFAULT; 274 } 275 276 Status = wrmalt(Adapter, (UINT)sWrmBuffer.Register, 277 (PUINT)sWrmBuffer.Data, sizeof(ULONG)); 278 279 if (Status == STATUS_SUCCESS) { 280 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "WRM Done\n"); 281 } else { 282 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "WRM Failed\n"); 283 Status = -EFAULT; 284 } 285 break; 286 } 287 288 case IOCTL_BCM_REGISTER_READ: 289 case IOCTL_BCM_EEPROM_REGISTER_READ: { 290 RDM_BUFFER sRdmBuffer = {0}; 291 PCHAR temp_buff = NULL; 292 UINT uiTempVar = 0; 293 if ((Adapter->IdleMode == TRUE) || 294 (Adapter->bShutStatus == TRUE) || 295 (Adapter->bPreparingForLowPowerMode == TRUE)) { 296 297 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Device in Idle Mode, Blocking Rdms\n"); 298 return -EACCES; 299 } 300 301 /* Copy Ioctl Buffer structure */ 302 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 303 return -EFAULT; 304 305 if (IoBuffer.InputLength > sizeof(sRdmBuffer)) 306 return -EINVAL; 307 308 if (copy_from_user(&sRdmBuffer, IoBuffer.InputBuffer, IoBuffer.InputLength)) 309 return -EFAULT; 310 311 if (IoBuffer.OutputLength > USHRT_MAX || 312 IoBuffer.OutputLength == 0) { 313 return -EINVAL; 314 } 315 316 temp_buff = kmalloc(IoBuffer.OutputLength, GFP_KERNEL); 317 if (!temp_buff) 318 return STATUS_FAILURE; 319 320 if ((((ULONG)sRdmBuffer.Register & 0x0F000000) != 0x0F000000) || 321 ((ULONG)sRdmBuffer.Register & 0x3)) { 322 323 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "RDM Done On invalid Address : %x Access Denied.\n", 324 (int)sRdmBuffer.Register); 325 326 kfree(temp_buff); 327 return -EINVAL; 328 } 329 330 uiTempVar = sRdmBuffer.Register & EEPROM_REJECT_MASK; 331 bytes = rdmaltWithLock(Adapter, (UINT)sRdmBuffer.Register, (PUINT)temp_buff, IoBuffer.OutputLength); 332 333 if (bytes > 0) { 334 Status = STATUS_SUCCESS; 335 if (copy_to_user(IoBuffer.OutputBuffer, temp_buff, bytes)) { 336 kfree(temp_buff); 337 return -EFAULT; 338 } 339 } else { 340 Status = bytes; 341 } 342 343 kfree(temp_buff); 344 break; 345 } 346 case IOCTL_BCM_REGISTER_WRITE: 347 case IOCTL_BCM_EEPROM_REGISTER_WRITE: { 348 WRM_BUFFER sWrmBuffer = {0}; 349 UINT uiTempVar = 0; 350 if ((Adapter->IdleMode == TRUE) || 351 (Adapter->bShutStatus == TRUE) || 352 (Adapter->bPreparingForLowPowerMode == TRUE)) { 353 354 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Device in Idle Mode, Blocking Wrms\n"); 355 return -EACCES; 356 } 357 358 /* Copy Ioctl Buffer structure */ 359 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 360 return -EFAULT; 361 362 if (IoBuffer.InputLength > sizeof(sWrmBuffer)) 363 return -EINVAL; 364 365 /* Get WrmBuffer structure */ 366 if (copy_from_user(&sWrmBuffer, IoBuffer.InputBuffer, IoBuffer.InputLength)) 367 return -EFAULT; 368 369 if ((((ULONG)sWrmBuffer.Register & 0x0F000000) != 0x0F000000) || 370 ((ULONG)sWrmBuffer.Register & 0x3)) { 371 372 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "WRM Done On invalid Address : %x Access Denied.\n", (int)sWrmBuffer.Register); 373 return -EINVAL; 374 } 375 376 uiTempVar = sWrmBuffer.Register & EEPROM_REJECT_MASK; 377 if (!((Adapter->pstargetparams->m_u32Customize) & VSG_MODE) && 378 ((uiTempVar == EEPROM_REJECT_REG_1) || 379 (uiTempVar == EEPROM_REJECT_REG_2) || 380 (uiTempVar == EEPROM_REJECT_REG_3) || 381 (uiTempVar == EEPROM_REJECT_REG_4)) && 382 (cmd == IOCTL_BCM_REGISTER_WRITE)) { 383 384 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "EEPROM Access Denied, not in VSG Mode\n"); 385 return -EFAULT; 386 } 387 388 Status = wrmaltWithLock(Adapter, (UINT)sWrmBuffer.Register, 389 (PUINT)sWrmBuffer.Data, sWrmBuffer.Length); 390 391 if (Status == STATUS_SUCCESS) { 392 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, OSAL_DBG, DBG_LVL_ALL, "WRM Done\n"); 393 } else { 394 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "WRM Failed\n"); 395 Status = -EFAULT; 396 } 397 break; 398 } 399 case IOCTL_BCM_GPIO_SET_REQUEST: { 400 UCHAR ucResetValue[4]; 401 UINT value = 0; 402 UINT uiBit = 0; 403 UINT uiOperation = 0; 404 405 GPIO_INFO gpio_info = {0}; 406 if ((Adapter->IdleMode == TRUE) || 407 (Adapter->bShutStatus == TRUE) || 408 (Adapter->bPreparingForLowPowerMode == TRUE)) { 409 410 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "GPIO Can't be set/clear in Low power Mode"); 411 return -EACCES; 412 } 413 414 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 415 return -EFAULT; 416 417 if (IoBuffer.InputLength > sizeof(gpio_info)) 418 return -EINVAL; 419 420 if (copy_from_user(&gpio_info, IoBuffer.InputBuffer, IoBuffer.InputLength)) 421 return -EFAULT; 422 423 uiBit = gpio_info.uiGpioNumber; 424 uiOperation = gpio_info.uiGpioValue; 425 value = (1<<uiBit); 426 427 if (IsReqGpioIsLedInNVM(Adapter, value) == FALSE) { 428 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Sorry, Requested GPIO<0x%X> is not correspond to LED !!!", value); 429 Status = -EINVAL; 430 break; 431 } 432 433 /* Set - setting 1 */ 434 if (uiOperation) { 435 /* Set the gpio output register */ 436 Status = wrmaltWithLock(Adapter, BCM_GPIO_OUTPUT_SET_REG, (PUINT)(&value), sizeof(UINT)); 437 438 if (Status == STATUS_SUCCESS) { 439 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Set the GPIO bit\n"); 440 } else { 441 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Failed to set the %dth GPIO\n", uiBit); 442 break; 443 } 444 } else { 445 /* Set the gpio output register */ 446 Status = wrmaltWithLock(Adapter, BCM_GPIO_OUTPUT_CLR_REG, (PUINT)(&value), sizeof(UINT)); 447 448 if (Status == STATUS_SUCCESS) { 449 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Set the GPIO bit\n"); 450 } else { 451 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Failed to clear the %dth GPIO\n", uiBit); 452 break; 453 } 454 } 455 456 bytes = rdmaltWithLock(Adapter, (UINT)GPIO_MODE_REGISTER, (PUINT)ucResetValue, sizeof(UINT)); 457 if (bytes < 0) { 458 Status = bytes; 459 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, 460 "GPIO_MODE_REGISTER read failed"); 461 break; 462 } else { 463 Status = STATUS_SUCCESS; 464 } 465 466 /* Set the gpio mode register to output */ 467 *(UINT *)ucResetValue |= (1<<uiBit); 468 Status = wrmaltWithLock(Adapter, GPIO_MODE_REGISTER, 469 (PUINT)ucResetValue, sizeof(UINT)); 470 471 if (Status == STATUS_SUCCESS) { 472 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Set the GPIO to output Mode\n"); 473 } else { 474 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Failed to put GPIO in Output Mode\n"); 475 break; 476 } 477 } 478 break; 479 480 case BCM_LED_THREAD_STATE_CHANGE_REQ: { 481 USER_THREAD_REQ threadReq = {0}; 482 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "User made LED thread InActive"); 483 484 if ((Adapter->IdleMode == TRUE) || 485 (Adapter->bShutStatus == TRUE) || 486 (Adapter->bPreparingForLowPowerMode == TRUE)) { 487 488 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "GPIO Can't be set/clear in Low power Mode"); 489 Status = -EACCES; 490 break; 491 } 492 493 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 494 return -EFAULT; 495 496 if (IoBuffer.InputLength > sizeof(threadReq)) 497 return -EINVAL; 498 499 if (copy_from_user(&threadReq, IoBuffer.InputBuffer, IoBuffer.InputLength)) 500 return -EFAULT; 501 502 /* if LED thread is running(Actively or Inactively) set it state to make inactive */ 503 if (Adapter->LEDInfo.led_thread_running) { 504 if (threadReq.ThreadState == LED_THREAD_ACTIVATION_REQ) { 505 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Activating thread req"); 506 Adapter->DriverState = LED_THREAD_ACTIVE; 507 } else { 508 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "DeActivating Thread req....."); 509 Adapter->DriverState = LED_THREAD_INACTIVE; 510 } 511 512 /* signal thread. */ 513 wake_up(&Adapter->LEDInfo.notify_led_event); 514 } 515 } 516 break; 517 518 case IOCTL_BCM_GPIO_STATUS_REQUEST: { 519 ULONG uiBit = 0; 520 UCHAR ucRead[4]; 521 GPIO_INFO gpio_info = {0}; 522 523 if ((Adapter->IdleMode == TRUE) || 524 (Adapter->bShutStatus == TRUE) || 525 (Adapter->bPreparingForLowPowerMode == TRUE)) 526 return -EACCES; 527 528 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 529 return -EFAULT; 530 531 if (IoBuffer.InputLength > sizeof(gpio_info)) 532 return -EINVAL; 533 534 if (copy_from_user(&gpio_info, IoBuffer.InputBuffer, IoBuffer.InputLength)) 535 return -EFAULT; 536 537 uiBit = gpio_info.uiGpioNumber; 538 539 /* Set the gpio output register */ 540 bytes = rdmaltWithLock(Adapter, (UINT)GPIO_PIN_STATE_REGISTER, 541 (PUINT)ucRead, sizeof(UINT)); 542 543 if (bytes < 0) { 544 Status = bytes; 545 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "RDM Failed\n"); 546 return Status; 547 } else { 548 Status = STATUS_SUCCESS; 549 } 550 } 551 break; 552 553 case IOCTL_BCM_GPIO_MULTI_REQUEST: { 554 UCHAR ucResetValue[4]; 555 GPIO_MULTI_INFO gpio_multi_info[MAX_IDX]; 556 PGPIO_MULTI_INFO pgpio_multi_info = (PGPIO_MULTI_INFO)gpio_multi_info; 557 558 memset(pgpio_multi_info, 0, MAX_IDX * sizeof(GPIO_MULTI_INFO)); 559 560 if ((Adapter->IdleMode == TRUE) || 561 (Adapter->bShutStatus == TRUE) || 562 (Adapter->bPreparingForLowPowerMode == TRUE)) 563 return -EINVAL; 564 565 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 566 return -EFAULT; 567 568 if (IoBuffer.InputLength > sizeof(gpio_multi_info)) 569 return -EINVAL; 570 571 if (copy_from_user(&gpio_multi_info, IoBuffer.InputBuffer, IoBuffer.InputLength)) 572 return -EFAULT; 573 574 if (IsReqGpioIsLedInNVM(Adapter, pgpio_multi_info[WIMAX_IDX].uiGPIOMask) == FALSE) { 575 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, 576 "Sorry, Requested GPIO<0x%X> is not correspond to NVM LED bit map<0x%X>!!!", 577 pgpio_multi_info[WIMAX_IDX].uiGPIOMask, Adapter->gpioBitMap); 578 Status = -EINVAL; 579 break; 580 } 581 582 /* Set the gpio output register */ 583 if ((pgpio_multi_info[WIMAX_IDX].uiGPIOMask) & 584 (pgpio_multi_info[WIMAX_IDX].uiGPIOCommand)) { 585 /* Set 1's in GPIO OUTPUT REGISTER */ 586 *(UINT *)ucResetValue = pgpio_multi_info[WIMAX_IDX].uiGPIOMask & 587 pgpio_multi_info[WIMAX_IDX].uiGPIOCommand & 588 pgpio_multi_info[WIMAX_IDX].uiGPIOValue; 589 590 if (*(UINT *) ucResetValue) 591 Status = wrmaltWithLock(Adapter, BCM_GPIO_OUTPUT_SET_REG, 592 (PUINT)ucResetValue, sizeof(ULONG)); 593 594 if (Status != STATUS_SUCCESS) { 595 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "WRM to BCM_GPIO_OUTPUT_SET_REG Failed."); 596 return Status; 597 } 598 599 /* Clear to 0's in GPIO OUTPUT REGISTER */ 600 *(UINT *)ucResetValue = (pgpio_multi_info[WIMAX_IDX].uiGPIOMask & 601 pgpio_multi_info[WIMAX_IDX].uiGPIOCommand & 602 (~(pgpio_multi_info[WIMAX_IDX].uiGPIOValue))); 603 604 if (*(UINT *) ucResetValue) 605 Status = wrmaltWithLock(Adapter, BCM_GPIO_OUTPUT_CLR_REG, (PUINT)ucResetValue, sizeof(ULONG)); 606 607 if (Status != STATUS_SUCCESS) { 608 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "WRM to BCM_GPIO_OUTPUT_CLR_REG Failed."); 609 return Status; 610 } 611 } 612 613 if (pgpio_multi_info[WIMAX_IDX].uiGPIOMask) { 614 bytes = rdmaltWithLock(Adapter, (UINT)GPIO_PIN_STATE_REGISTER, (PUINT)ucResetValue, sizeof(UINT)); 615 616 if (bytes < 0) { 617 Status = bytes; 618 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "RDM to GPIO_PIN_STATE_REGISTER Failed."); 619 return Status; 620 } else { 621 Status = STATUS_SUCCESS; 622 } 623 624 pgpio_multi_info[WIMAX_IDX].uiGPIOValue = (*(UINT *)ucResetValue & 625 pgpio_multi_info[WIMAX_IDX].uiGPIOMask); 626 } 627 628 Status = copy_to_user(IoBuffer.OutputBuffer, &gpio_multi_info, IoBuffer.OutputLength); 629 if (Status) { 630 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, 631 "Failed while copying Content to IOBufer for user space err:%d", Status); 632 return -EFAULT; 633 } 634 } 635 break; 636 637 case IOCTL_BCM_GPIO_MODE_REQUEST: { 638 UCHAR ucResetValue[4]; 639 GPIO_MULTI_MODE gpio_multi_mode[MAX_IDX]; 640 PGPIO_MULTI_MODE pgpio_multi_mode = (PGPIO_MULTI_MODE)gpio_multi_mode; 641 642 if ((Adapter->IdleMode == TRUE) || 643 (Adapter->bShutStatus == TRUE) || 644 (Adapter->bPreparingForLowPowerMode == TRUE)) 645 return -EINVAL; 646 647 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 648 return -EFAULT; 649 650 if (IoBuffer.InputLength > sizeof(gpio_multi_mode)) 651 return -EINVAL; 652 653 if (copy_from_user(&gpio_multi_mode, IoBuffer.InputBuffer, IoBuffer.InputLength)) 654 return -EFAULT; 655 656 bytes = rdmaltWithLock(Adapter, (UINT)GPIO_MODE_REGISTER, (PUINT)ucResetValue, sizeof(UINT)); 657 658 if (bytes < 0) { 659 Status = bytes; 660 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Read of GPIO_MODE_REGISTER failed"); 661 return Status; 662 } else { 663 Status = STATUS_SUCCESS; 664 } 665 666 /* Validating the request */ 667 if (IsReqGpioIsLedInNVM(Adapter, pgpio_multi_mode[WIMAX_IDX].uiGPIOMask) == FALSE) { 668 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, 669 "Sorry, Requested GPIO<0x%X> is not correspond to NVM LED bit map<0x%X>!!!", 670 pgpio_multi_mode[WIMAX_IDX].uiGPIOMask, Adapter->gpioBitMap); 671 Status = -EINVAL; 672 break; 673 } 674 675 if (pgpio_multi_mode[WIMAX_IDX].uiGPIOMask) { 676 /* write all OUT's (1's) */ 677 *(UINT *) ucResetValue |= (pgpio_multi_mode[WIMAX_IDX].uiGPIOMode & 678 pgpio_multi_mode[WIMAX_IDX].uiGPIOMask); 679 680 /* write all IN's (0's) */ 681 *(UINT *) ucResetValue &= ~((~pgpio_multi_mode[WIMAX_IDX].uiGPIOMode) & 682 pgpio_multi_mode[WIMAX_IDX].uiGPIOMask); 683 684 /* Currently implemented return the modes of all GPIO's 685 * else needs to bit AND with mask 686 */ 687 pgpio_multi_mode[WIMAX_IDX].uiGPIOMode = *(UINT *)ucResetValue; 688 689 Status = wrmaltWithLock(Adapter, GPIO_MODE_REGISTER, (PUINT)ucResetValue, sizeof(ULONG)); 690 if (Status == STATUS_SUCCESS) { 691 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, 692 "WRM to GPIO_MODE_REGISTER Done"); 693 } else { 694 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, 695 "WRM to GPIO_MODE_REGISTER Failed"); 696 Status = -EFAULT; 697 break; 698 } 699 } else { 700/* if uiGPIOMask is 0 then return mode register configuration */ 701 pgpio_multi_mode[WIMAX_IDX].uiGPIOMode = *(UINT *)ucResetValue; 702 } 703 704 Status = copy_to_user(IoBuffer.OutputBuffer, &gpio_multi_mode, IoBuffer.OutputLength); 705 if (Status) { 706 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, 707 "Failed while copying Content to IOBufer for user space err:%d", Status); 708 return -EFAULT; 709 } 710 } 711 break; 712 713 case IOCTL_MAC_ADDR_REQ: 714 case IOCTL_LINK_REQ: 715 case IOCTL_CM_REQUEST: 716 case IOCTL_SS_INFO_REQ: 717 case IOCTL_SEND_CONTROL_MESSAGE: 718 case IOCTL_IDLE_REQ: { 719 PVOID pvBuffer = NULL; 720 721 /* Copy Ioctl Buffer structure */ 722 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 723 return -EFAULT; 724 725 if (IoBuffer.InputLength < sizeof(struct link_request)) 726 return -EINVAL; 727 728 if (IoBuffer.InputLength > MAX_CNTL_PKT_SIZE) 729 return -EINVAL; 730 731 pvBuffer = memdup_user(IoBuffer.InputBuffer, 732 IoBuffer.InputLength); 733 if (IS_ERR(pvBuffer)) 734 return PTR_ERR(pvBuffer); 735 736 down(&Adapter->LowPowerModeSync); 737 Status = wait_event_interruptible_timeout(Adapter->lowpower_mode_wait_queue, 738 !Adapter->bPreparingForLowPowerMode, 739 (1 * HZ)); 740 if (Status == -ERESTARTSYS) 741 goto cntrlEnd; 742 743 if (Adapter->bPreparingForLowPowerMode) { 744 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, 745 "Preparing Idle Mode is still True - Hence Rejecting control message\n"); 746 Status = STATUS_FAILURE; 747 goto cntrlEnd; 748 } 749 Status = CopyBufferToControlPacket(Adapter, (PVOID)pvBuffer); 750 751cntrlEnd: 752 up(&Adapter->LowPowerModeSync); 753 kfree(pvBuffer); 754 break; 755 } 756 757 case IOCTL_BCM_BUFFER_DOWNLOAD_START: { 758 if (down_trylock(&Adapter->NVMRdmWrmLock)) { 759 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, 760 "IOCTL_BCM_CHIP_RESET not allowed as EEPROM Read/Write is in progress\n"); 761 return -EACCES; 762 } 763 764 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, 765 "Starting the firmware download PID =0x%x!!!!\n", current->pid); 766 767 if (down_trylock(&Adapter->fw_download_sema)) 768 return -EBUSY; 769 770 Adapter->bBinDownloaded = FALSE; 771 Adapter->fw_download_process_pid = current->pid; 772 Adapter->bCfgDownloaded = FALSE; 773 Adapter->fw_download_done = FALSE; 774 netif_carrier_off(Adapter->dev); 775 netif_stop_queue(Adapter->dev); 776 Status = reset_card_proc(Adapter); 777 if (Status) { 778 pr_err(PFX "%s: reset_card_proc Failed!\n", Adapter->dev->name); 779 up(&Adapter->fw_download_sema); 780 up(&Adapter->NVMRdmWrmLock); 781 return Status; 782 } 783 mdelay(10); 784 785 up(&Adapter->NVMRdmWrmLock); 786 return Status; 787 } 788 789 case IOCTL_BCM_BUFFER_DOWNLOAD: { 790 FIRMWARE_INFO *psFwInfo = NULL; 791 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Starting the firmware download PID =0x%x!!!!\n", current->pid); 792 793 if (!down_trylock(&Adapter->fw_download_sema)) { 794 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, 795 "Invalid way to download buffer. Use Start and then call this!!!\n"); 796 up(&Adapter->fw_download_sema); 797 Status = -EINVAL; 798 return Status; 799 } 800 801 /* Copy Ioctl Buffer structure */ 802 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) { 803 up(&Adapter->fw_download_sema); 804 return -EFAULT; 805 } 806 807 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, 808 "Length for FW DLD is : %lx\n", IoBuffer.InputLength); 809 810 if (IoBuffer.InputLength > sizeof(FIRMWARE_INFO)) { 811 up(&Adapter->fw_download_sema); 812 return -EINVAL; 813 } 814 815 psFwInfo = kmalloc(sizeof(*psFwInfo), GFP_KERNEL); 816 if (!psFwInfo) { 817 up(&Adapter->fw_download_sema); 818 return -ENOMEM; 819 } 820 821 if (copy_from_user(psFwInfo, IoBuffer.InputBuffer, IoBuffer.InputLength)) { 822 up(&Adapter->fw_download_sema); 823 return -EFAULT; 824 } 825 826 if (!psFwInfo->pvMappedFirmwareAddress || 827 (psFwInfo->u32FirmwareLength == 0)) { 828 829 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Something else is wrong %lu\n", 830 psFwInfo->u32FirmwareLength); 831 up(&Adapter->fw_download_sema); 832 Status = -EINVAL; 833 return Status; 834 } 835 836 Status = bcm_ioctl_fw_download(Adapter, psFwInfo); 837 838 if (Status != STATUS_SUCCESS) { 839 if (psFwInfo->u32StartingAddress == CONFIG_BEGIN_ADDR) 840 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "IOCTL: Configuration File Upload Failed\n"); 841 else 842 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "IOCTL: Firmware File Upload Failed\n"); 843 844 /* up(&Adapter->fw_download_sema); */ 845 846 if (Adapter->LEDInfo.led_thread_running & BCM_LED_THREAD_RUNNING_ACTIVELY) { 847 Adapter->DriverState = DRIVER_INIT; 848 Adapter->LEDInfo.bLedInitDone = FALSE; 849 wake_up(&Adapter->LEDInfo.notify_led_event); 850 } 851 } 852 853 if (Status != STATUS_SUCCESS) 854 up(&Adapter->fw_download_sema); 855 856 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, OSAL_DBG, DBG_LVL_ALL, "IOCTL: Firmware File Uploaded\n"); 857 kfree(psFwInfo); 858 return Status; 859 } 860 861 case IOCTL_BCM_BUFFER_DOWNLOAD_STOP: { 862 if (!down_trylock(&Adapter->fw_download_sema)) { 863 up(&Adapter->fw_download_sema); 864 return -EINVAL; 865 } 866 867 if (down_trylock(&Adapter->NVMRdmWrmLock)) { 868 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, 869 "FW download blocked as EEPROM Read/Write is in progress\n"); 870 up(&Adapter->fw_download_sema); 871 return -EACCES; 872 } 873 874 Adapter->bBinDownloaded = TRUE; 875 Adapter->bCfgDownloaded = TRUE; 876 atomic_set(&Adapter->CurrNumFreeTxDesc, 0); 877 Adapter->CurrNumRecvDescs = 0; 878 Adapter->downloadDDR = 0; 879 880 /* setting the Mips to Run */ 881 Status = run_card_proc(Adapter); 882 883 if (Status) { 884 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Firm Download Failed\n"); 885 up(&Adapter->fw_download_sema); 886 up(&Adapter->NVMRdmWrmLock); 887 return Status; 888 } else { 889 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, 890 DBG_LVL_ALL, "Firm Download Over...\n"); 891 } 892 893 mdelay(10); 894 895 /* Wait for MailBox Interrupt */ 896 if (StartInterruptUrb((PS_INTERFACE_ADAPTER)Adapter->pvInterfaceAdapter)) 897 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Unable to send interrupt...\n"); 898 899 timeout = 5*HZ; 900 Adapter->waiting_to_fw_download_done = FALSE; 901 wait_event_timeout(Adapter->ioctl_fw_dnld_wait_queue, 902 Adapter->waiting_to_fw_download_done, timeout); 903 Adapter->fw_download_process_pid = INVALID_PID; 904 Adapter->fw_download_done = TRUE; 905 atomic_set(&Adapter->CurrNumFreeTxDesc, 0); 906 Adapter->CurrNumRecvDescs = 0; 907 Adapter->PrevNumRecvDescs = 0; 908 atomic_set(&Adapter->cntrlpktCnt, 0); 909 Adapter->LinkUpStatus = 0; 910 Adapter->LinkStatus = 0; 911 912 if (Adapter->LEDInfo.led_thread_running & BCM_LED_THREAD_RUNNING_ACTIVELY) { 913 Adapter->DriverState = FW_DOWNLOAD_DONE; 914 wake_up(&Adapter->LEDInfo.notify_led_event); 915 } 916 917 if (!timeout) 918 Status = -ENODEV; 919 920 up(&Adapter->fw_download_sema); 921 up(&Adapter->NVMRdmWrmLock); 922 return Status; 923 } 924 925 case IOCTL_BE_BUCKET_SIZE: 926 Status = 0; 927 if (get_user(Adapter->BEBucketSize, (unsigned long __user *)arg)) 928 Status = -EFAULT; 929 break; 930 931 case IOCTL_RTPS_BUCKET_SIZE: 932 Status = 0; 933 if (get_user(Adapter->rtPSBucketSize, (unsigned long __user *)arg)) 934 Status = -EFAULT; 935 break; 936 937 case IOCTL_CHIP_RESET: { 938 INT NVMAccess = down_trylock(&Adapter->NVMRdmWrmLock); 939 if (NVMAccess) { 940 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, " IOCTL_BCM_CHIP_RESET not allowed as EEPROM Read/Write is in progress\n"); 941 return -EACCES; 942 } 943 944 down(&Adapter->RxAppControlQueuelock); 945 Status = reset_card_proc(Adapter); 946 flushAllAppQ(); 947 up(&Adapter->RxAppControlQueuelock); 948 up(&Adapter->NVMRdmWrmLock); 949 ResetCounters(Adapter); 950 break; 951 } 952 953 case IOCTL_QOS_THRESHOLD: { 954 USHORT uiLoopIndex; 955 956 Status = 0; 957 for (uiLoopIndex = 0; uiLoopIndex < NO_OF_QUEUES; uiLoopIndex++) { 958 if (get_user(Adapter->PackInfo[uiLoopIndex].uiThreshold, 959 (unsigned long __user *)arg)) { 960 Status = -EFAULT; 961 break; 962 } 963 } 964 break; 965 } 966 967 case IOCTL_DUMP_PACKET_INFO: 968 DumpPackInfo(Adapter); 969 DumpPhsRules(&Adapter->stBCMPhsContext); 970 Status = STATUS_SUCCESS; 971 break; 972 973 case IOCTL_GET_PACK_INFO: 974 if (copy_to_user(argp, &Adapter->PackInfo, sizeof(PacketInfo)*NO_OF_QUEUES)) 975 return -EFAULT; 976 Status = STATUS_SUCCESS; 977 break; 978 979 case IOCTL_BCM_SWITCH_TRANSFER_MODE: { 980 UINT uiData = 0; 981 if (copy_from_user(&uiData, argp, sizeof(UINT))) 982 return -EFAULT; 983 984 if (uiData) { 985 /* Allow All Packets */ 986 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "IOCTL_BCM_SWITCH_TRANSFER_MODE: ETH_PACKET_TUNNELING_MODE\n"); 987 Adapter->TransferMode = ETH_PACKET_TUNNELING_MODE; 988 } else { 989 /* Allow IP only Packets */ 990 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "IOCTL_BCM_SWITCH_TRANSFER_MODE: IP_PACKET_ONLY_MODE\n"); 991 Adapter->TransferMode = IP_PACKET_ONLY_MODE; 992 } 993 Status = STATUS_SUCCESS; 994 break; 995 } 996 997 case IOCTL_BCM_GET_DRIVER_VERSION: { 998 ulong len; 999 1000 /* Copy Ioctl Buffer structure */ 1001 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1002 return -EFAULT; 1003 1004 len = min_t(ulong, IoBuffer.OutputLength, strlen(VER_FILEVERSION_STR) + 1); 1005 1006 if (copy_to_user(IoBuffer.OutputBuffer, VER_FILEVERSION_STR, len)) 1007 return -EFAULT; 1008 Status = STATUS_SUCCESS; 1009 break; 1010 } 1011 1012 case IOCTL_BCM_GET_CURRENT_STATUS: { 1013 LINK_STATE link_state; 1014 1015 /* Copy Ioctl Buffer structure */ 1016 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) { 1017 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "copy_from_user failed..\n"); 1018 return -EFAULT; 1019 } 1020 1021 if (IoBuffer.OutputLength != sizeof(link_state)) { 1022 Status = -EINVAL; 1023 break; 1024 } 1025 1026 memset(&link_state, 0, sizeof(link_state)); 1027 link_state.bIdleMode = Adapter->IdleMode; 1028 link_state.bShutdownMode = Adapter->bShutStatus; 1029 link_state.ucLinkStatus = Adapter->LinkStatus; 1030 1031 if (copy_to_user(IoBuffer.OutputBuffer, &link_state, min_t(size_t, sizeof(link_state), IoBuffer.OutputLength))) { 1032 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Copy_to_user Failed..\n"); 1033 return -EFAULT; 1034 } 1035 Status = STATUS_SUCCESS; 1036 break; 1037 } 1038 1039 case IOCTL_BCM_SET_MAC_TRACING: { 1040 UINT tracing_flag; 1041 1042 /* copy ioctl Buffer structure */ 1043 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1044 return -EFAULT; 1045 1046 if (copy_from_user(&tracing_flag, IoBuffer.InputBuffer, sizeof(UINT))) 1047 return -EFAULT; 1048 1049 if (tracing_flag) 1050 Adapter->pTarangs->MacTracingEnabled = TRUE; 1051 else 1052 Adapter->pTarangs->MacTracingEnabled = FALSE; 1053 break; 1054 } 1055 1056 case IOCTL_BCM_GET_DSX_INDICATION: { 1057 ULONG ulSFId = 0; 1058 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1059 return -EFAULT; 1060 1061 if (IoBuffer.OutputLength < sizeof(stLocalSFAddIndicationAlt)) { 1062 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, 1063 "Mismatch req: %lx needed is =0x%zx!!!", 1064 IoBuffer.OutputLength, sizeof(stLocalSFAddIndicationAlt)); 1065 return -EINVAL; 1066 } 1067 1068 if (copy_from_user(&ulSFId, IoBuffer.InputBuffer, sizeof(ulSFId))) 1069 return -EFAULT; 1070 1071 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Get DSX Data SF ID is =%lx\n", ulSFId); 1072 get_dsx_sf_data_to_application(Adapter, ulSFId, IoBuffer.OutputBuffer); 1073 Status = STATUS_SUCCESS; 1074 } 1075 break; 1076 1077 case IOCTL_BCM_GET_HOST_MIBS: { 1078 PVOID temp_buff; 1079 1080 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1081 return -EFAULT; 1082 1083 if (IoBuffer.OutputLength != sizeof(S_MIBS_HOST_STATS_MIBS)) { 1084 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, 1085 "Length Check failed %lu %zd\n", 1086 IoBuffer.OutputLength, sizeof(S_MIBS_HOST_STATS_MIBS)); 1087 return -EINVAL; 1088 } 1089 1090 /* FIXME: HOST_STATS are too big for kmalloc (122048)! */ 1091 temp_buff = kzalloc(sizeof(S_MIBS_HOST_STATS_MIBS), GFP_KERNEL); 1092 if (!temp_buff) 1093 return STATUS_FAILURE; 1094 1095 Status = ProcessGetHostMibs(Adapter, temp_buff); 1096 GetDroppedAppCntrlPktMibs(temp_buff, pTarang); 1097 1098 if (Status != STATUS_FAILURE) 1099 if (copy_to_user(IoBuffer.OutputBuffer, temp_buff, sizeof(S_MIBS_HOST_STATS_MIBS))) { 1100 kfree(temp_buff); 1101 return -EFAULT; 1102 } 1103 1104 kfree(temp_buff); 1105 break; 1106 } 1107 1108 case IOCTL_BCM_WAKE_UP_DEVICE_FROM_IDLE: 1109 if ((FALSE == Adapter->bTriedToWakeUpFromlowPowerMode) && (TRUE == Adapter->IdleMode)) { 1110 Adapter->usIdleModePattern = ABORT_IDLE_MODE; 1111 Adapter->bWakeUpDevice = TRUE; 1112 wake_up(&Adapter->process_rx_cntrlpkt); 1113 } 1114 1115 Status = STATUS_SUCCESS; 1116 break; 1117 1118 case IOCTL_BCM_BULK_WRM: { 1119 PBULKWRM_BUFFER pBulkBuffer; 1120 UINT uiTempVar = 0; 1121 PCHAR pvBuffer = NULL; 1122 1123 if ((Adapter->IdleMode == TRUE) || 1124 (Adapter->bShutStatus == TRUE) || 1125 (Adapter->bPreparingForLowPowerMode == TRUE)) { 1126 1127 BCM_DEBUG_PRINT (Adapter, DBG_TYPE_PRINTK, 0, 0, "Device in Idle/Shutdown Mode, Blocking Wrms\n"); 1128 Status = -EACCES; 1129 break; 1130 } 1131 1132 /* Copy Ioctl Buffer structure */ 1133 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1134 return -EFAULT; 1135 1136 if (IoBuffer.InputLength < sizeof(ULONG) * 2) 1137 return -EINVAL; 1138 1139 pvBuffer = memdup_user(IoBuffer.InputBuffer, 1140 IoBuffer.InputLength); 1141 if (IS_ERR(pvBuffer)) 1142 return PTR_ERR(pvBuffer); 1143 1144 pBulkBuffer = (PBULKWRM_BUFFER)pvBuffer; 1145 1146 if (((ULONG)pBulkBuffer->Register & 0x0F000000) != 0x0F000000 || 1147 ((ULONG)pBulkBuffer->Register & 0x3)) { 1148 kfree(pvBuffer); 1149 BCM_DEBUG_PRINT (Adapter, DBG_TYPE_PRINTK, 0, 0, "WRM Done On invalid Address : %x Access Denied.\n", (int)pBulkBuffer->Register); 1150 Status = -EINVAL; 1151 break; 1152 } 1153 1154 uiTempVar = pBulkBuffer->Register & EEPROM_REJECT_MASK; 1155 if (!((Adapter->pstargetparams->m_u32Customize)&VSG_MODE) && 1156 ((uiTempVar == EEPROM_REJECT_REG_1) || 1157 (uiTempVar == EEPROM_REJECT_REG_2) || 1158 (uiTempVar == EEPROM_REJECT_REG_3) || 1159 (uiTempVar == EEPROM_REJECT_REG_4)) && 1160 (cmd == IOCTL_BCM_REGISTER_WRITE)) { 1161 1162 kfree(pvBuffer); 1163 BCM_DEBUG_PRINT (Adapter, DBG_TYPE_PRINTK, 0, 0, "EEPROM Access Denied, not in VSG Mode\n"); 1164 Status = -EFAULT; 1165 break; 1166 } 1167 1168 if (pBulkBuffer->SwapEndian == FALSE) 1169 Status = wrmWithLock(Adapter, (UINT)pBulkBuffer->Register, (PCHAR)pBulkBuffer->Values, IoBuffer.InputLength - 2*sizeof(ULONG)); 1170 else 1171 Status = wrmaltWithLock(Adapter, (UINT)pBulkBuffer->Register, (PUINT)pBulkBuffer->Values, IoBuffer.InputLength - 2*sizeof(ULONG)); 1172 1173 if (Status != STATUS_SUCCESS) 1174 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "WRM Failed\n"); 1175 1176 kfree(pvBuffer); 1177 break; 1178 } 1179 1180 case IOCTL_BCM_GET_NVM_SIZE: 1181 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1182 return -EFAULT; 1183 1184 if (Adapter->eNVMType == NVM_EEPROM || Adapter->eNVMType == NVM_FLASH) { 1185 if (copy_to_user(IoBuffer.OutputBuffer, &Adapter->uiNVMDSDSize, sizeof(UINT))) 1186 return -EFAULT; 1187 } 1188 1189 Status = STATUS_SUCCESS; 1190 break; 1191 1192 case IOCTL_BCM_CAL_INIT: { 1193 UINT uiSectorSize = 0 ; 1194 if (Adapter->eNVMType == NVM_FLASH) { 1195 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1196 return -EFAULT; 1197 1198 if (copy_from_user(&uiSectorSize, IoBuffer.InputBuffer, sizeof(UINT))) 1199 return -EFAULT; 1200 1201 if ((uiSectorSize < MIN_SECTOR_SIZE) || (uiSectorSize > MAX_SECTOR_SIZE)) { 1202 if (copy_to_user(IoBuffer.OutputBuffer, &Adapter->uiSectorSize, 1203 sizeof(UINT))) 1204 return -EFAULT; 1205 } else { 1206 if (IsFlash2x(Adapter)) { 1207 if (copy_to_user(IoBuffer.OutputBuffer, &Adapter->uiSectorSize, sizeof(UINT))) 1208 return -EFAULT; 1209 } else { 1210 if ((TRUE == Adapter->bShutStatus) || (TRUE == Adapter->IdleMode)) { 1211 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Device is in Idle/Shutdown Mode\n"); 1212 return -EACCES; 1213 } 1214 1215 Adapter->uiSectorSize = uiSectorSize; 1216 BcmUpdateSectorSize(Adapter, Adapter->uiSectorSize); 1217 } 1218 } 1219 Status = STATUS_SUCCESS; 1220 } else { 1221 Status = STATUS_FAILURE; 1222 } 1223 } 1224 break; 1225 1226 case IOCTL_BCM_SET_DEBUG: 1227#ifdef DEBUG 1228 { 1229 USER_BCM_DBG_STATE sUserDebugState; 1230 1231 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "In SET_DEBUG ioctl\n"); 1232 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1233 return -EFAULT; 1234 1235 if (copy_from_user(&sUserDebugState, IoBuffer.InputBuffer, sizeof(USER_BCM_DBG_STATE))) 1236 return -EFAULT; 1237 1238 BCM_DEBUG_PRINT (Adapter, DBG_TYPE_PRINTK, 0, 0, "IOCTL_BCM_SET_DEBUG: OnOff=%d Type = 0x%x ", 1239 sUserDebugState.OnOff, sUserDebugState.Type); 1240 /* sUserDebugState.Subtype <<= 1; */ 1241 sUserDebugState.Subtype = 1 << sUserDebugState.Subtype; 1242 BCM_DEBUG_PRINT (Adapter, DBG_TYPE_PRINTK, 0, 0, "actual Subtype=0x%x\n", sUserDebugState.Subtype); 1243 1244 /* Update new 'DebugState' in the Adapter */ 1245 Adapter->stDebugState.type |= sUserDebugState.Type; 1246 /* Subtype: A bitmap of 32 bits for Subtype per Type. 1247 * Valid indexes in 'subtype' array: 1,2,4,8 1248 * corresponding to valid Type values. Hence we can use the 'Type' field 1249 * as the index value, ignoring the array entries 0,3,5,6,7 ! 1250 */ 1251 if (sUserDebugState.OnOff) 1252 Adapter->stDebugState.subtype[sUserDebugState.Type] |= sUserDebugState.Subtype; 1253 else 1254 Adapter->stDebugState.subtype[sUserDebugState.Type] &= ~sUserDebugState.Subtype; 1255 1256 BCM_SHOW_DEBUG_BITMAP(Adapter); 1257 } 1258#endif 1259 break; 1260 1261 case IOCTL_BCM_NVM_READ: 1262 case IOCTL_BCM_NVM_WRITE: { 1263 NVM_READWRITE stNVMReadWrite; 1264 PUCHAR pReadData = NULL; 1265 ULONG ulDSDMagicNumInUsrBuff = 0; 1266 struct timeval tv0, tv1; 1267 memset(&tv0, 0, sizeof(struct timeval)); 1268 memset(&tv1, 0, sizeof(struct timeval)); 1269 if ((Adapter->eNVMType == NVM_FLASH) && (Adapter->uiFlashLayoutMajorVersion == 0)) { 1270 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "The Flash Control Section is Corrupted. Hence Rejection on NVM Read/Write\n"); 1271 return -EFAULT; 1272 } 1273 1274 if (IsFlash2x(Adapter)) { 1275 if ((Adapter->eActiveDSD != DSD0) && 1276 (Adapter->eActiveDSD != DSD1) && 1277 (Adapter->eActiveDSD != DSD2)) { 1278 1279 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "No DSD is active..hence NVM Command is blocked"); 1280 return STATUS_FAILURE; 1281 } 1282 } 1283 1284 /* Copy Ioctl Buffer structure */ 1285 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1286 return -EFAULT; 1287 1288 if (copy_from_user(&stNVMReadWrite, 1289 (IOCTL_BCM_NVM_READ == cmd) ? IoBuffer.OutputBuffer : IoBuffer.InputBuffer, 1290 sizeof(NVM_READWRITE))) 1291 return -EFAULT; 1292 1293 /* 1294 * Deny the access if the offset crosses the cal area limit. 1295 */ 1296 if (stNVMReadWrite.uiNumBytes > Adapter->uiNVMDSDSize) 1297 return STATUS_FAILURE; 1298 1299 if (stNVMReadWrite.uiOffset > Adapter->uiNVMDSDSize - stNVMReadWrite.uiNumBytes) { 1300 /* BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Can't allow access beyond NVM Size: 0x%x 0x%x\n", stNVMReadWrite.uiOffset, stNVMReadWrite.uiNumBytes); */ 1301 return STATUS_FAILURE; 1302 } 1303 1304 pReadData = memdup_user(stNVMReadWrite.pBuffer, 1305 stNVMReadWrite.uiNumBytes); 1306 if (IS_ERR(pReadData)) 1307 return PTR_ERR(pReadData); 1308 1309 do_gettimeofday(&tv0); 1310 if (IOCTL_BCM_NVM_READ == cmd) { 1311 down(&Adapter->NVMRdmWrmLock); 1312 1313 if ((Adapter->IdleMode == TRUE) || 1314 (Adapter->bShutStatus == TRUE) || 1315 (Adapter->bPreparingForLowPowerMode == TRUE)) { 1316 1317 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Device is in Idle/Shutdown Mode\n"); 1318 up(&Adapter->NVMRdmWrmLock); 1319 kfree(pReadData); 1320 return -EACCES; 1321 } 1322 1323 Status = BeceemNVMRead(Adapter, (PUINT)pReadData, stNVMReadWrite.uiOffset, stNVMReadWrite.uiNumBytes); 1324 up(&Adapter->NVMRdmWrmLock); 1325 1326 if (Status != STATUS_SUCCESS) { 1327 kfree(pReadData); 1328 return Status; 1329 } 1330 1331 if (copy_to_user(stNVMReadWrite.pBuffer, pReadData, stNVMReadWrite.uiNumBytes)) { 1332 kfree(pReadData); 1333 return -EFAULT; 1334 } 1335 } else { 1336 down(&Adapter->NVMRdmWrmLock); 1337 1338 if ((Adapter->IdleMode == TRUE) || 1339 (Adapter->bShutStatus == TRUE) || 1340 (Adapter->bPreparingForLowPowerMode == TRUE)) { 1341 1342 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Device is in Idle/Shutdown Mode\n"); 1343 up(&Adapter->NVMRdmWrmLock); 1344 kfree(pReadData); 1345 return -EACCES; 1346 } 1347 1348 Adapter->bHeaderChangeAllowed = TRUE; 1349 if (IsFlash2x(Adapter)) { 1350 /* 1351 * New Requirement:- 1352 * DSD section updation will be allowed in two case:- 1353 * 1. if DSD sig is present in DSD header means dongle is ok and updation is fruitfull 1354 * 2. if point 1 failes then user buff should have DSD sig. this point ensures that if dongle is 1355 * corrupted then user space program first modify the DSD header with valid DSD sig so 1356 * that this as well as further write may be worthwhile. 1357 * 1358 * This restriction has been put assuming that if DSD sig is corrupted, DSD 1359 * data won't be considered valid. 1360 */ 1361 1362 Status = BcmFlash2xCorruptSig(Adapter, Adapter->eActiveDSD); 1363 if (Status != STATUS_SUCCESS) { 1364 if (((stNVMReadWrite.uiOffset + stNVMReadWrite.uiNumBytes) != Adapter->uiNVMDSDSize) || 1365 (stNVMReadWrite.uiNumBytes < SIGNATURE_SIZE)) { 1366 1367 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "DSD Sig is present neither in Flash nor User provided Input.."); 1368 up(&Adapter->NVMRdmWrmLock); 1369 kfree(pReadData); 1370 return Status; 1371 } 1372 1373 ulDSDMagicNumInUsrBuff = ntohl(*(PUINT)(pReadData + stNVMReadWrite.uiNumBytes - SIGNATURE_SIZE)); 1374 if (ulDSDMagicNumInUsrBuff != DSD_IMAGE_MAGIC_NUMBER) { 1375 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "DSD Sig is present neither in Flash nor User provided Input.."); 1376 up(&Adapter->NVMRdmWrmLock); 1377 kfree(pReadData); 1378 return Status; 1379 } 1380 } 1381 } 1382 1383 Status = BeceemNVMWrite(Adapter, (PUINT)pReadData, stNVMReadWrite.uiOffset, stNVMReadWrite.uiNumBytes, stNVMReadWrite.bVerify); 1384 if (IsFlash2x(Adapter)) 1385 BcmFlash2xWriteSig(Adapter, Adapter->eActiveDSD); 1386 1387 Adapter->bHeaderChangeAllowed = FALSE; 1388 1389 up(&Adapter->NVMRdmWrmLock); 1390 1391 if (Status != STATUS_SUCCESS) { 1392 kfree(pReadData); 1393 return Status; 1394 } 1395 } 1396 1397 do_gettimeofday(&tv1); 1398 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, " timetaken by Write/read :%ld msec\n", (tv1.tv_sec - tv0.tv_sec)*1000 + (tv1.tv_usec - tv0.tv_usec)/1000); 1399 1400 kfree(pReadData); 1401 return STATUS_SUCCESS; 1402 } 1403 1404 case IOCTL_BCM_FLASH2X_SECTION_READ: { 1405 FLASH2X_READWRITE sFlash2xRead = {0}; 1406 PUCHAR pReadBuff = NULL ; 1407 UINT NOB = 0; 1408 UINT BuffSize = 0; 1409 UINT ReadBytes = 0; 1410 UINT ReadOffset = 0; 1411 void __user *OutPutBuff; 1412 1413 if (IsFlash2x(Adapter) != TRUE) { 1414 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Flash Does not have 2.x map"); 1415 return -EINVAL; 1416 } 1417 1418 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "IOCTL_BCM_FLASH2X_SECTION_READ Called"); 1419 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1420 return -EFAULT; 1421 1422 /* Reading FLASH 2.x READ structure */ 1423 if (copy_from_user(&sFlash2xRead, IoBuffer.InputBuffer, sizeof(FLASH2X_READWRITE))) 1424 return -EFAULT; 1425 1426 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "\nsFlash2xRead.Section :%x", sFlash2xRead.Section); 1427 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "\nsFlash2xRead.offset :%x", sFlash2xRead.offset); 1428 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "\nsFlash2xRead.numOfBytes :%x", sFlash2xRead.numOfBytes); 1429 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "\nsFlash2xRead.bVerify :%x\n", sFlash2xRead.bVerify); 1430 1431 /* This was internal to driver for raw read. now it has ben exposed to user space app. */ 1432 if (validateFlash2xReadWrite(Adapter, &sFlash2xRead) == FALSE) 1433 return STATUS_FAILURE; 1434 1435 NOB = sFlash2xRead.numOfBytes; 1436 if (NOB > Adapter->uiSectorSize) 1437 BuffSize = Adapter->uiSectorSize; 1438 else 1439 BuffSize = NOB; 1440 1441 ReadOffset = sFlash2xRead.offset ; 1442 OutPutBuff = IoBuffer.OutputBuffer; 1443 pReadBuff = (PCHAR)kzalloc(BuffSize , GFP_KERNEL); 1444 1445 if (pReadBuff == NULL) { 1446 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Memory allocation failed for Flash 2.x Read Structure"); 1447 return -ENOMEM; 1448 } 1449 down(&Adapter->NVMRdmWrmLock); 1450 1451 if ((Adapter->IdleMode == TRUE) || 1452 (Adapter->bShutStatus == TRUE) || 1453 (Adapter->bPreparingForLowPowerMode == TRUE)) { 1454 1455 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Device is in Idle/Shutdown Mode\n"); 1456 up(&Adapter->NVMRdmWrmLock); 1457 kfree(pReadBuff); 1458 return -EACCES; 1459 } 1460 1461 while (NOB) { 1462 if (NOB > Adapter->uiSectorSize) 1463 ReadBytes = Adapter->uiSectorSize; 1464 else 1465 ReadBytes = NOB; 1466 1467 /* Reading the data from Flash 2.x */ 1468 Status = BcmFlash2xBulkRead(Adapter, (PUINT)pReadBuff, sFlash2xRead.Section, ReadOffset, ReadBytes); 1469 if (Status) { 1470 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Flash 2x read err with Status :%d", Status); 1471 break; 1472 } 1473 1474 BCM_DEBUG_PRINT_BUFFER(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, pReadBuff, ReadBytes); 1475 1476 Status = copy_to_user(OutPutBuff, pReadBuff, ReadBytes); 1477 if (Status) { 1478 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Copy to use failed with status :%d", Status); 1479 up(&Adapter->NVMRdmWrmLock); 1480 kfree(pReadBuff); 1481 return -EFAULT; 1482 } 1483 NOB = NOB - ReadBytes; 1484 if (NOB) { 1485 ReadOffset = ReadOffset + ReadBytes; 1486 OutPutBuff = OutPutBuff + ReadBytes ; 1487 } 1488 } 1489 1490 up(&Adapter->NVMRdmWrmLock); 1491 kfree(pReadBuff); 1492 } 1493 break; 1494 1495 case IOCTL_BCM_FLASH2X_SECTION_WRITE: { 1496 FLASH2X_READWRITE sFlash2xWrite = {0}; 1497 PUCHAR pWriteBuff; 1498 void __user *InputAddr; 1499 UINT NOB = 0; 1500 UINT BuffSize = 0; 1501 UINT WriteOffset = 0; 1502 UINT WriteBytes = 0; 1503 1504 if (IsFlash2x(Adapter) != TRUE) { 1505 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Flash Does not have 2.x map"); 1506 return -EINVAL; 1507 } 1508 1509 /* First make this False so that we can enable the Sector Permission Check in BeceemFlashBulkWrite */ 1510 Adapter->bAllDSDWriteAllow = FALSE; 1511 1512 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "IOCTL_BCM_FLASH2X_SECTION_WRITE Called"); 1513 1514 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1515 return -EFAULT; 1516 1517 /* Reading FLASH 2.x READ structure */ 1518 if (copy_from_user(&sFlash2xWrite, IoBuffer.InputBuffer, sizeof(FLASH2X_READWRITE))) 1519 return -EFAULT; 1520 1521 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "\nsFlash2xRead.Section :%x", sFlash2xWrite.Section); 1522 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "\nsFlash2xRead.offset :%d", sFlash2xWrite.offset); 1523 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "\nsFlash2xRead.numOfBytes :%x", sFlash2xWrite.numOfBytes); 1524 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "\nsFlash2xRead.bVerify :%x\n", sFlash2xWrite.bVerify); 1525 1526 if ((sFlash2xWrite.Section != VSA0) && (sFlash2xWrite.Section != VSA1) && (sFlash2xWrite.Section != VSA2)) { 1527 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Only VSA write is allowed"); 1528 return -EINVAL; 1529 } 1530 1531 if (validateFlash2xReadWrite(Adapter, &sFlash2xWrite) == FALSE) 1532 return STATUS_FAILURE; 1533 1534 InputAddr = sFlash2xWrite.pDataBuff; 1535 WriteOffset = sFlash2xWrite.offset; 1536 NOB = sFlash2xWrite.numOfBytes; 1537 1538 if (NOB > Adapter->uiSectorSize) 1539 BuffSize = Adapter->uiSectorSize; 1540 else 1541 BuffSize = NOB ; 1542 1543 pWriteBuff = kmalloc(BuffSize, GFP_KERNEL); 1544 1545 if (pWriteBuff == NULL) 1546 return -ENOMEM; 1547 1548 /* extracting the remainder of the given offset. */ 1549 WriteBytes = Adapter->uiSectorSize; 1550 if (WriteOffset % Adapter->uiSectorSize) 1551 WriteBytes = Adapter->uiSectorSize - (WriteOffset % Adapter->uiSectorSize); 1552 1553 if (NOB < WriteBytes) 1554 WriteBytes = NOB; 1555 1556 down(&Adapter->NVMRdmWrmLock); 1557 1558 if ((Adapter->IdleMode == TRUE) || 1559 (Adapter->bShutStatus == TRUE) || 1560 (Adapter->bPreparingForLowPowerMode == TRUE)) { 1561 1562 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Device is in Idle/Shutdown Mode\n"); 1563 up(&Adapter->NVMRdmWrmLock); 1564 kfree(pWriteBuff); 1565 return -EACCES; 1566 } 1567 1568 BcmFlash2xCorruptSig(Adapter, sFlash2xWrite.Section); 1569 do { 1570 Status = copy_from_user(pWriteBuff, InputAddr, WriteBytes); 1571 if (Status) { 1572 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Copy to user failed with status :%d", Status); 1573 up(&Adapter->NVMRdmWrmLock); 1574 kfree(pWriteBuff); 1575 return -EFAULT; 1576 } 1577 BCM_DEBUG_PRINT_BUFFER(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, pWriteBuff, WriteBytes); 1578 1579 /* Writing the data from Flash 2.x */ 1580 Status = BcmFlash2xBulkWrite(Adapter, (PUINT)pWriteBuff, sFlash2xWrite.Section, WriteOffset, WriteBytes, sFlash2xWrite.bVerify); 1581 1582 if (Status) { 1583 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Flash 2x read err with Status :%d", Status); 1584 break; 1585 } 1586 1587 NOB = NOB - WriteBytes; 1588 if (NOB) { 1589 WriteOffset = WriteOffset + WriteBytes; 1590 InputAddr = InputAddr + WriteBytes; 1591 if (NOB > Adapter->uiSectorSize) 1592 WriteBytes = Adapter->uiSectorSize; 1593 else 1594 WriteBytes = NOB; 1595 } 1596 } while (NOB > 0); 1597 1598 BcmFlash2xWriteSig(Adapter, sFlash2xWrite.Section); 1599 up(&Adapter->NVMRdmWrmLock); 1600 kfree(pWriteBuff); 1601 } 1602 break; 1603 1604 case IOCTL_BCM_GET_FLASH2X_SECTION_BITMAP: { 1605 PFLASH2X_BITMAP psFlash2xBitMap; 1606 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "IOCTL_BCM_GET_FLASH2X_SECTION_BITMAP Called"); 1607 1608 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1609 return -EFAULT; 1610 1611 if (IoBuffer.OutputLength != sizeof(FLASH2X_BITMAP)) 1612 return -EINVAL; 1613 1614 psFlash2xBitMap = kzalloc(sizeof(FLASH2X_BITMAP), GFP_KERNEL); 1615 if (psFlash2xBitMap == NULL) { 1616 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Memory is not available"); 1617 return -ENOMEM; 1618 } 1619 1620 /* Reading the Flash Sectio Bit map */ 1621 down(&Adapter->NVMRdmWrmLock); 1622 1623 if ((Adapter->IdleMode == TRUE) || 1624 (Adapter->bShutStatus == TRUE) || 1625 (Adapter->bPreparingForLowPowerMode == TRUE)) { 1626 1627 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Device is in Idle/Shutdown Mode\n"); 1628 up(&Adapter->NVMRdmWrmLock); 1629 kfree(psFlash2xBitMap); 1630 return -EACCES; 1631 } 1632 1633 BcmGetFlash2xSectionalBitMap(Adapter, psFlash2xBitMap); 1634 up(&Adapter->NVMRdmWrmLock); 1635 if (copy_to_user(IoBuffer.OutputBuffer, psFlash2xBitMap, sizeof(FLASH2X_BITMAP))) { 1636 kfree(psFlash2xBitMap); 1637 return -EFAULT; 1638 } 1639 1640 kfree(psFlash2xBitMap); 1641 } 1642 break; 1643 1644 case IOCTL_BCM_SET_ACTIVE_SECTION: { 1645 FLASH2X_SECTION_VAL eFlash2xSectionVal = 0; 1646 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "IOCTL_BCM_SET_ACTIVE_SECTION Called"); 1647 1648 if (IsFlash2x(Adapter) != TRUE) { 1649 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Flash Does not have 2.x map"); 1650 return -EINVAL; 1651 } 1652 1653 Status = copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER)); 1654 if (Status) { 1655 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Copy of IOCTL BUFFER failed"); 1656 return -EFAULT; 1657 } 1658 1659 Status = copy_from_user(&eFlash2xSectionVal, IoBuffer.InputBuffer, sizeof(INT)); 1660 if (Status) { 1661 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Copy of flash section val failed"); 1662 return -EFAULT; 1663 } 1664 1665 down(&Adapter->NVMRdmWrmLock); 1666 1667 if ((Adapter->IdleMode == TRUE) || 1668 (Adapter->bShutStatus == TRUE) || 1669 (Adapter->bPreparingForLowPowerMode == TRUE)) { 1670 1671 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Device is in Idle/Shutdown Mode\n"); 1672 up(&Adapter->NVMRdmWrmLock); 1673 return -EACCES; 1674 } 1675 1676 Status = BcmSetActiveSection(Adapter, eFlash2xSectionVal); 1677 if (Status) 1678 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Failed to make it's priority Highest. Status %d", Status); 1679 1680 up(&Adapter->NVMRdmWrmLock); 1681 } 1682 break; 1683 1684 case IOCTL_BCM_IDENTIFY_ACTIVE_SECTION: { 1685 /* Right Now we are taking care of only DSD */ 1686 Adapter->bAllDSDWriteAllow = FALSE; 1687 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "IOCTL_BCM_IDENTIFY_ACTIVE_SECTION called"); 1688 Status = STATUS_SUCCESS; 1689 } 1690 break; 1691 1692 case IOCTL_BCM_COPY_SECTION: { 1693 FLASH2X_COPY_SECTION sCopySectStrut = {0}; 1694 Status = STATUS_SUCCESS; 1695 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "IOCTL_BCM_COPY_SECTION Called"); 1696 1697 Adapter->bAllDSDWriteAllow = FALSE; 1698 if (IsFlash2x(Adapter) != TRUE) { 1699 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Flash Does not have 2.x map"); 1700 return -EINVAL; 1701 } 1702 1703 Status = copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER)); 1704 if (Status) { 1705 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Copy of IOCTL BUFFER failed Status :%d", Status); 1706 return -EFAULT; 1707 } 1708 1709 Status = copy_from_user(&sCopySectStrut, IoBuffer.InputBuffer, sizeof(FLASH2X_COPY_SECTION)); 1710 if (Status) { 1711 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Copy of Copy_Section_Struct failed with Status :%d", Status); 1712 return -EFAULT; 1713 } 1714 1715 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Source SEction :%x", sCopySectStrut.SrcSection); 1716 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Destination SEction :%x", sCopySectStrut.DstSection); 1717 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "offset :%x", sCopySectStrut.offset); 1718 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "NOB :%x", sCopySectStrut.numOfBytes); 1719 1720 if (IsSectionExistInFlash(Adapter, sCopySectStrut.SrcSection) == FALSE) { 1721 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Source Section<%x> does not exixt in Flash ", sCopySectStrut.SrcSection); 1722 return -EINVAL; 1723 } 1724 1725 if (IsSectionExistInFlash(Adapter, sCopySectStrut.DstSection) == FALSE) { 1726 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Destinatio Section<%x> does not exixt in Flash ", sCopySectStrut.DstSection); 1727 return -EINVAL; 1728 } 1729 1730 if (sCopySectStrut.SrcSection == sCopySectStrut.DstSection) { 1731 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Source and Destination section should be different"); 1732 return -EINVAL; 1733 } 1734 1735 down(&Adapter->NVMRdmWrmLock); 1736 1737 if ((Adapter->IdleMode == TRUE) || 1738 (Adapter->bShutStatus == TRUE) || 1739 (Adapter->bPreparingForLowPowerMode == TRUE)) { 1740 1741 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Device is in Idle/Shutdown Mode\n"); 1742 up(&Adapter->NVMRdmWrmLock); 1743 return -EACCES; 1744 } 1745 1746 if (sCopySectStrut.SrcSection == ISO_IMAGE1 || sCopySectStrut.SrcSection == ISO_IMAGE2) { 1747 if (IsNonCDLessDevice(Adapter)) { 1748 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Device is Non-CDLess hence won't have ISO !!"); 1749 Status = -EINVAL; 1750 } else if (sCopySectStrut.numOfBytes == 0) { 1751 Status = BcmCopyISO(Adapter, sCopySectStrut); 1752 } else { 1753 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Partial Copy of ISO section is not Allowed.."); 1754 Status = STATUS_FAILURE; 1755 } 1756 up(&Adapter->NVMRdmWrmLock); 1757 return Status; 1758 } 1759 1760 Status = BcmCopySection(Adapter, sCopySectStrut.SrcSection, 1761 sCopySectStrut.DstSection, sCopySectStrut.offset, sCopySectStrut.numOfBytes); 1762 up(&Adapter->NVMRdmWrmLock); 1763 } 1764 break; 1765 1766 case IOCTL_BCM_GET_FLASH_CS_INFO: { 1767 Status = STATUS_SUCCESS; 1768 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, " IOCTL_BCM_GET_FLASH_CS_INFO Called"); 1769 1770 Status = copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER)); 1771 if (Status) { 1772 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Copy of IOCTL BUFFER failed"); 1773 return -EFAULT; 1774 } 1775 1776 if (Adapter->eNVMType != NVM_FLASH) { 1777 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Connected device does not have flash"); 1778 Status = -EINVAL; 1779 break; 1780 } 1781 1782 if (IsFlash2x(Adapter) == TRUE) { 1783 if (IoBuffer.OutputLength < sizeof(FLASH2X_CS_INFO)) 1784 return -EINVAL; 1785 1786 if (copy_to_user(IoBuffer.OutputBuffer, Adapter->psFlash2xCSInfo, sizeof(FLASH2X_CS_INFO))) 1787 return -EFAULT; 1788 } else { 1789 if (IoBuffer.OutputLength < sizeof(FLASH_CS_INFO)) 1790 return -EINVAL; 1791 1792 if (copy_to_user(IoBuffer.OutputBuffer, Adapter->psFlashCSInfo, sizeof(FLASH_CS_INFO))) 1793 return -EFAULT; 1794 } 1795 } 1796 break; 1797 1798 case IOCTL_BCM_SELECT_DSD: { 1799 UINT SectOfset = 0; 1800 FLASH2X_SECTION_VAL eFlash2xSectionVal; 1801 eFlash2xSectionVal = NO_SECTION_VAL; 1802 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "IOCTL_BCM_SELECT_DSD Called"); 1803 1804 if (IsFlash2x(Adapter) != TRUE) { 1805 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Flash Does not have 2.x map"); 1806 return -EINVAL; 1807 } 1808 1809 Status = copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER)); 1810 if (Status) { 1811 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Copy of IOCTL BUFFER failed"); 1812 return -EFAULT; 1813 } 1814 Status = copy_from_user(&eFlash2xSectionVal, IoBuffer.InputBuffer, sizeof(INT)); 1815 if (Status) { 1816 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Copy of flash section val failed"); 1817 return -EFAULT; 1818 } 1819 1820 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Read Section :%d", eFlash2xSectionVal); 1821 if ((eFlash2xSectionVal != DSD0) && 1822 (eFlash2xSectionVal != DSD1) && 1823 (eFlash2xSectionVal != DSD2)) { 1824 1825 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Passed section<%x> is not DSD section", eFlash2xSectionVal); 1826 return STATUS_FAILURE; 1827 } 1828 1829 SectOfset = BcmGetSectionValStartOffset(Adapter, eFlash2xSectionVal); 1830 if (SectOfset == INVALID_OFFSET) { 1831 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Provided Section val <%d> does not exixt in Flash 2.x", eFlash2xSectionVal); 1832 return -EINVAL; 1833 } 1834 1835 Adapter->bAllDSDWriteAllow = TRUE; 1836 Adapter->ulFlashCalStart = SectOfset; 1837 Adapter->eActiveDSD = eFlash2xSectionVal; 1838 } 1839 Status = STATUS_SUCCESS; 1840 break; 1841 1842 case IOCTL_BCM_NVM_RAW_READ: { 1843 NVM_READWRITE stNVMRead; 1844 INT NOB ; 1845 INT BuffSize ; 1846 INT ReadOffset = 0; 1847 UINT ReadBytes = 0 ; 1848 PUCHAR pReadBuff; 1849 void __user *OutPutBuff; 1850 1851 if (Adapter->eNVMType != NVM_FLASH) { 1852 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "NVM TYPE is not Flash"); 1853 return -EINVAL; 1854 } 1855 1856 /* Copy Ioctl Buffer structure */ 1857 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) { 1858 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "copy_from_user 1 failed\n"); 1859 return -EFAULT; 1860 } 1861 1862 if (copy_from_user(&stNVMRead, IoBuffer.OutputBuffer, sizeof(NVM_READWRITE))) 1863 return -EFAULT; 1864 1865 NOB = stNVMRead.uiNumBytes; 1866 /* In Raw-Read max Buff size : 64MB */ 1867 1868 if (NOB > DEFAULT_BUFF_SIZE) 1869 BuffSize = DEFAULT_BUFF_SIZE; 1870 else 1871 BuffSize = NOB; 1872 1873 ReadOffset = stNVMRead.uiOffset; 1874 OutPutBuff = stNVMRead.pBuffer; 1875 1876 pReadBuff = kzalloc(BuffSize , GFP_KERNEL); 1877 if (pReadBuff == NULL) { 1878 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Memory allocation failed for Flash 2.x Read Structure"); 1879 Status = -ENOMEM; 1880 break; 1881 } 1882 down(&Adapter->NVMRdmWrmLock); 1883 1884 if ((Adapter->IdleMode == TRUE) || 1885 (Adapter->bShutStatus == TRUE) || 1886 (Adapter->bPreparingForLowPowerMode == TRUE)) { 1887 1888 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Device is in Idle/Shutdown Mode\n"); 1889 kfree(pReadBuff); 1890 up(&Adapter->NVMRdmWrmLock); 1891 return -EACCES; 1892 } 1893 1894 Adapter->bFlashRawRead = TRUE; 1895 1896 while (NOB) { 1897 if (NOB > DEFAULT_BUFF_SIZE) 1898 ReadBytes = DEFAULT_BUFF_SIZE; 1899 else 1900 ReadBytes = NOB; 1901 1902 /* Reading the data from Flash 2.x */ 1903 Status = BeceemNVMRead(Adapter, (PUINT)pReadBuff, ReadOffset, ReadBytes); 1904 if (Status) { 1905 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Flash 2x read err with Status :%d", Status); 1906 break; 1907 } 1908 1909 BCM_DEBUG_PRINT_BUFFER(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, pReadBuff, ReadBytes); 1910 1911 Status = copy_to_user(OutPutBuff, pReadBuff, ReadBytes); 1912 if (Status) { 1913 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Copy to use failed with status :%d", Status); 1914 up(&Adapter->NVMRdmWrmLock); 1915 kfree(pReadBuff); 1916 return -EFAULT; 1917 } 1918 NOB = NOB - ReadBytes; 1919 if (NOB) { 1920 ReadOffset = ReadOffset + ReadBytes; 1921 OutPutBuff = OutPutBuff + ReadBytes; 1922 } 1923 } 1924 Adapter->bFlashRawRead = FALSE; 1925 up(&Adapter->NVMRdmWrmLock); 1926 kfree(pReadBuff); 1927 break; 1928 } 1929 1930 case IOCTL_BCM_CNTRLMSG_MASK: { 1931 ULONG RxCntrlMsgBitMask = 0; 1932 1933 /* Copy Ioctl Buffer structure */ 1934 Status = copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER)); 1935 if (Status) { 1936 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "copy of Ioctl buffer is failed from user space"); 1937 return -EFAULT; 1938 } 1939 1940 if (IoBuffer.InputLength != sizeof(unsigned long)) { 1941 Status = -EINVAL; 1942 break; 1943 } 1944 1945 Status = copy_from_user(&RxCntrlMsgBitMask, IoBuffer.InputBuffer, IoBuffer.InputLength); 1946 if (Status) { 1947 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "copy of control bit mask failed from user space"); 1948 return -EFAULT; 1949 } 1950 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "\n Got user defined cntrl msg bit mask :%lx", RxCntrlMsgBitMask); 1951 pTarang->RxCntrlMsgBitMask = RxCntrlMsgBitMask; 1952 } 1953 break; 1954 1955 case IOCTL_BCM_GET_DEVICE_DRIVER_INFO: { 1956 DEVICE_DRIVER_INFO DevInfo; 1957 1958 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "Called IOCTL_BCM_GET_DEVICE_DRIVER_INFO\n"); 1959 1960 DevInfo.MaxRDMBufferSize = BUFFER_4K; 1961 DevInfo.u32DSDStartOffset = EEPROM_CALPARAM_START; 1962 DevInfo.u32RxAlignmentCorrection = 0; 1963 DevInfo.u32NVMType = Adapter->eNVMType; 1964 DevInfo.u32InterfaceType = BCM_USB; 1965 1966 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1967 return -EFAULT; 1968 1969 if (IoBuffer.OutputLength < sizeof(DevInfo)) 1970 return -EINVAL; 1971 1972 if (copy_to_user(IoBuffer.OutputBuffer, &DevInfo, sizeof(DevInfo))) 1973 return -EFAULT; 1974 } 1975 break; 1976 1977 case IOCTL_BCM_TIME_SINCE_NET_ENTRY: { 1978 ST_TIME_ELAPSED stTimeElapsedSinceNetEntry = {0}; 1979 1980 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "IOCTL_BCM_TIME_SINCE_NET_ENTRY called"); 1981 1982 if (copy_from_user(&IoBuffer, argp, sizeof(IOCTL_BUFFER))) 1983 return -EFAULT; 1984 1985 if (IoBuffer.OutputLength < sizeof(ST_TIME_ELAPSED)) 1986 return -EINVAL; 1987 1988 stTimeElapsedSinceNetEntry.ul64TimeElapsedSinceNetEntry = get_seconds() - Adapter->liTimeSinceLastNetEntry; 1989 1990 if (copy_to_user(IoBuffer.OutputBuffer, &stTimeElapsedSinceNetEntry, sizeof(ST_TIME_ELAPSED))) 1991 return -EFAULT; 1992 } 1993 break; 1994 1995 case IOCTL_CLOSE_NOTIFICATION: 1996 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, OSAL_DBG, DBG_LVL_ALL, "IOCTL_CLOSE_NOTIFICATION"); 1997 break; 1998 1999 default: 2000 pr_info(DRV_NAME ": unknown ioctl cmd=%#x\n", cmd); 2001 Status = STATUS_FAILURE; 2002 break; 2003 } 2004 return Status; 2005} 2006 2007 2008static const struct file_operations bcm_fops = { 2009 .owner = THIS_MODULE, 2010 .open = bcm_char_open, 2011 .release = bcm_char_release, 2012 .read = bcm_char_read, 2013 .unlocked_ioctl = bcm_char_ioctl, 2014 .llseek = no_llseek, 2015}; 2016 2017int register_control_device_interface(PMINI_ADAPTER Adapter) 2018{ 2019 2020 if (Adapter->major > 0) 2021 return Adapter->major; 2022 2023 Adapter->major = register_chrdev(0, DEV_NAME, &bcm_fops); 2024 if (Adapter->major < 0) { 2025 pr_err(DRV_NAME ": could not created character device\n"); 2026 return Adapter->major; 2027 } 2028 2029 Adapter->pstCreatedClassDevice = device_create(bcm_class, NULL, 2030 MKDEV(Adapter->major, 0), 2031 Adapter, DEV_NAME); 2032 2033 if (IS_ERR(Adapter->pstCreatedClassDevice)) { 2034 pr_err(DRV_NAME ": class device create failed\n"); 2035 unregister_chrdev(Adapter->major, DEV_NAME); 2036 return PTR_ERR(Adapter->pstCreatedClassDevice); 2037 } 2038 2039 return 0; 2040} 2041 2042void unregister_control_device_interface(PMINI_ADAPTER Adapter) 2043{ 2044 if (Adapter->major > 0) { 2045 device_destroy(bcm_class, MKDEV(Adapter->major, 0)); 2046 unregister_chrdev(Adapter->major, DEV_NAME); 2047 } 2048} 2049