diff options
Diffstat (limited to 'drivers/staging/ft1000')
19 files changed, 4319 insertions, 6076 deletions
diff --git a/drivers/staging/ft1000/Kconfig b/drivers/staging/ft1000/Kconfig index d6da1304b45..c54b4e83d6e 100644 --- a/drivers/staging/ft1000/Kconfig +++ b/drivers/staging/ft1000/Kconfig @@ -13,7 +13,7 @@ config FT1000_USB config FT1000_PCMCIA tristate "Driver for ft1000 pcmcia device." - depends on PCMCIA && BROKEN + depends on PCMCIA depends on NET help Say Y if you want to have support for Flarion card also called diff --git a/drivers/staging/ft1000/ft1000-pcmcia/boot.h b/drivers/staging/ft1000/ft1000-pcmcia/boot.h index 1fc4ac12e24..60c015c1c28 100644 --- a/drivers/staging/ft1000/ft1000-pcmcia/boot.h +++ b/drivers/staging/ft1000/ft1000-pcmcia/boot.h @@ -1,158 +1,158 @@ -//--------------------------------------------------------------------------- -// FT1000 driver for Flarion Flash OFDM NIC Device -// -// Copyright (C) 2002 Flarion Technologies, All rights reserved. -// -// This program is free software; you can redistribute it and/or modify it -// under the terms of the GNU General Public License as published by the Free -// Software Foundation; either version 2 of the License, or (at your option) any -// later version. This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY -// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for -// more details. You should have received a copy of the GNU General Public -// License along with this program; if not, write to the -// Free Software Foundation, Inc., 59 Temple Place - -// Suite 330, Boston, MA 02111-1307, USA. -//--------------------------------------------------------------------------- -// -// File: boot.h -// -// Description: boatloader -// -// History: -// 1/11/05 Whc Ported to Linux. -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + FT1000 driver for Flarion Flash OFDM NIC Device + + Copyright (C) 2002 Flarion Technologies, All rights reserved. + + This program is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your option) any + later version. This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + more details. You should have received a copy of the GNU General Public + License along with this program; if not, write to the + Free Software Foundation, Inc., 59 Temple Place - + Suite 330, Boston, MA 02111-1307, USA. + --------------------------------------------------------------------------- + + File: boot.h + + Description: boatloader + + History: + 1/11/05 Whc Ported to Linux. + +---------------------------------------------------------------------------*/ #ifndef _BOOTH_ #define _BOOTH_ -// Official bootloader -unsigned char bootimage [] = { -0x00,0x00,0x01,0x5E,0x00,0x00 -,0x00,0x00,0x00,0x00,0x02,0xD7 -,0x00,0x00,0x01,0x5E,0x46,0xB3 -,0xE6,0x02,0x00,0x98,0xE6,0x8C -,0x00,0x98,0xFB,0x92,0xFF,0xFF -,0x98,0xFB,0x94,0xFF,0xFF,0x98 -,0xFB,0x06,0x08,0x00,0x98,0xFB -,0x96,0x84,0x00,0x98,0xFB,0x08 -,0x1C,0x00,0x98,0xFB,0x51,0x25 -,0x10,0x1C,0x00,0xE6,0x51,0x01 -,0x07,0xFD,0x4C,0xFF,0x20,0xF5 -,0x51,0x02,0x20,0x08,0x00,0x4C -,0xFF,0x20,0x3C,0x00,0xC0,0x64 -,0x98,0xC0,0x66,0x98,0xC0,0x68 -,0x98,0xC0,0x6A,0x98,0xC0,0x6C -,0x98,0x90,0x08,0x90,0x09,0x90 -,0x0A,0x90,0x0B,0x90,0x0C,0x90 -,0x0D,0x90,0x0E,0x90,0x0F,0x90 -,0x04,0x90,0x06,0xFB,0x51,0x22 -,0x16,0x08,0x03,0xFB,0x51,0x52 -,0x16,0x08,0x04,0xFB,0x51,0x24 -,0x2B,0x08,0x06,0xFB,0x51,0x54 -,0x2B,0x08,0x07,0xFB,0x51,0x24 -,0x2B,0x08,0x09,0xFB,0x51,0x54 -,0x2B,0x08,0x0A,0xFB,0x51,0x12 -,0x16,0x08,0x0C,0xFB,0x51,0x52 -,0x16,0x08,0x0D,0x78,0x00,0x00 -,0x00,0x16,0x00,0x00,0xEC,0x31 -,0xAE,0x00,0x00,0x81,0x4C,0x0F -,0xE6,0x43,0xFF,0xEC,0x31,0x4E -,0x00,0x00,0x91,0xEC,0x31,0xAE -,0x00,0x00,0x91,0x4C,0x0F,0xE6 -,0x43,0xFF,0xEC,0x31,0x5E,0x00 -,0x00,0xA1,0xEB,0x31,0x08,0x00 -,0x00,0xA6,0xEB,0x31,0x08,0x00 -,0x00,0xAC,0x3C,0x00,0xEB,0x31 -,0x08,0x00,0x00,0xA8,0x76,0xFE -,0xFE,0x08,0xEB,0x31,0x08,0x20 -,0x00,0x00,0x76,0xFF,0xFF,0x18 -,0xED,0x31,0x08,0x20,0x00,0x00 -,0x26,0x10,0x04,0x10,0xF5,0x3C -,0x01,0x3C,0x00,0x08,0x01,0x12 -,0x3C,0x11,0x3C,0x00,0x08,0x01 -,0x0B,0x08,0x00,0x6D,0xEC,0x31 -,0xAE,0x20,0x00,0x06,0xED,0x4D -,0x08,0x00,0x00,0x67,0x80,0x6F -,0x00,0x01,0x0B,0x6F,0x00,0x02 -,0x2E,0x76,0xEE,0x01,0x48,0x06 -,0x01,0x39,0xED,0x4D,0x18,0x00 -,0x02,0xED,0x4D,0x08,0x00,0x04 -,0x14,0x06,0xA4,0xED,0x31,0x22 -,0x00,0x00,0xAC,0x76,0xEE,0x07 -,0x48,0x6D,0x22,0x01,0x1E,0x08 -,0x01,0x58,0xEB,0x31,0x08,0x00 -,0x00,0xAC,0x06,0xFF,0xBA,0x3C -,0x00,0xEB,0x31,0x08,0x20,0x00 -,0x04,0x3C,0x30,0xEB,0x31,0x08 -,0x20,0x00,0x02,0x3C,0x10,0xEB -,0x31,0x08,0x20,0x00,0x00,0xED -,0x31,0x08,0x20,0x00,0x00,0x04 -,0x10,0xF7,0xED,0x31,0x08,0x00 -,0x00,0xA2,0x91,0x00,0x9C,0x3C -,0x80,0xEB,0x31,0x08,0x20,0x00 -,0x04,0x3C,0x20,0xEB,0x31,0x08 -,0x20,0x00,0x02,0x3C,0x10,0xEB -,0x31,0x08,0x20,0x00,0x00,0xED -,0x31,0x08,0x20,0x00,0x00,0x04 -,0x10,0xF7,0xED,0x31,0x08,0x20 -,0x00,0x04,0x42,0x10,0x90,0x08 -,0xEC,0x31,0xAE,0x20,0x00,0x06 -,0xA4,0x41,0x08,0x00,0xB6,0xED -,0x41,0x28,0x7D,0xFF,0xFF,0x22 -,0xB3,0x40,0x98,0x2A,0x32,0xEB -,0x41,0x28,0xB4,0x43,0xFC,0x05 -,0xFF,0xE6,0xA0,0x31,0x20,0x00 -,0x06,0xEB,0x31,0x08,0x20,0x00 -,0x04,0x3C,0x20,0xEB,0x31,0x08 -,0x20,0x00,0x02,0x3C,0x10,0xEB -,0x31,0x08,0x20,0x00,0x00,0xED -,0x31,0x08,0x20,0x00,0x00,0x04 -,0x10,0xF7,0xED,0x31,0x08,0x20 -,0x00,0x04,0x42,0x10,0x90,0x08 -,0xEC,0x31,0xAE,0x20,0x00,0x06 -,0xA4,0x41,0x08,0x00,0x68,0xED -,0x41,0x28,0x7D,0xFF,0xFF,0x22 -,0xB3,0x40,0x98,0x2A,0x32,0xEB -,0x41,0x28,0xB4,0x43,0xFC,0x05 -,0xFF,0xE6,0x48,0x04,0xEB,0x31 -,0x08,0x20,0x00,0x04,0xEB,0x31 -,0x18,0x20,0x00,0x02,0x3C,0x11 -,0xEB,0x31,0x18,0x20,0x00,0x00 -,0xED,0x31,0x08,0x20,0x00,0x00 -,0x04,0x10,0xF7,0xED,0x31,0x08 -,0x20,0x00,0x02,0x66,0x00,0x6F -,0x00,0x01,0x16,0x76,0xEE,0x06 -,0x48,0x4A,0x1E,0x48,0x04,0xED -,0x31,0x08,0x20,0x00,0x04,0xEB -,0x31,0x08,0x00,0x00,0xA4,0x48 -,0x04,0xED,0x31,0x08,0x20,0x00 -,0x04,0xEB,0x31,0x08,0x00,0x00 -,0xA2,0x48,0x04,0x20,0x20,0x4A -,0x7C,0x46,0x82,0x50,0x05,0x50 -,0x15,0xB5,0x1E,0x98,0xED,0x31 -,0x08,0x00,0x00,0xA8,0x10,0x47 -,0x3B,0x2C,0x01,0xDB,0x40,0x11 -,0x98,0xC1,0x1E,0x98,0x10,0x07 -,0x30,0xF9,0x40,0x07,0x18,0x98 -,0x2A,0x10,0xEB,0x31,0x08,0x00 -,0x00,0xA8,0xA4,0x1E,0x98,0xBB -,0x1E,0x98,0x50,0x14,0x50,0x04 -,0x46,0x83,0x48,0x04,0x02,0x01 -,0x00,0x50,0x05,0x50,0x15,0x10 -,0x87,0x3F,0x90,0x2B,0x18,0x01 -,0x00,0xC0,0x31,0x00,0x00,0xAE -,0xDF,0x41,0x00,0x08,0x00,0x1A -,0x42,0x11,0x67,0x01,0xDF,0x41 -,0x02,0x08,0x00,0x10,0x42,0x11 -,0x62,0x01,0xB4,0x43,0x4A,0x68 -,0x50,0x14,0x50,0x04,0x24,0x10 -,0x48,0x04,0xF2,0x31,0x00,0x01 -,0x00,0x00,0xAE,0xF6,0x31,0x00 -,0x01,0x00,0x00,0xAE,0x62,0xE4 -,0xE5,0x61,0x04,0x48,0x04,0xE5 -,0x63,0x05,0x48,0x04,0x20,0x20 -,0x00,0x00,0x00,0x00 +/* Official bootloader */ +static unsigned char bootimage[] = { + 0x00, 0x00, 0x01, 0x5E, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x02, 0xD7, + 0x00, 0x00, 0x01, 0x5E, 0x46, 0xB3, + 0xE6, 0x02, 0x00, 0x98, 0xE6, 0x8C, + 0x00, 0x98, 0xFB, 0x92, 0xFF, 0xFF, + 0x98, 0xFB, 0x94, 0xFF, 0xFF, 0x98, + 0xFB, 0x06, 0x08, 0x00, 0x98, 0xFB, + 0x96, 0x84, 0x00, 0x98, 0xFB, 0x08, + 0x1C, 0x00, 0x98, 0xFB, 0x51, 0x25, + 0x10, 0x1C, 0x00, 0xE6, 0x51, 0x01, + 0x07, 0xFD, 0x4C, 0xFF, 0x20, 0xF5, + 0x51, 0x02, 0x20, 0x08, 0x00, 0x4C, + 0xFF, 0x20, 0x3C, 0x00, 0xC0, 0x64, + 0x98, 0xC0, 0x66, 0x98, 0xC0, 0x68, + 0x98, 0xC0, 0x6A, 0x98, 0xC0, 0x6C, + 0x98, 0x90, 0x08, 0x90, 0x09, 0x90, + 0x0A, 0x90, 0x0B, 0x90, 0x0C, 0x90, + 0x0D, 0x90, 0x0E, 0x90, 0x0F, 0x90, + 0x04, 0x90, 0x06, 0xFB, 0x51, 0x22, + 0x16, 0x08, 0x03, 0xFB, 0x51, 0x52, + 0x16, 0x08, 0x04, 0xFB, 0x51, 0x24, + 0x2B, 0x08, 0x06, 0xFB, 0x51, 0x54, + 0x2B, 0x08, 0x07, 0xFB, 0x51, 0x24, + 0x2B, 0x08, 0x09, 0xFB, 0x51, 0x54, + 0x2B, 0x08, 0x0A, 0xFB, 0x51, 0x12, + 0x16, 0x08, 0x0C, 0xFB, 0x51, 0x52, + 0x16, 0x08, 0x0D, 0x78, 0x00, 0x00, + 0x00, 0x16, 0x00, 0x00, 0xEC, 0x31, + 0xAE, 0x00, 0x00, 0x81, 0x4C, 0x0F, + 0xE6, 0x43, 0xFF, 0xEC, 0x31, 0x4E, + 0x00, 0x00, 0x91, 0xEC, 0x31, 0xAE, + 0x00, 0x00, 0x91, 0x4C, 0x0F, 0xE6, + 0x43, 0xFF, 0xEC, 0x31, 0x5E, 0x00, + 0x00, 0xA1, 0xEB, 0x31, 0x08, 0x00, + 0x00, 0xA6, 0xEB, 0x31, 0x08, 0x00, + 0x00, 0xAC, 0x3C, 0x00, 0xEB, 0x31, + 0x08, 0x00, 0x00, 0xA8, 0x76, 0xFE, + 0xFE, 0x08, 0xEB, 0x31, 0x08, 0x20, + 0x00, 0x00, 0x76, 0xFF, 0xFF, 0x18, + 0xED, 0x31, 0x08, 0x20, 0x00, 0x00, + 0x26, 0x10, 0x04, 0x10, 0xF5, 0x3C, + 0x01, 0x3C, 0x00, 0x08, 0x01, 0x12, + 0x3C, 0x11, 0x3C, 0x00, 0x08, 0x01, + 0x0B, 0x08, 0x00, 0x6D, 0xEC, 0x31, + 0xAE, 0x20, 0x00, 0x06, 0xED, 0x4D, + 0x08, 0x00, 0x00, 0x67, 0x80, 0x6F, + 0x00, 0x01, 0x0B, 0x6F, 0x00, 0x02, + 0x2E, 0x76, 0xEE, 0x01, 0x48, 0x06, + 0x01, 0x39, 0xED, 0x4D, 0x18, 0x00, + 0x02, 0xED, 0x4D, 0x08, 0x00, 0x04, + 0x14, 0x06, 0xA4, 0xED, 0x31, 0x22, + 0x00, 0x00, 0xAC, 0x76, 0xEE, 0x07, + 0x48, 0x6D, 0x22, 0x01, 0x1E, 0x08, + 0x01, 0x58, 0xEB, 0x31, 0x08, 0x00, + 0x00, 0xAC, 0x06, 0xFF, 0xBA, 0x3C, + 0x00, 0xEB, 0x31, 0x08, 0x20, 0x00, + 0x04, 0x3C, 0x30, 0xEB, 0x31, 0x08, + 0x20, 0x00, 0x02, 0x3C, 0x10, 0xEB, + 0x31, 0x08, 0x20, 0x00, 0x00, 0xED, + 0x31, 0x08, 0x20, 0x00, 0x00, 0x04, + 0x10, 0xF7, 0xED, 0x31, 0x08, 0x00, + 0x00, 0xA2, 0x91, 0x00, 0x9C, 0x3C, + 0x80, 0xEB, 0x31, 0x08, 0x20, 0x00, + 0x04, 0x3C, 0x20, 0xEB, 0x31, 0x08, + 0x20, 0x00, 0x02, 0x3C, 0x10, 0xEB, + 0x31, 0x08, 0x20, 0x00, 0x00, 0xED, + 0x31, 0x08, 0x20, 0x00, 0x00, 0x04, + 0x10, 0xF7, 0xED, 0x31, 0x08, 0x20, + 0x00, 0x04, 0x42, 0x10, 0x90, 0x08, + 0xEC, 0x31, 0xAE, 0x20, 0x00, 0x06, + 0xA4, 0x41, 0x08, 0x00, 0xB6, 0xED, + 0x41, 0x28, 0x7D, 0xFF, 0xFF, 0x22, + 0xB3, 0x40, 0x98, 0x2A, 0x32, 0xEB, + 0x41, 0x28, 0xB4, 0x43, 0xFC, 0x05, + 0xFF, 0xE6, 0xA0, 0x31, 0x20, 0x00, + 0x06, 0xEB, 0x31, 0x08, 0x20, 0x00, + 0x04, 0x3C, 0x20, 0xEB, 0x31, 0x08, + 0x20, 0x00, 0x02, 0x3C, 0x10, 0xEB, + 0x31, 0x08, 0x20, 0x00, 0x00, 0xED, + 0x31, 0x08, 0x20, 0x00, 0x00, 0x04, + 0x10, 0xF7, 0xED, 0x31, 0x08, 0x20, + 0x00, 0x04, 0x42, 0x10, 0x90, 0x08, + 0xEC, 0x31, 0xAE, 0x20, 0x00, 0x06, + 0xA4, 0x41, 0x08, 0x00, 0x68, 0xED, + 0x41, 0x28, 0x7D, 0xFF, 0xFF, 0x22, + 0xB3, 0x40, 0x98, 0x2A, 0x32, 0xEB, + 0x41, 0x28, 0xB4, 0x43, 0xFC, 0x05, + 0xFF, 0xE6, 0x48, 0x04, 0xEB, 0x31, + 0x08, 0x20, 0x00, 0x04, 0xEB, 0x31, + 0x18, 0x20, 0x00, 0x02, 0x3C, 0x11, + 0xEB, 0x31, 0x18, 0x20, 0x00, 0x00, + 0xED, 0x31, 0x08, 0x20, 0x00, 0x00, + 0x04, 0x10, 0xF7, 0xED, 0x31, 0x08, + 0x20, 0x00, 0x02, 0x66, 0x00, 0x6F, + 0x00, 0x01, 0x16, 0x76, 0xEE, 0x06, + 0x48, 0x4A, 0x1E, 0x48, 0x04, 0xED, + 0x31, 0x08, 0x20, 0x00, 0x04, 0xEB, + 0x31, 0x08, 0x00, 0x00, 0xA4, 0x48, + 0x04, 0xED, 0x31, 0x08, 0x20, 0x00, + 0x04, 0xEB, 0x31, 0x08, 0x00, 0x00, + 0xA2, 0x48, 0x04, 0x20, 0x20, 0x4A, + 0x7C, 0x46, 0x82, 0x50, 0x05, 0x50, + 0x15, 0xB5, 0x1E, 0x98, 0xED, 0x31, + 0x08, 0x00, 0x00, 0xA8, 0x10, 0x47, + 0x3B, 0x2C, 0x01, 0xDB, 0x40, 0x11, + 0x98, 0xC1, 0x1E, 0x98, 0x10, 0x07, + 0x30, 0xF9, 0x40, 0x07, 0x18, 0x98, + 0x2A, 0x10, 0xEB, 0x31, 0x08, 0x00, + 0x00, 0xA8, 0xA4, 0x1E, 0x98, 0xBB, + 0x1E, 0x98, 0x50, 0x14, 0x50, 0x04, + 0x46, 0x83, 0x48, 0x04, 0x02, 0x01, + 0x00, 0x50, 0x05, 0x50, 0x15, 0x10, + 0x87, 0x3F, 0x90, 0x2B, 0x18, 0x01, + 0x00, 0xC0, 0x31, 0x00, 0x00, 0xAE, + 0xDF, 0x41, 0x00, 0x08, 0x00, 0x1A, + 0x42, 0x11, 0x67, 0x01, 0xDF, 0x41, + 0x02, 0x08, 0x00, 0x10, 0x42, 0x11, + 0x62, 0x01, 0xB4, 0x43, 0x4A, 0x68, + 0x50, 0x14, 0x50, 0x04, 0x24, 0x10, + 0x48, 0x04, 0xF2, 0x31, 0x00, 0x01, + 0x00, 0x00, 0xAE, 0xF6, 0x31, 0x00, + 0x01, 0x00, 0x00, 0xAE, 0x62, 0xE4, + 0xE5, 0x61, 0x04, 0x48, 0x04, 0xE5, + 0x63, 0x05, 0x48, 0x04, 0x20, 0x20, + 0x00, 0x00, 0x00, 0x00 }; #endif diff --git a/drivers/staging/ft1000/ft1000-pcmcia/ft1000.conf b/drivers/staging/ft1000/ft1000-pcmcia/ft1000.conf deleted file mode 100644 index e2321a42e31..00000000000 --- a/drivers/staging/ft1000/ft1000-pcmcia/ft1000.conf +++ /dev/null @@ -1,14 +0,0 @@ -device "ft1000_cs" - class "network" module "ft1000","ft1000_cs" - -card "flarion FT1000" - manfid 0x02cc, 0x0100 - bind "ft1000_cs" - -card "flarion FT1000" - manfid 0x02cc, 0x1000 - bind "ft1000_cs" - -card "flarion FT1000" - manfid 0x02cc, 0x1300 - bind "ft1000_cs" diff --git a/drivers/staging/ft1000/ft1000-pcmcia/ft1000.h b/drivers/staging/ft1000/ft1000-pcmcia/ft1000.h index 61e1cfc8044..0c21ac68003 100644 --- a/drivers/staging/ft1000/ft1000-pcmcia/ft1000.h +++ b/drivers/staging/ft1000/ft1000-pcmcia/ft1000.h @@ -1,409 +1,73 @@ -//--------------------------------------------------------------------------- -// FT1000 driver for Flarion Flash OFDM NIC Device -// -// Copyright (C) 2002 Flarion Technologies, All rights reserved. -// -// This program is free software; you can redistribute it and/or modify it -// under the terms of the GNU General Public License as published by the Free -// Software Foundation; either version 2 of the License, or (at your option) any -// later version. This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY -// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for -// more details. You should have received a copy of the GNU General Public -// License along with this program; if not, write to the -// Free Software Foundation, Inc., 59 Temple Place - -// Suite 330, Boston, MA 02111-1307, USA. -//--------------------------------------------------------------------------- -// -// File: ft1000.h -// -// Description: Common structures and defines -// -// History: -// 8/29/02 Whc Ported to Linux. -// 7/19/04 Whc Drop packet and cmd msg with pseudo header -// checksum -// 10/27/04 Whc Added dynamic downloading of test image. -// 01/11/04 Whc Added support for Magnemite ASIC -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + FT1000 driver for Flarion Flash OFDM NIC Device + + Copyright (C) 2002 Flarion Technologies, All rights reserved. + + This program is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your option) any + later version. This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + more details. You should have received a copy of the GNU General Public + License along with this program; if not, write to the + Free Software Foundation, Inc., 59 Temple Place - + Suite 330, Boston, MA 02111-1307, USA. +--------------------------------------------------------------------------- + Description: Common structures and defines +---------------------------------------------------------------------------*/ #ifndef _FT1000H_ #define _FT1000H_ +#include "../ft1000.h" -#define FT1000_DRV_VER 0x01010300 +#define FT1000_DRV_VER 0x01010300 -#define DSPVERSZ 4 -#define HWSERNUMSZ 16 -#define SKUSZ 20 -#define EUISZ 8 -#define MODESZ 2 -#define CALVERSZ 2 -#define CALDATESZ 6 +#define FT1000_DPRAM_BASE 0x0000 /* Dual Port RAM starting offset */ -// Pseudo Header structure -typedef struct _PSEUDO_HDR -{ - unsigned short length; // length of msg body - unsigned char source; // hardware source id - // Host = 0x10 - // Dsp = 0x20 - unsigned char destination; // hardware destination id (refer to source) - unsigned char portdest; // software destination port id - // Host = 0x00 - // Applicaton Broadcast = 0x10 - // Network Stack = 0x20 - // Dsp OAM = 0x80 - // Dsp Airlink = 0x90 - // Dsp Loader = 0xa0 - // Dsp MIP = 0xb0 - unsigned char portsrc; // software source port id (refer to portdest) - unsigned short sh_str_id; // not used - unsigned char control; // not used - unsigned char rsvd1; - unsigned char seq_num; // message sequence number - unsigned char rsvd2; - unsigned short qos_class; // not used - unsigned short checksum; // pseudo header checksum -} __attribute__ ((packed)) PSEUDO_HDR, *PPSEUDO_HDR; - -// Definitions to maintain compatibility between other platforms -#define UCHAR u8 -#define USHORT u16 -#define ULONG u32 -#define BOOLEAN u8 -#define PULONG u32 * -#define PUSHORT u16 * -#define PUCHAR u8 * -#define PCHAR u8 * -#define UINT u32 - -#define ELECTRABUZZ_ID 0 // ASIC ID for Electrabuzz -#define MAGNEMITE_ID 0x1a01 // ASIC ID for Magnemite - -// MEMORY MAP common to both ELECTRABUZZ and MAGNEMITE -#define FT1000_REG_DPRAM_ADDR 0x000E // DPADR - Dual Port Ram Indirect Address Register -#define FT1000_REG_SUP_CTRL 0x0020 // HCTR - Host Control Register -#define FT1000_REG_SUP_STAT 0x0022 // HSTAT - Host Status Register -#define FT1000_REG_RESET 0x0024 // HCTR - Host Control Register -#define FT1000_REG_SUP_ISR 0x0026 // HISR - Host Interrupt Status Register -#define FT1000_REG_SUP_IMASK 0x0028 // HIMASK - Host Interrupt Mask -#define FT1000_REG_DOORBELL 0x002a // DBELL - Door Bell Register -#define FT1000_REG_ASIC_ID 0x002e // ASICID - ASIC Identification Number - // (Electrabuzz=0 Magnemite=0x1A01) - -// MEMORY MAP FOR ELECTRABUZZ ASIC - -#define FT1000_REG_UFIFO_STAT 0x0000 // UFSR - Uplink FIFO status register -#define FT1000_REG_UFIFO_BEG 0x0002 // UFBR - Uplink FIFO beginning register -#define FT1000_REG_UFIFO_MID 0x0004 // UFMR - Uplink FIFO middle register -#define FT1000_REG_UFIFO_END 0x0006 // UFER - Uplink FIFO end register -#define FT1000_REG_DFIFO_STAT 0x0008 // DFSR - Downlink FIFO status register -#define FT1000_REG_DFIFO 0x000A // DFR - Downlink FIFO Register -#define FT1000_REG_DPRAM_DATA 0x000C // DPRAM - Dual Port Indirect Data Register -#define FT1000_REG_WATERMARK 0x0010 // WMARK - Watermark Register - -// MEMORY MAP FOR MAGNEMITE -#define FT1000_REG_MAG_UFDR 0x0000 // UFDR - Uplink FIFO Data Register (32-bits) -#define FT1000_REG_MAG_UFDRL 0x0000 // UFDRL - Uplink FIFO Data Register low-word (16-bits) -#define FT1000_REG_MAG_UFDRH 0x0002 // UFDRH - Uplink FIFO Data Register high-word (16-bits) -#define FT1000_REG_MAG_UFER 0x0004 // UFER - Uplink FIFO End Register -#define FT1000_REG_MAG_UFSR 0x0006 // UFSR - Uplink FIFO Status Register -#define FT1000_REG_MAG_DFR 0x0008 // DFR - Downlink FIFO Register (32-bits) -#define FT1000_REG_MAG_DFRL 0x0008 // DFRL - Downlink FIFO Register low-word (16-bits) -#define FT1000_REG_MAG_DFRH 0x000a // DFRH - Downlink FIFO Register high-word (16-bits) -#define FT1000_REG_MAG_DFSR 0x000c // DFSR - Downlink FIFO Status Register -#define FT1000_REG_MAG_DPDATA 0x0010 // DPDATA - Dual Port RAM Indirect Data Register (32-bits) -#define FT1000_REG_MAG_DPDATAL 0x0010 // DPDATAL - Dual Port RAM Indirect Data Register low-word (16-bits) -#define FT1000_REG_MAG_DPDATAH 0x0012 // DPDATAH - Dual Port RAM Indirect Data Register high-word (16-bits) -#define FT1000_REG_MAG_WATERMARK 0x002c // WMARK - Watermark Register - -// Reserved Dual Port RAM offsets for Electrabuzz -#define FT1000_DPRAM_TX_BASE 0x0002 // Host to PC Card Messaging Area -#define FT1000_DPRAM_RX_BASE 0x0800 // PC Card to Host Messaging Area -#define FT1000_FIFO_LEN 0x7FC // total length for DSP FIFO tracking -#define FT1000_HI_HO 0x7FE // heartbeat with HI/HO -#define FT1000_DSP_STATUS 0xFFE // dsp status - non-zero is a request to reset dsp -#define FT1000_DSP_LED 0xFFA // dsp led status for PAD device -#define FT1000_DSP_CON_STATE 0xFF8 // DSP Connection Status Info -#define FT1000_DPRAM_FEFE 0x002 // location for dsp ready indicator -#define FT1000_DSP_TIMER0 0x1FF0 // Timer Field from Basestation -#define FT1000_DSP_TIMER1 0x1FF2 // Timer Field from Basestation -#define FT1000_DSP_TIMER2 0x1FF4 // Timer Field from Basestation -#define FT1000_DSP_TIMER3 0x1FF6 // Timer Field from Basestation - -// Reserved Dual Port RAM offsets for Magnemite -#define FT1000_DPRAM_MAG_TX_BASE 0x0000 // Host to PC Card Messaging Area -#define FT1000_DPRAM_MAG_RX_BASE 0x0200 // PC Card to Host Messaging Area -#define FT1000_MAG_FIFO_LEN 0x1FF // total length for DSP FIFO tracking -#define FT1000_MAG_FIFO_LEN_INDX 0x1 // low-word index -#define FT1000_MAG_HI_HO 0x1FF // heartbeat with HI/HO -#define FT1000_MAG_HI_HO_INDX 0x0 // high-word index -#define FT1000_MAG_DSP_LED 0x3FE // dsp led status for PAD device -#define FT1000_MAG_DSP_LED_INDX 0x0 // dsp led status for PAD device - -#define FT1000_MAG_DSP_CON_STATE 0x3FE // DSP Connection Status Info -#define FT1000_MAG_DSP_CON_STATE_INDX 0x1 // DSP Connection Status Info - -#define FT1000_MAG_DPRAM_FEFE 0x000 // location for dsp ready indicator -#define FT1000_MAG_DPRAM_FEFE_INDX 0x0 // location for dsp ready indicator - -#define FT1000_MAG_DSP_TIMER0 0x3FC // Timer Field from Basestation -#define FT1000_MAG_DSP_TIMER0_INDX 0x1 - -#define FT1000_MAG_DSP_TIMER1 0x3FC // Timer Field from Basestation -#define FT1000_MAG_DSP_TIMER1_INDX 0x0 - -#define FT1000_MAG_DSP_TIMER2 0x3FD // Timer Field from Basestation -#define FT1000_MAG_DSP_TIMER2_INDX 0x1 - -#define FT1000_MAG_DSP_TIMER3 0x3FD // Timer Field from Basestation -#define FT1000_MAG_DSP_TIMER3_INDX 0x0 - -#define FT1000_MAG_TOTAL_LEN 0x200 -#define FT1000_MAG_TOTAL_LEN_INDX 0x1 - -#define FT1000_MAG_PH_LEN 0x200 -#define FT1000_MAG_PH_LEN_INDX 0x0 - -#define FT1000_MAG_PORT_ID 0x201 -#define FT1000_MAG_PORT_ID_INDX 0x0 - -#define HOST_INTF_LE 0x0 // Host interface little endian mode -#define HOST_INTF_BE 0x1 // Host interface big endian mode - -// PC Card to Host Doorbell assignments -#define FT1000_DB_DPRAM_RX 0x0001 // this value indicates that DSP has - // data for host in DPRAM -#define FT1000_ASIC_RESET_REQ 0x0004 // DSP requesting host to reset the ASIC -#define FT1000_DSP_ASIC_RESET 0x0008 // DSP indicating host that it will reset the ASIC -#define FT1000_DB_COND_RESET 0x0010 // DSP request for a card reset. - -// Host to PC Card Doorbell assignments -#define FT1000_DB_DPRAM_TX 0x0100 // this value indicates that host has - // data for DSP in DPRAM. -#define FT1000_ASIC_RESET_DSP 0x0400 // Responds to FT1000_ASIC_RESET_REQ -#define FT1000_DB_HB 0x1000 // Indicates that supervisor - // has a heartbeat message for DSP. - -#define FT1000_DPRAM_BASE 0x0000 // Dual Port RAM starting offset - -#define hi 0x6869 // PC Card heartbeat values -#define ho 0x686f // PC Card heartbeat values - -// Magnemite specific defines -#define hi_mag 0x6968 // Byte swap hi to avoid additional system call -#define ho_mag 0x6f68 // Byte swap ho to avoid additional system call - -// -// Bit field definitions for Host Interrupt Status Register -// -// Indicate the cause of an interrupt. -// -#define ISR_EMPTY 0x00 // no bits set -#define ISR_DOORBELL_ACK 0x01 // Doorbell acknowledge from DSP -#define ISR_DOORBELL_PEND 0x02 // Doorbell pending from DSP -#define ISR_RCV 0x04 // Packet available in Downlink FIFO -#define ISR_WATERMARK 0x08 // Watermark requirements satisfied +/* + * Maximum number of occurrence of pseudo header errors before resetting PC + * Card. + */ +#define MAX_PH_ERR 300 -// Bit field definition for Host Interrupt Mask -#define ISR_MASK_NONE 0x0000 // no bits set -#define ISR_MASK_DOORBELL_ACK 0x0001 // Doorbell acknowledge mask -#define ISR_MASK_DOORBELL_PEND 0x0002 // Doorbell pending mask -#define ISR_MASK_RCV 0x0004 // Downlink Packet available mask -#define ISR_MASK_WATERMARK 0x0008 // Watermark interrupt mask -#define ISR_MASK_ALL 0xffff // Mask all interrupts +#define SUCCESS 0x00 +#define FAILURE 0x01 -// Bit field definition for Host Control Register -#define DSP_RESET_BIT 0x0001 // Bit field to control dsp reset state - // (0 = out of reset 1 = reset) -#define ASIC_RESET_BIT 0x0002 // Bit field to control ASIC reset state - // (0 = out of reset 1 = reset) +struct ft1000_pcmcia { + int PktIntfErr; + u16 packetseqnum; + void *link; +}; -// Default interrupt mask (Enable Doorbell pending and Packet available interrupts) -#define ISR_DEFAULT_MASK 0x7ff9 +struct pcmcia_device; +struct net_device; +extern struct net_device *init_ft1000_card(struct pcmcia_device *link, + void *ft1000_reset); +extern void stop_ft1000_card(struct net_device *dev); +extern int card_download(struct net_device *dev, const u8 *pFileStart, + size_t FileLength); +extern void ft1000InitProc(struct net_device *dev); +extern void ft1000CleanupProc(struct net_device *dev); -// Application specific IDs -#define DSPID 0x20 -#define HOSTID 0x10 -#define DSPAIRID 0x90 -#define DRIVERID 0x00 -#define NETWORKID 0x20 - -// Size of DPRAM Message -#define MAX_CMD_SQSIZE 1780 - -#define ENET_MAX_SIZE 1514 -#define ENET_HEADER_SIZE 14 - -#define SLOWQ_TYPE 0 -#define FASTQ_TYPE 1 - -#define MAX_DSP_SESS_REC 1024 - -#define DSP_QID_OFFSET 4 -#define PSEUDOSZ 16 -#define PSEUDOSZWRD 8 - -// Maximum number of occurrence of pseudo header errors before resetting PC Card. -#define MAX_PH_ERR 300 - -// Driver message types -#define MEDIA_STATE 0x0010 -#define TIME_UPDATE 0x0020 -#define DSP_PROVISION 0x0030 -#define DSP_INIT_MSG 0x0050 -#define DSP_HIBERNATE 0x0060 - -#define DSP_STORE_INFO 0x0070 -#define DSP_GET_INFO 0x0071 -#define GET_DRV_ERR_RPT_MSG 0x0073 -#define RSP_DRV_ERR_RPT_MSG 0x0074 - -// Driver Error Messages for DSP -#define DSP_HB_INFO 0x7ef0 -#define DSP_FIFO_INFO 0x7ef1 -#define DSP_CONDRESET_INFO 0x7ef2 -#define DSP_CMDLEN_INFO 0x7ef3 -#define DSP_CMDPHCKSUM_INFO 0x7ef4 -#define DSP_PKTPHCKSUM_INFO 0x7ef5 -#define DSP_PKTLEN_INFO 0x7ef6 -#define DSP_USER_RESET 0x7ef7 -#define FIFO_FLUSH_MAXLIMIT 0x7ef8 -#define FIFO_FLUSH_BADCNT 0x7ef9 -#define FIFO_ZERO_LEN 0x7efa - -#define HOST_QID_OFFSET 5 -#define QTYPE_OFFSET 13 - -#define SUCCESS 0x00 -#define FAILURE 0x01 -#define TRUE 0x1 -#define FALSE 0x0 - -#define MAX_NUM_APP 6 - -#define MAXIMUM_ASIC_HB_CNT 15 - -typedef struct _DRVMSG { - PSEUDO_HDR pseudo; - u16 type; - u16 length; - u8 data[0]; -} __attribute__ ((packed)) DRVMSG, *PDRVMSG; - -typedef struct _MEDIAMSG { - PSEUDO_HDR pseudo; - u16 type; - u16 length; - u16 state; - u32 ip_addr; - u32 net_mask; - u32 gateway; - u32 dns_1; - u32 dns_2; -} __attribute__ ((packed)) MEDIAMSG, *PMEDIAMSG; - -typedef struct _TIMEMSG { - PSEUDO_HDR pseudo; - u16 type; - u16 length; - u8 timeval[8]; -} __attribute__ ((packed)) TIMEMSG, *PTIMEMSG; - -typedef struct _DSPINITMSG { - PSEUDO_HDR pseudo; - u16 type; - u16 length; - u8 DspVer[DSPVERSZ]; // DSP version number - u8 HwSerNum[HWSERNUMSZ]; // Hardware Serial Number - u8 Sku[SKUSZ]; // SKU - u8 eui64[EUISZ]; // EUI64 - u8 ProductMode[MODESZ]; // Product Mode (Market/Production) - u8 RfCalVer[CALVERSZ]; // Rf Calibration version - u8 RfCalDate[CALDATESZ]; // Rf Calibration date -} __attribute__ ((packed)) DSPINITMSG, *PDSPINITMSG; - -typedef struct _DSPHIBERNATE { - PSEUDO_HDR pseudo; - u16 type; - u16 length; - u32 timeout; - u16 sess_info[0]; -} DSPHIBERNATE, *PDSPHIBERNATE; +extern u16 ft1000_read_dpram(struct net_device *dev, int offset); +extern void card_bootload(struct net_device *dev); +extern u16 ft1000_read_dpram_mag_16(struct net_device *dev, int offset, + int Index); +extern u32 ft1000_read_dpram_mag_32(struct net_device *dev, int offset); +void ft1000_write_dpram_mag_32(struct net_device *dev, int offset, u32 value); -typedef struct _APP_INFO_BLOCK +/* Read the value of a given ASIC register. */ +static inline u16 ft1000_read_reg(struct net_device *dev, u16 offset) { - u32 fileobject; // Application's file object - u16 app_id; // Application id -} APP_INFO_BLOCK, *PAPP_INFO_BLOCK; - -typedef struct _PROV_RECORD { - struct list_head list; - u8 *pprov_data; -} PROV_RECORD, *PPROV_RECORD; - -typedef struct _FT1000_INFO { - struct net_device_stats stats; - u16 DrvErrNum; - u16 AsicID; - int ASICResetNum; - int DspAsicReset; - int PktIntfErr; - int DSPResetNum; - int NumIOCTLBufs; - int IOCTLBufLvl; - int DeviceCreated; - int CardReady; - int DspHibernateFlag; - int DSPReady; - u8 DeviceName[15]; - int DeviceMajor; - int registered; - int mediastate; - u16 packetseqnum; - u8 squeseqnum; // sequence number on slow queue - spinlock_t dpram_lock; - u16 CurrentInterruptEnableMask; - int InterruptsEnabled; - u16 fifo_cnt; - u8 DspVer[DSPVERSZ]; // DSP version number - u8 HwSerNum[HWSERNUMSZ]; // Hardware Serial Number - u8 Sku[SKUSZ]; // SKU - u8 eui64[EUISZ]; // EUI64 - time_t ConTm; // Connection Time - u16 LedStat; - u16 ConStat; - u16 ProgConStat; - u8 ProductMode[MODESZ]; - u8 RfCalVer[CALVERSZ]; - u8 RfCalDate[CALDATESZ]; - u16 DSP_TIME[4]; - struct list_head prov_list; - int appcnt; - APP_INFO_BLOCK app_info[MAX_NUM_APP]; - u16 DSPInfoBlklen; - u16 DrvMsgPend; - int (*ft1000_reset)(void *); - void *link; - u16 DSPInfoBlk[MAX_DSP_SESS_REC]; - union { - u16 Rec[MAX_DSP_SESS_REC]; - u32 MagRec[MAX_DSP_SESS_REC/2]; - } DSPSess; - struct proc_dir_entry *proc_ft1000; - char netdevname[IFNAMSIZ]; -} FT1000_INFO, *PFT1000_INFO; + return inw(dev->base_addr + offset); +} -typedef struct _DPRAM_BLK { - struct list_head list; - u16 *pbuffer; -} __attribute__ ((packed)) DPRAM_BLK, *PDPRAM_BLK; - -extern u16 ft1000_read_dpram (struct net_device *dev, int offset); -extern void card_bootload(struct net_device *dev); -extern u16 ft1000_read_dpram_mag_16 (struct net_device *dev, int offset, int Index); -extern u32 ft1000_read_dpram_mag_32 (struct net_device *dev, int offset); -void ft1000_write_dpram_mag_32 (struct net_device *dev, int offset, u32 value); +/* Set the value of a given ASIC register. */ +static inline void ft1000_write_reg(struct net_device *dev, u16 offset, + u16 value) +{ + outw(value, dev->base_addr + offset); +} -#endif // _FT1000H_ +#endif diff --git a/drivers/staging/ft1000/ft1000-pcmcia/ft1000_cs.c b/drivers/staging/ft1000/ft1000-pcmcia/ft1000_cs.c index 2163eae295f..1f8b3ca35c6 100644 --- a/drivers/staging/ft1000/ft1000-pcmcia/ft1000_cs.c +++ b/drivers/staging/ft1000/ft1000-pcmcia/ft1000_cs.c @@ -29,218 +29,54 @@ #include <linux/kernel.h> #include <linux/module.h> #include <linux/init.h> -#include <linux/ptrace.h> -#include <linux/slab.h> -#include <linux/string.h> -#include <linux/timer.h> -#include <linux/ioport.h> -#include <linux/delay.h> - #include <linux/netdevice.h> -#include <linux/etherdevice.h> - -//#include <pcmcia/version.h> // Slavius 21.10.2009 removed from kernel -#include <pcmcia/cs_types.h> -#include <pcmcia/cs.h> #include <pcmcia/cistpl.h> -#include <pcmcia/cisreg.h> #include <pcmcia/ds.h> -#include <asm/io.h> -#include <asm/system.h> -#include <asm/byteorder.h> -#include <asm/uaccess.h> - -#include "ft1000_cs.h" // Slavius 21.10.2009 because CS_SUCCESS constant is missing due to removed pcmcia/version.h - /*====================================================================*/ -/* Module parameters */ - -#define INT_MODULE_PARM(n, v) static int n = v; MODULE_PARM(n, "i") - MODULE_AUTHOR("Wai Chan"); MODULE_DESCRIPTION("FT1000 PCMCIA driver"); MODULE_LICENSE("GPL"); -/* Newer, simpler way of listing specific interrupts */ - -/* The old way: bit map of interrupts to choose from */ -/* This means pick from 15, 14, 12, 11, 10, 9, 7, 5, 4, and 3 */ - -/* - All the PCMCIA modules use PCMCIA_DEBUG to control debugging. If - you do not define PCMCIA_DEBUG at all, all the debug code will be - left out. If you compile with PCMCIA_DEBUG=0, the debug code will - be present but disabled. -*/ -#ifdef FT_DEBUG -#define DEBUG(n, args...) printk(KERN_DEBUG args) -#else -#define DEBUG(n, args...) -#endif - /*====================================================================*/ -struct net_device *init_ft1000_card(int, int, unsigned char *, - void *ft1000_reset, struct pcmcia_device * link, - struct device *fdev); -void stop_ft1000_card(struct net_device *); - static int ft1000_config(struct pcmcia_device *link); -static void ft1000_release(struct pcmcia_device *link); - -/* - The attach() and detach() entry points are used to create and destroy - "instances" of the driver, where each instance represents everything - needed to manage one actual PCMCIA card. -*/ - static void ft1000_detach(struct pcmcia_device *link); -static int ft1000_attach(struct pcmcia_device *link); +static int ft1000_attach(struct pcmcia_device *link); -typedef struct local_info_t { - struct pcmcia_device *link; - struct net_device *dev; -} local_info_t; - -#define MAX_ASIC_RESET_CNT 10 -#define COR_DEFAULT 0x55 +#include "ft1000.h" /*====================================================================*/ -static void ft1000_reset(struct pcmcia_device * link) +static void ft1000_reset(struct pcmcia_device *link) { - conf_reg_t reg; - - DEBUG(0, "ft1000_cs:ft1000_reset is called................\n"); - - /* Soft-Reset card */ - reg.Action = CS_WRITE; - reg.Offset = CISREG_COR; - reg.Value = COR_SOFT_RESET; - pcmcia_access_configuration_register(link, ®); - - /* Wait until the card has acknowledged our reset */ - udelay(2); - - /* Restore original COR configuration index */ - /* Need at least 2 write to respond */ - reg.Action = CS_WRITE; - reg.Offset = CISREG_COR; - reg.Value = COR_DEFAULT; - pcmcia_access_configuration_register(link, ®); - - /* Wait until the card has finished restarting */ - udelay(1); - - reg.Action = CS_WRITE; - reg.Offset = CISREG_COR; - reg.Value = COR_DEFAULT; - pcmcia_access_configuration_register(link, ®); - - /* Wait until the card has finished restarting */ - udelay(1); - - reg.Action = CS_WRITE; - reg.Offset = CISREG_COR; - reg.Value = COR_DEFAULT; - pcmcia_access_configuration_register(link, ®); - - /* Wait until the card has finished restarting */ - udelay(1); - + pcmcia_reset_card(link->socket); } -/*====================================================================*/ - -static int get_tuple_first(struct pcmcia_device *link, tuple_t * tuple, - cisparse_t * parse) -{ - int i; - i = pcmcia_get_first_tuple(link, tuple); - if (i != CS_SUCCESS) - return i; - i = pcmcia_get_tuple_data(link, tuple); - if (i != CS_SUCCESS) - return i; - return pcmcia_parse_tuple(tuple, parse); // Slavius 21.10.2009 removed unused link parameter -} - -static int get_tuple_next(struct pcmcia_device *link, tuple_t * tuple, - cisparse_t * parse) -{ - int i; - i = pcmcia_get_next_tuple(link, tuple); - if (i != CS_SUCCESS) - return i; - i = pcmcia_get_tuple_data(link, tuple); - if (i != CS_SUCCESS) - return i; - return pcmcia_parse_tuple(tuple, parse); // Slavius 21.10.2009 removed unused link parameter -} - -/*====================================================================== - - -======================================================================*/ - static int ft1000_attach(struct pcmcia_device *link) { - - local_info_t *local; - - DEBUG(0, "ft1000_cs: ft1000_attach()\n"); - - local = kmalloc(sizeof(local_info_t), GFP_KERNEL); - if (!local) { - return -ENOMEM; - } - memset(local, 0, sizeof(local_info_t)); - local->link = link; - - link->priv = local; - local->dev = NULL; - - link->irq.Attributes = IRQ_TYPE_EXCLUSIVE; - link->irq.IRQInfo1 = IRQ_LEVEL_ID; - link->conf.Attributes = CONF_ENABLE_IRQ; - link->conf.IntType = INT_MEMORY_AND_IO; - link->irq.Handler = NULL; + link->priv = NULL; + link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; return ft1000_config(link); -} /* ft1000_attach */ - -/*====================================================================== - - This deletes a driver "instance". The device is de-registered - with Card Services. If it has been released, all local data - structures are freed. Otherwise, the structures will be freed - when the device is released. - -======================================================================*/ +} static void ft1000_detach(struct pcmcia_device *link) { - struct net_device *dev = ((local_info_t *) link->priv)->dev; - - DEBUG(0, "ft1000_cs: ft1000_detach(0x%p)\n", link); - - if (link == NULL) { - DEBUG(0,"ft1000_cs:ft1000_detach: Got a NULL pointer\n"); - return; - } + struct net_device *dev = link->priv; - if (dev) { + if (dev) stop_ft1000_card(dev); - } - - ft1000_release(link); - /* This points to the parent local_info_t struct */ + pcmcia_disable_device(link); free_netdev(dev); +} -} /* ft1000_detach */ +static int ft1000_confcheck(struct pcmcia_device *link, void *priv_data) +{ + return pcmcia_request_io(link); +} /*====================================================================== @@ -250,215 +86,43 @@ static void ft1000_detach(struct pcmcia_device *link) ======================================================================*/ -#define CS_CHECK(fn, ret) \ - do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) +static int ft1000_config(struct pcmcia_device *link) +{ + int ret; -#define CFG_CHECK(fn, ret) \ - last_fn = (fn); if ((last_ret = (ret)) != 0) goto next_entry + dev_dbg(&link->dev, "ft1000_cs: ft1000_config(0x%p)\n", link); -static int ft1000_config(struct pcmcia_device * link) -{ - tuple_t tuple; - cisparse_t parse; - int last_fn, last_ret, i; - u_char buf[64]; - cistpl_lan_node_id_t *node_id; - cistpl_cftable_entry_t dflt = { 0 }; - cistpl_cftable_entry_t *cfg; - unsigned char mac_address[6]; - - DEBUG(0, "ft1000_cs: ft1000_config(0x%p)\n", link); - - /* - This reads the card's CONFIG tuple to find its configuration - registers. - */ -// tuple.DesiredTuple = CISTPL_CONFIG; -// tuple.Attributes = 0; - tuple.TupleData = buf; - tuple.TupleDataMax = sizeof(buf); - tuple.TupleOffset = 0; -// CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(link, &tuple)); -// CS_CHECK(GetTupleData, pcmcia_get_tuple_data(link, &tuple)); -// CS_CHECK(ParseTuple, pcmcia_parse_tuple(link, &tuple, &parse)); -// link->conf.ConfigBase = parse.config.base; -// link->conf.Present = parse.config.rmask[0]; - - /* - In this loop, we scan the CIS for configuration table entries, - each of which describes a valid card configuration, including - voltage, IO window, memory window, and interrupt settings. - - We make no assumptions about the card to be configured: we use - just the information available in the CIS. In an ideal world, - this would work for any PCMCIA card, but it requires a complete - and accurate CIS. In practice, a driver usually "knows" most of - these things without consulting the CIS, and most client drivers - will only use the CIS to fill in implementation-defined details. - */ - tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; - tuple.Attributes = 0; - CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(link, &tuple)); - while (1) { - cfg = &(parse.cftable_entry); - CFG_CHECK(GetTupleData, pcmcia_get_tuple_data(link, &tuple)); - CFG_CHECK(ParseTuple, - pcmcia_parse_tuple(&tuple, &parse)); // Slavius 21.10.2009 removed unused link parameter - - if (cfg->flags & CISTPL_CFTABLE_DEFAULT) - dflt = *cfg; - if (cfg->index == 0) - goto next_entry; - link->conf.ConfigIndex = cfg->index; - - /* Do we need to allocate an interrupt? */ - if (cfg->irq.IRQInfo1 || dflt.irq.IRQInfo1) - link->conf.Attributes |= CONF_ENABLE_IRQ; - - /* IO window settings */ - link->io.NumPorts1 = link->io.NumPorts2 = 0; - if ((cfg->io.nwin > 0) || (dflt.io.nwin > 0)) { - cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt.io; - link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO; - if (!(io->flags & CISTPL_IO_8BIT)) { - DEBUG(0, "ft1000_cs: IO_DATA_PATH_WIDTH_16\n"); - link->io.Attributes1 = IO_DATA_PATH_WIDTH_16; - } - if (!(io->flags & CISTPL_IO_16BIT)) { - DEBUG(0, "ft1000_cs: IO_DATA_PATH_WIDTH_8\n"); - link->io.Attributes1 = IO_DATA_PATH_WIDTH_8; - } - link->io.IOAddrLines = io->flags & CISTPL_IO_LINES_MASK; - link->io.BasePort1 = io->win[0].base; - link->io.NumPorts1 = io->win[0].len; - if (io->nwin > 1) { - link->io.Attributes2 = link->io.Attributes1; - link->io.BasePort2 = io->win[1].base; - link->io.NumPorts2 = io->win[1].len; - } - /* This reserves IO space but doesn't actually enable it */ - pcmcia_request_io(link, &link->io); - } - - break; - - next_entry: - last_ret = pcmcia_get_next_tuple(link, &tuple); - } - if (last_ret != CS_SUCCESS) { - cs_error(link, RequestIO, last_ret); - goto failed; + /* setup IO window */ + ret = pcmcia_loop_config(link, ft1000_confcheck, NULL); + if (ret) { + dev_err(&link->dev, "Could not configure pcmcia\n"); + return -ENODEV; } - /* - Allocate an interrupt line. Note that this does not assign a - handler to the interrupt, unless the 'Handler' member of the - irq structure is initialized. - */ - CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq)); - - /* - This actually configures the PCMCIA socket -- setting up - the I/O windows and the interrupt mapping, and putting the - card and host interface into "Memory and IO" mode. - */ - CS_CHECK(RequestConfiguration, - pcmcia_request_configuration(link, &link->conf)); - - /* Get MAC address from tuples */ - - tuple.Attributes = tuple.TupleOffset = 0; - tuple.TupleData = buf; - tuple.TupleDataMax = sizeof(buf); - - /* Check for a LAN function extension tuple */ - tuple.DesiredTuple = CISTPL_FUNCE; - i = get_tuple_first(link, &tuple, &parse); - while (i == CS_SUCCESS) { - if (parse.funce.type == CISTPL_FUNCE_LAN_NODE_ID) - break; - i = get_tuple_next(link, &tuple, &parse); + /* configure device */ + ret = pcmcia_enable_device(link); + if (ret) { + dev_err(&link->dev, "Could not enable pcmcia\n"); + goto failed; } - if (i == CS_SUCCESS) { - node_id = (cistpl_lan_node_id_t *) parse.funce.data; - if (node_id->nb == 6) { - for (i = 0; i < 6; i++) - mac_address[i] = node_id->id[i]; - } + link->priv = init_ft1000_card(link, &ft1000_reset); + if (!link->priv) { + dev_err(&link->dev, "Could not register as network device\n"); + goto failed; } - ((local_info_t *) link->priv)->dev = - init_ft1000_card(link->irq.AssignedIRQ, link->io.BasePort1, - &mac_address[0], ft1000_reset, link, - &handle_to_dev(link)); - - /* - At this point, the dev_node_t structure(s) need to be - initialized and arranged in a linked list at link->dev. - */ - /* Finally, report what we've done */ return 0; - -cs_failed: - cs_error(link, last_fn, last_ret); failed: - ft1000_release(link); + pcmcia_disable_device(link); return -ENODEV; - -} /* ft1000_config */ - -/*====================================================================== - - After a card is removed, ft1000_release() will unregister the - device, and release the PCMCIA configuration. If the device is - still open, this will be postponed until it is closed. - -======================================================================*/ - -static void ft1000_release(struct pcmcia_device * link) -{ - - DEBUG(0, "ft1000_cs: ft1000_release(0x%p)\n", link); - - /* - If the device is currently in use, we won't release until it - is actually closed, because until then, we can't be sure that - no one will try to access the device or its data structures. - */ - - /* Unlink the device chain */ - link->dev_node = NULL; - - /* - In a normal driver, additional code may be needed to release - other kernel data structures associated with this device. - */ - - /* Don't bother checking to see if these succeed or not */ - - pcmcia_disable_device(link); -} /* ft1000_release */ - -/*====================================================================== - - The card status event handler. Mostly, this schedules other - stuff to run after an event is received. - - When a CARD_REMOVAL event is received, we immediately set a - private flag to block future accesses to this device. All the - functions that actually access the device should check this flag - to make sure the card is still present. - -======================================================================*/ +} static int ft1000_suspend(struct pcmcia_device *link) { - struct net_device *dev = ((local_info_t *) link->priv)->dev; - - DEBUG(1, "ft1000_cs: ft1000_event(0x%06x)\n", event); + struct net_device *dev = link->priv; if (link->open) netif_device_detach(dev); @@ -467,16 +131,12 @@ static int ft1000_suspend(struct pcmcia_device *link) static int ft1000_resume(struct pcmcia_device *link) { -/* struct net_device *dev = link->priv; - */ return 0; } - - /*====================================================================*/ -static struct pcmcia_device_id ft1000_ids[] = { +static const struct pcmcia_device_id ft1000_ids[] = { PCMCIA_DEVICE_MANF_CARD(0x02cc, 0x0100), PCMCIA_DEVICE_MANF_CARD(0x02cc, 0x1000), PCMCIA_DEVICE_MANF_CARD(0x02cc, 0x1300), @@ -486,26 +146,22 @@ static struct pcmcia_device_id ft1000_ids[] = { MODULE_DEVICE_TABLE(pcmcia, ft1000_ids); static struct pcmcia_driver ft1000_cs_driver = { - .owner = THIS_MODULE, - .drv = { - .name = "ft1000_cs", - }, - .probe = ft1000_attach, - .remove = ft1000_detach, + .owner = THIS_MODULE, + .name = "ft1000_cs", + .probe = ft1000_attach, + .remove = ft1000_detach, .id_table = ft1000_ids, - .suspend = ft1000_suspend, - .resume = ft1000_resume, + .suspend = ft1000_suspend, + .resume = ft1000_resume, }; static int __init init_ft1000_cs(void) { - DEBUG(0, "ft1000_cs: loading\n"); return pcmcia_register_driver(&ft1000_cs_driver); } static void __exit exit_ft1000_cs(void) { - DEBUG(0, "ft1000_cs: unloading\n"); pcmcia_unregister_driver(&ft1000_cs_driver); } diff --git a/drivers/staging/ft1000/ft1000-pcmcia/ft1000_cs.h b/drivers/staging/ft1000/ft1000-pcmcia/ft1000_cs.h deleted file mode 100644 index 2b5e383631f..00000000000 --- a/drivers/staging/ft1000/ft1000-pcmcia/ft1000_cs.h +++ /dev/null @@ -1 +0,0 @@ -#define CS_SUCCESS 0x00 diff --git a/drivers/staging/ft1000/ft1000-pcmcia/ft1000_dev.h b/drivers/staging/ft1000/ft1000-pcmcia/ft1000_dev.h deleted file mode 100644 index 4a89bd1bbf7..00000000000 --- a/drivers/staging/ft1000/ft1000-pcmcia/ft1000_dev.h +++ /dev/null @@ -1,66 +0,0 @@ -//--------------------------------------------------------------------------- -// FT1000 driver for Flarion Flash OFDM NIC Device -// -// Copyright (C) 2002 Flarion Technologies, All rights reserved. -// -// This program is free software; you can redistribute it and/or modify it -// under the terms of the GNU General Public License as published by the Free -// Software Foundation; either version 2 of the License, or (at your option) any -// later version. This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY -// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for -// more details. You should have received a copy of the GNU General Public -// License along with this program; if not, write to the -// Free Software Foundation, Inc., 59 Temple Place - -// Suite 330, Boston, MA 02111-1307, USA. -//--------------------------------------------------------------------------- -// -// File: ft1000_dev.h -// -// Description: Register definitions and bit masks for the FT1000 NIC -// -// History: -// 2/5/02 Ivan Bohannon Written. -// 8/29/02 Whc Ported to Linux. -// -//--------------------------------------------------------------------------- -#ifndef _FT1000_DEVH_ -#define _FT1000_DEVH_ - -//--------------------------------------------------------------------------- -// -// Function: ft1000_read_reg -// Descripton: This function will read the value of a given ASIC register. -// Input: -// dev - device structure -// offset - ASIC register offset -// Output: -// data - ASIC register value -// -//--------------------------------------------------------------------------- -static inline u16 ft1000_read_reg (struct net_device *dev, u16 offset) { - u16 data = 0; - - data = inw(dev->base_addr + offset); - - return (data); -} - -//--------------------------------------------------------------------------- -// -// Function: ft1000_write_reg -// Descripton: This function will set the value for a given ASIC register. -// Input: -// dev - device structure -// offset - ASIC register offset -// value - value to write -// Output: -// None. -// -//--------------------------------------------------------------------------- -static inline void ft1000_write_reg (struct net_device *dev, u16 offset, u16 value) { - outw (value, dev->base_addr + offset); -} - -#endif // _FT1000_DEVH_ - diff --git a/drivers/staging/ft1000/ft1000-pcmcia/ft1000_dnld.c b/drivers/staging/ft1000/ft1000-pcmcia/ft1000_dnld.c index 0bf398d570d..d44e8583ad1 100644 --- a/drivers/staging/ft1000/ft1000-pcmcia/ft1000_dnld.c +++ b/drivers/staging/ft1000/ft1000-pcmcia/ft1000_dnld.c @@ -30,12 +30,10 @@ #include <linux/netdevice.h> #include <linux/timer.h> #include <linux/delay.h> -#include <linux/slab.h> #include <asm/io.h> #include <asm/uaccess.h> #include <linux/vmalloc.h> -#include "ft1000_dev.h" #include "ft1000.h" #include "boot.h" @@ -88,83 +86,62 @@ #define STATE_DONE_PROV 0x06 #define STATE_DONE_FILE 0x07 -USHORT get_handshake(struct net_device *dev, USHORT expected_value); -void put_handshake(struct net_device *dev, USHORT handshake_value); -USHORT get_request_type(struct net_device *dev); +u16 get_handshake(struct net_device *dev, u16 expected_value); +void put_handshake(struct net_device *dev, u16 handshake_value); +u16 get_request_type(struct net_device *dev); long get_request_value(struct net_device *dev); void put_request_value(struct net_device *dev, long lvalue); -USHORT hdr_checksum(PPSEUDO_HDR pHdr); - -typedef struct _DSP_FILE_HDR { - long build_date; - long dsp_coff_date; - long loader_code_address; - long loader_code_size; - long loader_code_end; - long dsp_code_address; - long dsp_code_size; - long dsp_code_end; - long reserved[8]; -} __attribute__ ((packed)) DSP_FILE_HDR, *PDSP_FILE_HDR; - -typedef struct _DSP_FILE_HDR_5 { - long version_id; // Version ID of this image format. - long package_id; // Package ID of code release. - long build_date; // Date/time stamp when file was built. - long commands_offset; // Offset to attached commands in Pseudo Hdr format. - long loader_offset; // Offset to bootloader code. - long loader_code_address; // Start address of bootloader. - long loader_code_end; // Where bootloader code ends. - long loader_code_size; - long version_data_offset; // Offset were scrambled version data begins. - long version_data_size; // Size, in words, of scrambled version data. - long nDspImages; // Number of DSP images in file. -} __attribute__ ((packed)) DSP_FILE_HDR_5, *PDSP_FILE_HDR_5; - -typedef struct _DSP_IMAGE_INFO { - long coff_date; // Date/time when DSP Coff image was built. - long begin_offset; // Offset in file where image begins. - long end_offset; // Offset in file where image begins. - long run_address; // On chip Start address of DSP code. - long image_size; // Size of image. - long version; // Embedded version # of DSP code. -} __attribute__ ((packed)) DSP_IMAGE_INFO, *PDSP_IMAGE_INFO; - -typedef struct _DSP_IMAGE_INFO_V6 { - long coff_date; // Date/time when DSP Coff image was built. - long begin_offset; // Offset in file where image begins. - long end_offset; // Offset in file where image begins. - long run_address; // On chip Start address of DSP code. - long image_size; // Size of image. - long version; // Embedded version # of DSP code. - unsigned short checksum; // Dsp File checksum +u16 hdr_checksum(struct pseudo_hdr *pHdr); + +struct dsp_file_hdr { + u32 version_id; /* Version ID of this image format. */ + u32 package_id; /* Package ID of code release. */ + u32 build_date; /* Date/time stamp when file was built. */ + u32 commands_offset; /* Offset to attached commands in Pseudo Hdr format. */ + u32 loader_offset; /* Offset to bootloader code. */ + u32 loader_code_address; /* Start address of bootloader. */ + u32 loader_code_end; /* Where bootloader code ends. */ + u32 loader_code_size; + u32 version_data_offset; /* Offset were scrambled version data begins. */ + u32 version_data_size; /* Size, in words, of scrambled version data. */ + u32 nDspImages; /* Number of DSP images in file. */ +} __attribute__ ((packed)); + +struct dsp_image_info { + u32 coff_date; /* Date/time when DSP Coff image was built. */ + u32 begin_offset; /* Offset in file where image begins. */ + u32 end_offset; /* Offset in file where image begins. */ + u32 run_address; /* On chip Start address of DSP code. */ + u32 image_size; /* Size of image. */ + u32 version; /* Embedded version # of DSP code. */ + unsigned short checksum; /* Dsp File checksum */ unsigned short pad1; -} __attribute__ ((packed)) DSP_IMAGE_INFO_V6, *PDSP_IMAGE_INFO_V6; +} __attribute__ ((packed)); void card_bootload(struct net_device *dev) { - FT1000_INFO *info = (PFT1000_INFO) netdev_priv(dev); + struct ft1000_info *info = (struct ft1000_info *) netdev_priv(dev); unsigned long flags; - PULONG pdata; - UINT size; - UINT i; - ULONG templong; + u32 *pdata; + u32 size; + u32 i; + u32 templong; DEBUG(0, "card_bootload is called\n"); - pdata = (PULONG) bootimage; + pdata = (u32 *) bootimage; size = sizeof(bootimage); - // check for odd word - if (size & 0x0003) { + /* check for odd word */ + if (size & 0x0003) size += 4; - } - // Provide mutual exclusive access while reading ASIC registers. + + /* Provide mutual exclusive access while reading ASIC registers. */ spin_lock_irqsave(&info->dpram_lock, flags); - // need to set i/o base address initially and hardware will autoincrement + /* need to set i/o base address initially and hardware will autoincrement */ ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, FT1000_DPRAM_BASE); - // write bytes + /* write bytes */ for (i = 0; i < (size >> 2); i++) { templong = *pdata++; outl(templong, dev->base_addr + FT1000_REG_MAG_DPDATA); @@ -173,11 +150,11 @@ void card_bootload(struct net_device *dev) spin_unlock_irqrestore(&info->dpram_lock, flags); } -USHORT get_handshake(struct net_device *dev, USHORT expected_value) +u16 get_handshake(struct net_device *dev, u16 expected_value) { - FT1000_INFO *info = (PFT1000_INFO) netdev_priv(dev); - USHORT handshake; - ULONG tempx; + struct ft1000_info *info = (struct ft1000_info *) netdev_priv(dev); + u16 handshake; + u32 tempx; int loopcnt; loopcnt = 0; @@ -191,7 +168,7 @@ USHORT get_handshake(struct net_device *dev, USHORT expected_value) tempx = ntohl(ft1000_read_dpram_mag_32 (dev, DWNLD_MAG_HANDSHAKE_LOC)); - handshake = (USHORT) tempx; + handshake = (u16) tempx; } if ((handshake == expected_value) @@ -208,27 +185,27 @@ USHORT get_handshake(struct net_device *dev, USHORT expected_value) } -void put_handshake(struct net_device *dev, USHORT handshake_value) +void put_handshake(struct net_device *dev, u16 handshake_value) { - FT1000_INFO *info = (PFT1000_INFO) netdev_priv(dev); - ULONG tempx; + struct ft1000_info *info = (struct ft1000_info *) netdev_priv(dev); + u32 tempx; if (info->AsicID == ELECTRABUZZ_ID) { ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, DWNLD_HANDSHAKE_LOC); ft1000_write_reg(dev, FT1000_REG_DPRAM_DATA, handshake_value); /* Handshake */ } else { - tempx = (ULONG) handshake_value; + tempx = (u32) handshake_value; tempx = ntohl(tempx); ft1000_write_dpram_mag_32(dev, DWNLD_MAG_HANDSHAKE_LOC, tempx); /* Handshake */ } } -USHORT get_request_type(struct net_device *dev) +u16 get_request_type(struct net_device *dev) { - FT1000_INFO *info = (PFT1000_INFO) netdev_priv(dev); - USHORT request_type; - ULONG tempx; + struct ft1000_info *info = (struct ft1000_info *) netdev_priv(dev); + u16 request_type; + u32 tempx; if (info->AsicID == ELECTRABUZZ_ID) { ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, DWNLD_TYPE_LOC); @@ -236,7 +213,7 @@ USHORT get_request_type(struct net_device *dev) } else { tempx = ft1000_read_dpram_mag_32(dev, DWNLD_MAG_TYPE_LOC); tempx = ntohl(tempx); - request_type = (USHORT) tempx; + request_type = (u16) tempx; } return request_type; @@ -245,9 +222,9 @@ USHORT get_request_type(struct net_device *dev) long get_request_value(struct net_device *dev) { - FT1000_INFO *info = (PFT1000_INFO) netdev_priv(dev); + struct ft1000_info *info = (struct ft1000_info *) netdev_priv(dev); long value; - USHORT w_val; + u16 w_val; if (info->AsicID == ELECTRABUZZ_ID) { ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, @@ -274,19 +251,19 @@ long get_request_value(struct net_device *dev) void put_request_value(struct net_device *dev, long lvalue) { - FT1000_INFO *info = (PFT1000_INFO) netdev_priv(dev); - USHORT size; - ULONG tempx; + struct ft1000_info *info = (struct ft1000_info *) netdev_priv(dev); + u16 size; + u32 tempx; if (info->AsicID == ELECTRABUZZ_ID) { - size = (USHORT) (lvalue >> 16); + size = (u16) (lvalue >> 16); ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, DWNLD_SIZE_MSW_LOC); ft1000_write_reg(dev, FT1000_REG_DPRAM_DATA, size); - size = (USHORT) (lvalue); + size = (u16) (lvalue); ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, DWNLD_SIZE_LSW_LOC); @@ -299,10 +276,10 @@ void put_request_value(struct net_device *dev, long lvalue) } -USHORT hdr_checksum(PPSEUDO_HDR pHdr) +u16 hdr_checksum(struct pseudo_hdr *pHdr) { - USHORT *usPtr = (USHORT *) pHdr; - USHORT chksum; + u16 *usPtr = (u16 *) pHdr; + u16 chksum; chksum = ((((((usPtr[0] ^ usPtr[1]) ^ usPtr[2]) ^ usPtr[3]) ^ usPtr[4]) ^ usPtr[5]) ^ usPtr[6]); @@ -310,32 +287,30 @@ USHORT hdr_checksum(PPSEUDO_HDR pHdr) return chksum; } -int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) +int card_download(struct net_device *dev, const u8 *pFileStart, + size_t FileLength) { - FT1000_INFO *info = (PFT1000_INFO) netdev_priv(dev); + struct ft1000_info *info = (struct ft1000_info *) netdev_priv(dev); int Status = SUCCESS; - USHORT DspWordCnt = 0; - UINT uiState; - USHORT handshake; - PPSEUDO_HDR pHdr; - USHORT usHdrLength; - PDSP_FILE_HDR pFileHdr; + u32 uiState; + u16 handshake; + struct pseudo_hdr *pHdr; + u16 usHdrLength; long word_length; - USHORT request; - USHORT temp; - PPROV_RECORD pprov_record; - PUCHAR pbuffer; - PDSP_FILE_HDR_5 pFileHdr5; - PDSP_IMAGE_INFO pDspImageInfo = NULL; - PDSP_IMAGE_INFO_V6 pDspImageInfoV6 = NULL; + u16 request; + u16 temp; + struct prov_record *pprov_record; + u8 *pbuffer; + struct dsp_file_hdr *pFileHdr5; + struct dsp_image_info *pDspImageInfoV6 = NULL; long requested_version; - BOOLEAN bGoodVersion = 0; - PDRVMSG pMailBoxData; - USHORT *pUsData = NULL; - USHORT *pUsFile = NULL; - UCHAR *pUcFile = NULL; - UCHAR *pBootEnd = NULL; - UCHAR *pCodeEnd = NULL; + bool bGoodVersion = false; + struct drv_msg *pMailBoxData; + u16 *pUsData = NULL; + u16 *pUsFile = NULL; + u8 *pUcFile = NULL; + u8 *pBootEnd = NULL; + u8 *pCodeEnd = NULL; int imageN; long file_version; long loader_code_address = 0; @@ -346,36 +321,22 @@ int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) unsigned long templong; unsigned long image_chksum = 0; - // - // Get version id of file, at first 4 bytes of file, for newer files. - // file_version = *(long *)pFileStart; + if (file_version != 6) { + printk(KERN_ERR "ft1000: unsupported firmware version %ld\n", file_version); + Status = FAILURE; + } uiState = STATE_START_DWNLD; - pFileHdr = (PDSP_FILE_HDR) pFileStart; - pFileHdr5 = (PDSP_FILE_HDR_5) pFileStart; - - switch (file_version) { - case 5: - case 6: - pUsFile = - (USHORT *) ((long)pFileStart + pFileHdr5->loader_offset); - pUcFile = - (UCHAR *) ((long)pFileStart + pFileHdr5->loader_offset); - - pBootEnd = - (UCHAR *) ((long)pFileStart + pFileHdr5->loader_code_end); + pFileHdr5 = (struct dsp_file_hdr *) pFileStart; - loader_code_address = pFileHdr5->loader_code_address; - loader_code_size = pFileHdr5->loader_code_size; - bGoodVersion = FALSE; - break; - - default: - Status = FAILURE; - break; - } + pUsFile = (u16 *) ((long)pFileStart + pFileHdr5->loader_offset); + pUcFile = (u8 *) ((long)pFileStart + pFileHdr5->loader_offset); + pBootEnd = (u8 *) ((long)pFileStart + pFileHdr5->loader_code_end); + loader_code_address = pFileHdr5->loader_code_address; + loader_code_size = pFileHdr5->loader_code_size; + bGoodVersion = false; while ((Status == SUCCESS) && (uiState != STATE_DONE_FILE)) { @@ -384,11 +345,10 @@ int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) handshake = get_handshake(dev, HANDSHAKE_DSP_BL_READY); - if (handshake == HANDSHAKE_DSP_BL_READY) { + if (handshake == HANDSHAKE_DSP_BL_READY) put_handshake(dev, HANDSHAKE_DRIVER_READY); - } else { + else Status = FAILURE; - } uiState = STATE_BOOT_DWNLD; @@ -412,8 +372,8 @@ int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) break; case REQUEST_DONE_BL: /* Reposition ptrs to beginning of code section */ - pUsFile = (USHORT *) ((long)pBootEnd); - pUcFile = (UCHAR *) ((long)pBootEnd); + pUsFile = (u16 *) ((long)pBootEnd); + pUcFile = (u8 *) ((long)pBootEnd); uiState = STATE_CODE_DWNLD; break; case REQUEST_CODE_SEGMENT: @@ -430,48 +390,27 @@ int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) Status = FAILURE; break; } - // Provide mutual exclusive access while reading ASIC registers. + /* Provide mutual exclusive access while reading ASIC registers. */ spin_lock_irqsave(&info->dpram_lock, flags); - if (file_version == 5) { - /* - * Position ASIC DPRAM auto-increment pointer. - */ - ft1000_write_reg(dev, - FT1000_REG_DPRAM_ADDR, - DWNLD_PS_HDR_LOC); - - for (; word_length > 0; word_length--) { /* In words */ - //temp = *pUsFile; - //temp = RtlUshortByteSwap(temp); - ft1000_write_reg(dev, - FT1000_REG_DPRAM_DATA, - *pUsFile); - pUsFile++; - pUcFile += 2; - DspWordCnt++; - } - } else { - /* - * Position ASIC DPRAM auto-increment pointer. - */ - outw(DWNLD_MAG_PS_HDR_LOC, + /* + * Position ASIC DPRAM auto-increment pointer. + */ + outw(DWNLD_MAG_PS_HDR_LOC, + dev->base_addr + + FT1000_REG_DPRAM_ADDR); + if (word_length & 0x01) + word_length++; + word_length = word_length / 2; + + for (; word_length > 0; word_length--) { /* In words */ + templong = *pUsFile++; + templong |= + (*pUsFile++ << 16); + pUcFile += 4; + outl(templong, dev->base_addr + - FT1000_REG_DPRAM_ADDR); - if (word_length & 0x01) { - word_length++; - } - word_length = word_length / 2; - - for (; word_length > 0; word_length--) { /* In words */ - templong = *pUsFile++; - templong |= - (*pUsFile++ << 16); - pUcFile += 4; - outl(templong, - dev->base_addr + - FT1000_REG_MAG_DPDATAL); - } + FT1000_REG_MAG_DPDATAL); } spin_unlock_irqrestore(&info-> dpram_lock, @@ -521,24 +460,8 @@ int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) break; case REQUEST_DONE_CL: /* Reposition ptrs to beginning of provisioning section */ - switch (file_version) { - case 5: - case 6: - pUsFile = - (USHORT *) ((long)pFileStart - + - pFileHdr5-> - commands_offset); - pUcFile = - (UCHAR *) ((long)pFileStart - + - pFileHdr5-> - commands_offset); - break; - default: - Status = FAILURE; - break; - } + pUsFile = (u16 *) ((long)pFileStart + pFileHdr5->commands_offset); + pUcFile = (u8 *) ((long)pFileStart + pFileHdr5->commands_offset); uiState = STATE_DONE_DWNLD; break; case REQUEST_CODE_SEGMENT: @@ -559,58 +482,37 @@ int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) Status = FAILURE; break; } - if (file_version == 5) { - /* - * Position ASIC DPRAM auto-increment pointer. - */ - ft1000_write_reg(dev, - FT1000_REG_DPRAM_ADDR, - DWNLD_PS_HDR_LOC); - - for (; word_length > 0; word_length--) { /* In words */ - //temp = *pUsFile; - //temp = RtlUshortByteSwap(temp); - ft1000_write_reg(dev, - FT1000_REG_DPRAM_DATA, - *pUsFile); - pUsFile++; - pUcFile += 2; - DspWordCnt++; - } - } else { - /* - * Position ASIC DPRAM auto-increment pointer. - */ - outw(DWNLD_MAG_PS_HDR_LOC, + /* + * Position ASIC DPRAM auto-increment pointer. + */ + outw(DWNLD_MAG_PS_HDR_LOC, + dev->base_addr + + FT1000_REG_DPRAM_ADDR); + if (word_length & 0x01) + word_length++; + word_length = word_length / 2; + + for (; word_length > 0; word_length--) { /* In words */ + templong = *pUsFile++; + templong |= + (*pUsFile++ << 16); + pUcFile += 4; + outl(templong, dev->base_addr + - FT1000_REG_DPRAM_ADDR); - if (word_length & 0x01) { - word_length++; - } - word_length = word_length / 2; - - for (; word_length > 0; word_length--) { /* In words */ - templong = *pUsFile++; - templong |= - (*pUsFile++ << 16); - pUcFile += 4; - outl(templong, - dev->base_addr + - FT1000_REG_MAG_DPDATAL); - } + FT1000_REG_MAG_DPDATAL); } break; case REQUEST_MAILBOX_DATA: - // Convert length from byte count to word count. Make sure we round up. + /* Convert length from byte count to word count. Make sure we round up. */ word_length = (long)(info->DSPInfoBlklen + 1) / 2; put_request_value(dev, word_length); pMailBoxData = - (PDRVMSG) & info->DSPInfoBlk[0]; + (struct drv_msg *) &info->DSPInfoBlk[0]; pUsData = - (USHORT *) & pMailBoxData->data[0]; - // Provide mutual exclusive access while reading ASIC registers. + (u16 *) &pMailBoxData->data[0]; + /* Provide mutual exclusive access while reading ASIC registers. */ spin_lock_irqsave(&info->dpram_lock, flags); if (file_version == 5) { @@ -635,9 +537,9 @@ int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) outw(DWNLD_MAG_PS_HDR_LOC, dev->base_addr + FT1000_REG_DPRAM_ADDR); - if (word_length & 0x01) { + if (word_length & 0x01) word_length++; - } + word_length = word_length / 2; for (; word_length > 0; word_length--) { /* In words */ @@ -659,51 +561,32 @@ int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) pFileHdr5->version_data_size; put_request_value(dev, word_length); pUsFile = - (USHORT *) ((long)pFileStart + + (u16 *) ((long)pFileStart + pFileHdr5-> version_data_offset); - // Provide mutual exclusive access while reading ASIC registers. + /* Provide mutual exclusive access while reading ASIC registers. */ spin_lock_irqsave(&info->dpram_lock, flags); - if (file_version == 5) { - /* - * Position ASIC DPRAM auto-increment pointer. - */ - ft1000_write_reg(dev, - FT1000_REG_DPRAM_ADDR, - DWNLD_PS_HDR_LOC); - - for (; word_length > 0; word_length--) { /* In words */ - ft1000_write_reg(dev, - FT1000_REG_DPRAM_DATA, - *pUsFile - /*temp */ - ); - pUsFile++; - } - } else { - /* - * Position ASIC DPRAM auto-increment pointer. - */ - outw(DWNLD_MAG_PS_HDR_LOC, + /* + * Position ASIC DPRAM auto-increment pointer. + */ + outw(DWNLD_MAG_PS_HDR_LOC, + dev->base_addr + + FT1000_REG_DPRAM_ADDR); + if (word_length & 0x01) + word_length++; + word_length = word_length / 2; + + for (; word_length > 0; word_length--) { /* In words */ + templong = + ntohs(*pUsFile++); + temp = + ntohs(*pUsFile++); + templong |= + (temp << 16); + outl(templong, dev->base_addr + - FT1000_REG_DPRAM_ADDR); - if (word_length & 0x01) { - word_length++; - } - word_length = word_length / 2; - - for (; word_length > 0; word_length--) { /* In words */ - templong = - ntohs(*pUsFile++); - temp = - ntohs(*pUsFile++); - templong |= - (temp << 16); - outl(templong, - dev->base_addr + - FT1000_REG_MAG_DPDATAL); - } + FT1000_REG_MAG_DPDATAL); } spin_unlock_irqrestore(&info-> dpram_lock, @@ -711,120 +594,71 @@ int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) break; case REQUEST_CODE_BY_VERSION: - bGoodVersion = FALSE; + bGoodVersion = false; requested_version = get_request_value(dev); - if (file_version == 5) { - pDspImageInfo = - (PDSP_IMAGE_INFO) ((long) - pFileStart - + - sizeof - (DSP_FILE_HDR_5)); - for (imageN = 0; - imageN < - pFileHdr5->nDspImages; - imageN++) { - if (pDspImageInfo-> - version == - requested_version) { - bGoodVersion = - TRUE; - pUsFile = - (USHORT - *) ((long) - pFileStart - + - pDspImageInfo-> - begin_offset); - pUcFile = - (UCHAR - *) ((long) - pFileStart - + - pDspImageInfo-> - begin_offset); - pCodeEnd = - (UCHAR - *) ((long) - pFileStart - + - pDspImageInfo-> - end_offset); - run_address = - pDspImageInfo-> - run_address; - run_size = - pDspImageInfo-> - image_size; - break; - } - pDspImageInfo++; - } - } else { - pDspImageInfoV6 = - (PDSP_IMAGE_INFO_V6) ((long) - pFileStart - + - sizeof - (DSP_FILE_HDR_5)); - for (imageN = 0; - imageN < - pFileHdr5->nDspImages; - imageN++) { - temp = (USHORT) - (pDspImageInfoV6-> - version); - templong = temp; - temp = (USHORT) - (pDspImageInfoV6-> - version >> 16); - templong |= - (temp << 16); - if (templong == - requested_version) { - bGoodVersion = - TRUE; - pUsFile = - (USHORT - *) ((long) - pFileStart - + - pDspImageInfoV6-> - begin_offset); - pUcFile = - (UCHAR - *) ((long) - pFileStart - + - pDspImageInfoV6-> - begin_offset); - pCodeEnd = - (UCHAR - *) ((long) - pFileStart - + - pDspImageInfoV6-> - end_offset); - run_address = - pDspImageInfoV6-> - run_address; - run_size = - pDspImageInfoV6-> - image_size; - image_chksum = - (ULONG) - pDspImageInfoV6-> - checksum; - DEBUG(0, - "ft1000_dnld: image_chksum = 0x%8x\n", - (unsigned - int) - image_chksum); - break; - } - pDspImageInfoV6++; + pDspImageInfoV6 = + (struct dsp_image_info *) ((long) + pFileStart + + + sizeof + (struct dsp_file_hdr)); + for (imageN = 0; + imageN < + pFileHdr5->nDspImages; + imageN++) { + temp = (u16) + (pDspImageInfoV6-> + version); + templong = temp; + temp = (u16) + (pDspImageInfoV6-> + version >> 16); + templong |= + (temp << 16); + if (templong == + requested_version) { + bGoodVersion = + true; + pUsFile = + (u16 + *) ((long) + pFileStart + + + pDspImageInfoV6-> + begin_offset); + pUcFile = + (u8 + *) ((long) + pFileStart + + + pDspImageInfoV6-> + begin_offset); + pCodeEnd = + (u8 + *) ((long) + pFileStart + + + pDspImageInfoV6-> + end_offset); + run_address = + pDspImageInfoV6-> + run_address; + run_size = + pDspImageInfoV6-> + image_size; + image_chksum = + (u32) + pDspImageInfoV6-> + checksum; + DEBUG(0, + "ft1000_dnld: image_chksum = 0x%8x\n", + (unsigned + int) + image_chksum); + break; } + pDspImageInfoV6++; } if (!bGoodVersion) { /* @@ -847,17 +681,17 @@ int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) break; case STATE_DONE_DWNLD: - if (((UINT) (pUcFile) - (UINT) pFileStart) >= - (UINT) FileLength) { + if (((unsigned long) (pUcFile) - (unsigned long) pFileStart) >= + (unsigned long) FileLength) { uiState = STATE_DONE_FILE; break; } - pHdr = (PPSEUDO_HDR) pUsFile; + pHdr = (struct pseudo_hdr *) pUsFile; if (pHdr->portdest == 0x80 /* DspOAM */ && (pHdr->portsrc == 0x00 /* Driver */ - || pHdr->portsrc == 0x10 /* FMM */ )) { + || pHdr->portsrc == 0x10 /* FMM */)) { uiState = STATE_SECTION_PROV; } else { DEBUG(1, @@ -873,26 +707,26 @@ int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) case STATE_SECTION_PROV: - pHdr = (PPSEUDO_HDR) pUcFile; + pHdr = (struct pseudo_hdr *) pUcFile; if (pHdr->checksum == hdr_checksum(pHdr)) { - if (pHdr->portdest != 0x80 /* Dsp OAM */ ) { + if (pHdr->portdest != 0x80 /* Dsp OAM */) { uiState = STATE_DONE_PROV; break; } usHdrLength = ntohs(pHdr->length); /* Byte length for PROV records */ - // Get buffer for provisioning data + /* Get buffer for provisioning data */ pbuffer = - kmalloc((usHdrLength + sizeof(PSEUDO_HDR)), + kmalloc((usHdrLength + sizeof(struct pseudo_hdr)), GFP_ATOMIC); if (pbuffer) { memcpy(pbuffer, (void *)pUcFile, - (UINT) (usHdrLength + - sizeof(PSEUDO_HDR))); - // link provisioning data + (u32) (usHdrLength + + sizeof(struct pseudo_hdr))); + /* link provisioning data */ pprov_record = - kmalloc(sizeof(PROV_RECORD), + kmalloc(sizeof(struct prov_record), GFP_ATOMIC); if (pprov_record) { pprov_record->pprov_data = @@ -900,13 +734,13 @@ int card_download(struct net_device *dev, void *pFileStart, UINT FileLength) list_add_tail(&pprov_record-> list, &info->prov_list); - // Move to next entry if available + /* Move to next entry if available */ pUcFile = - (UCHAR *) ((UINT) pUcFile + - (UINT) ((usHdrLength + 1) & 0xFFFFFFFE) + sizeof(PSEUDO_HDR)); - if ((UINT) (pUcFile) - - (UINT) (pFileStart) >= - (UINT) FileLength) { + (u8 *) ((unsigned long) pUcFile + + (unsigned long) ((usHdrLength + 1) & 0xFFFFFFFE) + sizeof(struct pseudo_hdr)); + if ((unsigned long) (pUcFile) - + (unsigned long) (pFileStart) >= + (unsigned long) FileLength) { uiState = STATE_DONE_FILE; } diff --git a/drivers/staging/ft1000/ft1000-pcmcia/ft1000_hw.c b/drivers/staging/ft1000/ft1000-pcmcia/ft1000_hw.c index 588afd5a5dd..a6158bef58e 100644 --- a/drivers/staging/ft1000/ft1000-pcmcia/ft1000_hw.c +++ b/drivers/staging/ft1000/ft1000-pcmcia/ft1000_hw.c @@ -15,7 +15,7 @@ License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. ------------------------------------------------------------------------------*/ + -------------------------------------------------------------------------*/ #include <linux/kernel.h> #include <linux/module.h> @@ -29,7 +29,6 @@ #include <linux/interrupt.h> #include <linux/in.h> #include <asm/io.h> -#include <asm/system.h> #include <asm/bitops.h> #include <linux/netdevice.h> @@ -43,6 +42,10 @@ #include <linux/firmware.h> #include <linux/ethtool.h> +#include <pcmcia/cistpl.h> +#include <pcmcia/cisreg.h> +#include <pcmcia/ds.h> + #ifdef FT_DEBUG #define DEBUG(n, args...) printk(KERN_DEBUG args); #else @@ -50,19 +53,13 @@ #endif #include <linux/delay.h> -#include "ft1000_dev.h" #include "ft1000.h" -int card_download(struct net_device *dev, void *pFileStart, UINT FileLength); - -void ft1000InitProc(struct net_device *dev); -void ft1000CleanupProc(struct net_device *dev); - -const struct firmware *fw_entry; +static const struct firmware *fw_entry; static void ft1000_hbchk(u_long data); static struct timer_list poll_timer = { - function:ft1000_hbchk + .function = ft1000_hbchk }; static u16 cmdbuffer[1024]; @@ -83,83 +80,48 @@ MODULE_SUPPORTED_DEVICE("FT1000"); #define MAX_RCV_LOOP 100 -//--------------------------------------------------------------------------- -// -// Function: ft1000_asic_read -// Descripton: This function will retrieve the value of a specific ASIC -// register. -// Input: -// dev - network device structure -// offset - ASIC register to read -// Output: -// value - value of ASIC register -// -//--------------------------------------------------------------------------- -inline u16 ft1000_asic_read(struct net_device *dev, u16 offset) -{ - return (ft1000_read_reg(dev, offset)); -} - -//--------------------------------------------------------------------------- -// -// Function: ft1000_asic_write -// Descripton: This function will set the value of a specific ASIC -// register. -// Input: -// dev - network device structure -// value - value to set ASIC register -// Output: -// none -// -//--------------------------------------------------------------------------- -inline void ft1000_asic_write(struct net_device *dev, u16 offset, u16 value) -{ - ft1000_write_reg(dev, offset, value); -} +/*--------------------------------------------------------------------------- -//--------------------------------------------------------------------------- -// -// Function: ft1000_read_fifo_len -// Descripton: This function will read the ASIC Uplink FIFO status register -// which will return the number of bytes remaining in the Uplink FIFO. -// Sixteen bytes are subtracted to make sure that the ASIC does not -// reach its threshold. -// Input: -// dev - network device structure -// Output: -// value - number of bytes available in the ASIC Uplink FIFO. -// -//--------------------------------------------------------------------------- + Function: ft1000_read_fifo_len + Description: This function will read the ASIC Uplink FIFO status register + which will return the number of bytes remaining in the Uplink FIFO. + Sixteen bytes are subtracted to make sure that the ASIC does not + reach its threshold. + Input: + dev - network device structure + Output: + value - number of bytes available in the ASIC Uplink FIFO. + + -------------------------------------------------------------------------*/ static inline u16 ft1000_read_fifo_len(struct net_device *dev) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); - if (info->AsicID == ELECTRABUZZ_ID) { + if (info->AsicID == ELECTRABUZZ_ID) return (ft1000_read_reg(dev, FT1000_REG_UFIFO_STAT) - 16); - } else { + else return (ft1000_read_reg(dev, FT1000_REG_MAG_UFSR) - 16); - } } -//--------------------------------------------------------------------------- -// -// Function: ft1000_read_dpram -// Descripton: This function will read the specific area of dpram -// (Electrabuzz ASIC only) -// Input: -// dev - device structure -// offset - index of dpram -// Output: -// value - value of dpram -// -//--------------------------------------------------------------------------- -u16 ft1000_read_dpram(struct net_device * dev, int offset) +/*--------------------------------------------------------------------------- + + Function: ft1000_read_dpram + Description: This function will read the specific area of dpram + (Electrabuzz ASIC only) + Input: + dev - device structure + offset - index of dpram + Output: + value - value of dpram + + -------------------------------------------------------------------------*/ +u16 ft1000_read_dpram(struct net_device *dev, int offset) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); unsigned long flags; u16 data; - // Provide mutual exclusive access while reading ASIC registers. + /* Provide mutual exclusive access while reading ASIC registers. */ spin_lock_irqsave(&info->dpram_lock, flags); ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, offset); data = ft1000_read_reg(dev, FT1000_REG_DPRAM_DATA); @@ -168,54 +130,54 @@ u16 ft1000_read_dpram(struct net_device * dev, int offset) return (data); } -//--------------------------------------------------------------------------- -// -// Function: ft1000_write_dpram -// Descripton: This function will write to a specific area of dpram -// (Electrabuzz ASIC only) -// Input: -// dev - device structure -// offset - index of dpram -// value - value to write -// Output: -// none. -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + + Function: ft1000_write_dpram + Description: This function will write to a specific area of dpram + (Electrabuzz ASIC only) + Input: + dev - device structure + offset - index of dpram + value - value to write + Output: + none. + + -------------------------------------------------------------------------*/ static inline void ft1000_write_dpram(struct net_device *dev, int offset, u16 value) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); unsigned long flags; - // Provide mutual exclusive access while reading ASIC registers. + /* Provide mutual exclusive access while reading ASIC registers. */ spin_lock_irqsave(&info->dpram_lock, flags); ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, offset); ft1000_write_reg(dev, FT1000_REG_DPRAM_DATA, value); spin_unlock_irqrestore(&info->dpram_lock, flags); } -//--------------------------------------------------------------------------- -// -// Function: ft1000_read_dpram_mag_16 -// Descripton: This function will read the specific area of dpram -// (Magnemite ASIC only) -// Input: -// dev - device structure -// offset - index of dpram -// Output: -// value - value of dpram -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + + Function: ft1000_read_dpram_mag_16 + Description: This function will read the specific area of dpram + (Magnemite ASIC only) + Input: + dev - device structure + offset - index of dpram + Output: + value - value of dpram + + -------------------------------------------------------------------------*/ u16 ft1000_read_dpram_mag_16(struct net_device *dev, int offset, int Index) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); unsigned long flags; u16 data; - // Provide mutual exclusive access while reading ASIC registers. + /* Provide mutual exclusive access while reading ASIC registers. */ spin_lock_irqsave(&info->dpram_lock, flags); ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, offset); - // check if we want to read upper or lower 32-bit word + /* check if we want to read upper or lower 32-bit word */ if (Index) { data = ft1000_read_reg(dev, FT1000_REG_MAG_DPDATAL); } else { @@ -226,26 +188,26 @@ u16 ft1000_read_dpram_mag_16(struct net_device *dev, int offset, int Index) return (data); } -//--------------------------------------------------------------------------- -// -// Function: ft1000_write_dpram_mag_16 -// Descripton: This function will write to a specific area of dpram -// (Magnemite ASIC only) -// Input: -// dev - device structure -// offset - index of dpram -// value - value to write -// Output: -// none. -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + + Function: ft1000_write_dpram_mag_16 + Description: This function will write to a specific area of dpram + (Magnemite ASIC only) + Input: + dev - device structure + offset - index of dpram + value - value to write + Output: + none. + + -------------------------------------------------------------------------*/ static inline void ft1000_write_dpram_mag_16(struct net_device *dev, int offset, u16 value, int Index) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); unsigned long flags; - // Provide mutual exclusive access while reading ASIC registers. + /* Provide mutual exclusive access while reading ASIC registers. */ spin_lock_irqsave(&info->dpram_lock, flags); ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, offset); if (Index) { @@ -256,25 +218,25 @@ static inline void ft1000_write_dpram_mag_16(struct net_device *dev, spin_unlock_irqrestore(&info->dpram_lock, flags); } -//--------------------------------------------------------------------------- -// -// Function: ft1000_read_dpram_mag_32 -// Descripton: This function will read the specific area of dpram -// (Magnemite ASIC only) -// Input: -// dev - device structure -// offset - index of dpram -// Output: -// value - value of dpram -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + + Function: ft1000_read_dpram_mag_32 + Description: This function will read the specific area of dpram + (Magnemite ASIC only) + Input: + dev - device structure + offset - index of dpram + Output: + value - value of dpram + + -------------------------------------------------------------------------*/ u32 ft1000_read_dpram_mag_32(struct net_device *dev, int offset) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); unsigned long flags; u32 data; - // Provide mutual exclusive access while reading ASIC registers. + /* Provide mutual exclusive access while reading ASIC registers. */ spin_lock_irqsave(&info->dpram_lock, flags); ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, offset); data = inl(dev->base_addr + FT1000_REG_MAG_DPDATAL); @@ -283,69 +245,65 @@ u32 ft1000_read_dpram_mag_32(struct net_device *dev, int offset) return (data); } -//--------------------------------------------------------------------------- -// -// Function: ft1000_write_dpram_mag_32 -// Descripton: This function will write to a specific area of dpram -// (Magnemite ASIC only) -// Input: -// dev - device structure -// offset - index of dpram -// value - value to write -// Output: -// none. -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + + Function: ft1000_write_dpram_mag_32 + Description: This function will write to a specific area of dpram + (Magnemite ASIC only) + Input: + dev - device structure + offset - index of dpram + value - value to write + Output: + none. + + -------------------------------------------------------------------------*/ void ft1000_write_dpram_mag_32(struct net_device *dev, int offset, u32 value) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); unsigned long flags; - // Provide mutual exclusive access while reading ASIC registers. + /* Provide mutual exclusive access while reading ASIC registers. */ spin_lock_irqsave(&info->dpram_lock, flags); ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, offset); outl(value, dev->base_addr + FT1000_REG_MAG_DPDATAL); spin_unlock_irqrestore(&info->dpram_lock, flags); } -//--------------------------------------------------------------------------- -// -// Function: ft1000_enable_interrupts -// Descripton: This function will enable interrupts base on the current interrupt mask. -// Input: -// dev - device structure -// Output: -// None. -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + + Function: ft1000_enable_interrupts + Description: This function will enable interrupts base on the current interrupt mask. + Input: + dev - device structure + Output: + None. + + -------------------------------------------------------------------------*/ static void ft1000_enable_interrupts(struct net_device *dev) { - FT1000_INFO *info = netdev_priv(dev); u16 tempword; DEBUG(1, "ft1000_hw:ft1000_enable_interrupts()\n"); - ft1000_write_reg(dev, FT1000_REG_SUP_IMASK, - info->CurrentInterruptEnableMask); + ft1000_write_reg(dev, FT1000_REG_SUP_IMASK, ISR_DEFAULT_MASK); tempword = ft1000_read_reg(dev, FT1000_REG_SUP_IMASK); DEBUG(1, "ft1000_hw:ft1000_enable_interrupts:current interrupt enable mask = 0x%x\n", tempword); - info->InterruptsEnabled = TRUE; } -//--------------------------------------------------------------------------- -// -// Function: ft1000_disable_interrupts -// Descripton: This function will disable all interrupts. -// Input: -// dev - device structure -// Output: -// None. -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + + Function: ft1000_disable_interrupts + Description: This function will disable all interrupts. + Input: + dev - device structure + Output: + None. + + -------------------------------------------------------------------------*/ static void ft1000_disable_interrupts(struct net_device *dev) { - FT1000_INFO *info = netdev_priv(dev); u16 tempword; DEBUG(1, "ft1000_hw: ft1000_disable_interrupts()\n"); @@ -354,45 +312,46 @@ static void ft1000_disable_interrupts(struct net_device *dev) DEBUG(1, "ft1000_hw:ft1000_disable_interrupts:current interrupt enable mask = 0x%x\n", tempword); - info->InterruptsEnabled = FALSE; } -//--------------------------------------------------------------------------- -// -// Function: ft1000_reset_asic -// Descripton: This function will call the Card Service function to reset the -// ASIC. -// Input: -// dev - device structure -// Output: -// none -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + + Function: ft1000_reset_asic + Description: This function will call the Card Service function to reset the + ASIC. + Input: + dev - device structure + Output: + none + + -------------------------------------------------------------------------*/ static void ft1000_reset_asic(struct net_device *dev) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); + struct ft1000_pcmcia *pcmcia = info->priv; u16 tempword; DEBUG(1, "ft1000_hw:ft1000_reset_asic called\n"); - (*info->ft1000_reset) (info->link); - info->ASICResetNum++; + (*info->ft1000_reset) (pcmcia->link); - // Let's use the register provided by the Magnemite ASIC to reset the - // ASIC and DSP. + /* + * Let's use the register provided by the Magnemite ASIC to reset the + * ASIC and DSP. + */ if (info->AsicID == MAGNEMITE_ID) { ft1000_write_reg(dev, FT1000_REG_RESET, (DSP_RESET_BIT | ASIC_RESET_BIT)); } mdelay(1); if (info->AsicID == ELECTRABUZZ_ID) { - // set watermark to -1 in order to not generate an interrrupt + /* set watermark to -1 in order to not generate an interrupt */ ft1000_write_reg(dev, FT1000_REG_WATERMARK, 0xffff); } else { - // set watermark to -1 in order to not generate an interrrupt + /* set watermark to -1 in order to not generate an interrupt */ ft1000_write_reg(dev, FT1000_REG_MAG_WATERMARK, 0xffff); } - // clear interrupts + /* clear interrupts */ tempword = ft1000_read_reg(dev, FT1000_REG_SUP_ISR); DEBUG(1, "ft1000_hw: interrupt status register = 0x%x\n", tempword); ft1000_write_reg(dev, FT1000_REG_SUP_ISR, tempword); @@ -401,24 +360,24 @@ static void ft1000_reset_asic(struct net_device *dev) } -//--------------------------------------------------------------------------- -// -// Function: ft1000_reset_card -// Descripton: This function will reset the card -// Input: -// dev - device structure -// Output: -// status - FALSE (card reset fail) -// TRUE (card reset successful) -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + + Function: ft1000_reset_card + Description: This function will reset the card + Input: + dev - device structure + Output: + status - false (card reset fail) + true (card reset successful) + + -------------------------------------------------------------------------*/ static int ft1000_reset_card(struct net_device *dev) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); u16 tempword; int i; unsigned long flags; - PPROV_RECORD ptr; + struct prov_record *ptr; DEBUG(1, "ft1000_hw:ft1000_reset_card called.....\n"); @@ -427,13 +386,13 @@ static int ft1000_reset_card(struct net_device *dev) info->squeseqnum = 0; ft1000_disable_interrupts(dev); -// del_timer(&poll_timer); + /* del_timer(&poll_timer); */ - // Make sure we free any memory reserve for provisioning + /* Make sure we free any memory reserve for provisioning */ while (list_empty(&info->prov_list) == 0) { DEBUG(0, "ft1000_hw:ft1000_reset_card:deleting provisioning record\n"); - ptr = list_entry(info->prov_list.next, PROV_RECORD, list); + ptr = list_entry(info->prov_list.next, struct prov_record, list); list_del(&ptr->list); kfree(ptr->pprov_data); kfree(ptr); @@ -449,18 +408,16 @@ static int ft1000_reset_card(struct net_device *dev) (DSP_RESET_BIT | ASIC_RESET_BIT)); } - // Copy DSP session record into info block if this is not a coldstart + /* Copy DSP session record into info block if this is not a coldstart */ if (ft1000_card_present == 1) { spin_lock_irqsave(&info->dpram_lock, flags); if (info->AsicID == ELECTRABUZZ_ID) { - if (info->DspHibernateFlag == 0) { - ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, - FT1000_DPRAM_RX_BASE); - for (i = 0; i < MAX_DSP_SESS_REC; i++) { - info->DSPSess.Rec[i] = - ft1000_read_reg(dev, - FT1000_REG_DPRAM_DATA); - } + ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, + FT1000_DPRAM_RX_BASE); + for (i = 0; i < MAX_DSP_SESS_REC; i++) { + info->DSPSess.Rec[i] = + ft1000_read_reg(dev, + FT1000_REG_DPRAM_DATA); } } else { ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, @@ -475,31 +432,29 @@ static int ft1000_reset_card(struct net_device *dev) DEBUG(1, "ft1000_hw:ft1000_reset_card:resetting ASIC\n"); mdelay(10); - //reset ASIC + /* reset ASIC */ ft1000_reset_asic(dev); - info->DSPResetNum++; - DEBUG(1, "ft1000_hw:ft1000_reset_card:downloading dsp image\n"); if (info->AsicID == MAGNEMITE_ID) { - // Put dsp in reset and take ASIC out of reset + /* Put dsp in reset and take ASIC out of reset */ DEBUG(0, "ft1000_hw:ft1000_reset_card:Put DSP in reset and take ASIC out of reset\n"); ft1000_write_reg(dev, FT1000_REG_RESET, DSP_RESET_BIT); - // Setting MAGNEMITE ASIC to big endian mode + /* Setting MAGNEMITE ASIC to big endian mode */ ft1000_write_reg(dev, FT1000_REG_SUP_CTRL, HOST_INTF_BE); - // Download bootloader + /* Download bootloader */ card_bootload(dev); - // Take DSP out of reset + /* Take DSP out of reset */ ft1000_write_reg(dev, FT1000_REG_RESET, 0); - // FLARION_DSP_ACTIVE; + /* FLARION_DSP_ACTIVE; */ mdelay(10); DEBUG(0, "ft1000_hw:ft1000_reset_card:Take DSP out of reset\n"); - // Wait for 0xfefe indicating dsp ready before starting download + /* Wait for 0xfefe indicating dsp ready before starting download */ for (i = 0; i < 50; i++) { tempword = ft1000_read_dpram_mag_16(dev, FT1000_MAG_DPRAM_FEFE, @@ -513,18 +468,18 @@ static int ft1000_reset_card(struct net_device *dev) if (i == 50) { DEBUG(0, "ft1000_hw:ft1000_reset_card:No FEFE detected from DSP\n"); - return FALSE; + return false; } } else { - // Take DSP out of reset + /* Take DSP out of reset */ ft1000_write_reg(dev, FT1000_REG_RESET, ~DSP_RESET_BIT); mdelay(10); } if (card_download(dev, fw_entry->data, fw_entry->size)) { DEBUG(1, "card download unsuccessful\n"); - return FALSE; + return false; } else { DEBUG(1, "card download successful\n"); } @@ -532,17 +487,19 @@ static int ft1000_reset_card(struct net_device *dev) mdelay(10); if (info->AsicID == ELECTRABUZZ_ID) { - // Need to initialize the FIFO length counter to zero in order to sync up - // with the DSP + /* + * Need to initialize the FIFO length counter to zero in order to sync up + * with the DSP + */ info->fifo_cnt = 0; ft1000_write_dpram(dev, FT1000_FIFO_LEN, info->fifo_cnt); - // Initialize DSP heartbeat area to ho + /* Initialize DSP heartbeat area to ho */ ft1000_write_dpram(dev, FT1000_HI_HO, ho); tempword = ft1000_read_dpram(dev, FT1000_HI_HO); DEBUG(1, "ft1000_hw:ft1000_reset_asic:hi_ho value = 0x%x\n", tempword); } else { - // Initialize DSP heartbeat area to ho + /* Initialize DSP heartbeat area to ho */ ft1000_write_dpram_mag_16(dev, FT1000_MAG_HI_HO, ho_mag, FT1000_MAG_HI_HO_INDX); tempword = @@ -556,72 +513,76 @@ static int ft1000_reset_card(struct net_device *dev) ft1000_enable_interrupts(dev); /* Schedule heartbeat process to run every 2 seconds */ -// poll_timer.expires = jiffies + (2*HZ); -// poll_timer.data = (u_long)dev; -// add_timer(&poll_timer); + /* poll_timer.expires = jiffies + (2*HZ); */ + /* poll_timer.data = (u_long)dev; */ + /* add_timer(&poll_timer); */ - return TRUE; + return true; } -//--------------------------------------------------------------------------- -// -// Function: ft1000_chkcard -// Descripton: This function will check if the device is presently available on -// the system. -// Input: -// dev - device structure -// Output: -// status - FALSE (device is not present) -// TRUE (device is present) -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + + Function: ft1000_chkcard + Description: This function will check if the device is presently available on + the system. + Input: + dev - device structure + Output: + status - false (device is not present) + true (device is present) + + -------------------------------------------------------------------------*/ static int ft1000_chkcard(struct net_device *dev) { u16 tempword; - // Mask register is used to check for device presence since it is never - // set to zero. + /* + * Mask register is used to check for device presence since it is never + * set to zero. + */ tempword = ft1000_read_reg(dev, FT1000_REG_SUP_IMASK); if (tempword == 0) { DEBUG(1, "ft1000_hw:ft1000_chkcard: IMASK = 0 Card not detected\n"); - return FALSE; + return false; } - // The system will return the value of 0xffff for the version register - // if the device is not present. + /* + * The system will return the value of 0xffff for the version register + * if the device is not present. + */ tempword = ft1000_read_reg(dev, FT1000_REG_ASIC_ID); if (tempword == 0xffff) { DEBUG(1, "ft1000_hw:ft1000_chkcard: Version = 0xffff Card not detected\n"); - return FALSE; + return false; } - return TRUE; + return true; } -//--------------------------------------------------------------------------- -// -// Function: ft1000_hbchk -// Descripton: This function will perform the heart beat check of the DSP as -// well as the ASIC. -// Input: -// dev - device structure -// Output: -// none -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + + Function: ft1000_hbchk + Description: This function will perform the heart beat check of the DSP as + well as the ASIC. + Input: + dev - device structure + Output: + none + + -------------------------------------------------------------------------*/ static void ft1000_hbchk(u_long data) { struct net_device *dev = (struct net_device *)data; - FT1000_INFO *info; - USHORT tempword; + struct ft1000_info *info; + u16 tempword; info = netdev_priv(dev); if (info->CardReady == 1) { - // Perform dsp heartbeat check + /* Perform dsp heartbeat check */ if (info->AsicID == ELECTRABUZZ_ID) { tempword = ft1000_read_dpram(dev, FT1000_HI_HO); } else { @@ -632,7 +593,7 @@ static void ft1000_hbchk(u_long data) } DEBUG(1, "ft1000_hw:ft1000_hbchk:hi_ho value = 0x%x\n", tempword); - // Let's perform another check if ho is not detected + /* Let's perform another check if ho is not detected */ if (tempword != ho) { if (info->AsicID == ELECTRABUZZ_ID) { tempword = ft1000_read_dpram(dev, FT1000_HI_HO); @@ -686,7 +647,7 @@ static void ft1000_hbchk(u_long data) } tempword = ft1000_read_reg(dev, FT1000_REG_DOORBELL); - // Let's check doorbell again if fail + /* Let's check doorbell again if fail */ if (tempword & FT1000_DB_HB) { tempword = ft1000_read_reg(dev, FT1000_REG_DOORBELL); } @@ -733,8 +694,10 @@ static void ft1000_hbchk(u_long data) add_timer(&poll_timer); return; } - // Set dedicated area to hi and ring appropriate doorbell according - // to hi/ho heartbeat protocol + /* + * Set dedicated area to hi and ring appropriate doorbell according + * to hi/ho heartbeat protocol + */ if (info->AsicID == ELECTRABUZZ_ID) { ft1000_write_dpram(dev, FT1000_HI_HO, hi); } else { @@ -750,7 +713,7 @@ static void ft1000_hbchk(u_long data) (dev, FT1000_MAG_HI_HO, FT1000_MAG_HI_HO_INDX)); } - // Let's write hi again if fail + /* Let's write hi again if fail */ if (tempword != hi) { if (info->AsicID == ELECTRABUZZ_ID) { ft1000_write_dpram(dev, FT1000_HI_HO, hi); @@ -821,33 +784,35 @@ static void ft1000_hbchk(u_long data) add_timer(&poll_timer); } -//--------------------------------------------------------------------------- -// -// Function: ft1000_send_cmd -// Descripton: -// Input: -// Output: -// -//--------------------------------------------------------------------------- -void ft1000_send_cmd (struct net_device *dev, u16 *ptempbuffer, int size, u16 qtype) +/*--------------------------------------------------------------------------- + + Function: ft1000_send_cmd + Description: + Input: + Output: + + -------------------------------------------------------------------------*/ +static void ft1000_send_cmd (struct net_device *dev, u16 *ptempbuffer, int size, u16 qtype) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); int i; u16 tempword; unsigned long flags; - size += PSEUDOSZ; - // check for odd byte and increment to 16-bit word align value + size += sizeof(struct pseudo_hdr); + /* check for odd byte and increment to 16-bit word align value */ if ((size & 0x0001)) { size++; } DEBUG(1, "FT1000:ft1000_send_cmd:total length = %d\n", size); DEBUG(1, "FT1000:ft1000_send_cmd:length = %d\n", ntohs(*ptempbuffer)); - // put message into slow queue area - // All messages are in the form total_len + pseudo header + message body + /* + * put message into slow queue area + * All messages are in the form total_len + pseudo header + message body + */ spin_lock_irqsave(&info->dpram_lock, flags); - // Make sure SLOWQ doorbell is clear + /* Make sure SLOWQ doorbell is clear */ tempword = ft1000_read_reg(dev, FT1000_REG_DOORBELL); i=0; while (tempword & FT1000_DB_DPRAM_TX) { @@ -863,9 +828,9 @@ void ft1000_send_cmd (struct net_device *dev, u16 *ptempbuffer, int size, u16 qt if (info->AsicID == ELECTRABUZZ_ID) { ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, FT1000_DPRAM_TX_BASE); - // Write total length to dpram + /* Write total length to dpram */ ft1000_write_reg(dev, FT1000_REG_DPRAM_DATA, size); - // Write pseudo header and messgae body + /* Write pseudo header and messgae body */ for (i = 0; i < (size >> 1); i++) { DEBUG(1, "FT1000:ft1000_send_cmd:data %d = 0x%x\n", i, *ptempbuffer); @@ -875,9 +840,9 @@ void ft1000_send_cmd (struct net_device *dev, u16 *ptempbuffer, int size, u16 qt } else { ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, FT1000_DPRAM_MAG_TX_BASE); - // Write total length to dpram + /* Write total length to dpram */ ft1000_write_reg(dev, FT1000_REG_MAG_DPDATAH, htons(size)); - // Write pseudo header and messgae body + /* Write pseudo header and messgae body */ ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, FT1000_DPRAM_MAG_TX_BASE + 1); for (i = 0; i < (size >> 2); i++) { @@ -897,26 +862,27 @@ void ft1000_send_cmd (struct net_device *dev, u16 *ptempbuffer, int size, u16 qt } spin_unlock_irqrestore(&info->dpram_lock, flags); - // ring doorbell to notify DSP that we have a message ready + /* ring doorbell to notify DSP that we have a message ready */ ft1000_write_reg(dev, FT1000_REG_DOORBELL, FT1000_DB_DPRAM_TX); } -//--------------------------------------------------------------------------- -// -// Function: ft1000_receive_cmd -// Descripton: This function will read a message from the dpram area. -// Input: -// dev - network device structure -// pbuffer - caller supply address to buffer -// pnxtph - pointer to next pseudo header -// Output: -// Status = 0 (unsuccessful) -// = 1 (successful) -// -//--------------------------------------------------------------------------- -BOOLEAN ft1000_receive_cmd(struct net_device *dev, u16 * pbuffer, int maxsz, u16 *pnxtph) +/*--------------------------------------------------------------------------- + + Function: ft1000_receive_cmd + Description: This function will read a message from the dpram area. + Input: + dev - network device structure + pbuffer - caller supply address to buffer + pnxtph - pointer to next pseudo header + Output: + Status = 0 (unsuccessful) + = 1 (successful) + + -------------------------------------------------------------------------*/ +static bool ft1000_receive_cmd(struct net_device *dev, u16 *pbuffer, + int maxsz, u16 *pnxtph) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); u16 size; u16 *ppseudohdr; int i; @@ -924,18 +890,18 @@ BOOLEAN ft1000_receive_cmd(struct net_device *dev, u16 * pbuffer, int maxsz, u16 unsigned long flags; if (info->AsicID == ELECTRABUZZ_ID) { - size = ( ft1000_read_dpram(dev, *pnxtph) ) + PSEUDOSZ; + size = ( ft1000_read_dpram(dev, *pnxtph) ) + sizeof(struct pseudo_hdr); } else { size = ntohs(ft1000_read_dpram_mag_16 (dev, FT1000_MAG_PH_LEN, - FT1000_MAG_PH_LEN_INDX)) + PSEUDOSZ; + FT1000_MAG_PH_LEN_INDX)) + sizeof(struct pseudo_hdr); } if (size > maxsz) { DEBUG(1, "FT1000:ft1000_receive_cmd:Invalid command length = %d\n", size); - return FALSE; + return false; } else { ppseudohdr = (u16 *) pbuffer; spin_lock_irqsave(&info->dpram_lock, flags); @@ -965,7 +931,7 @@ BOOLEAN ft1000_receive_cmd(struct net_device *dev, u16 * pbuffer, int maxsz, u16 FT1000_REG_MAG_DPDATAH); pbuffer++; } - //copy odd aligned word + /* copy odd aligned word */ *pbuffer = inw(dev->base_addr + FT1000_REG_MAG_DPDATAL); DEBUG(1, "ft1000_hw:received data = 0x%x\n", *pbuffer); pbuffer++; @@ -974,14 +940,16 @@ BOOLEAN ft1000_receive_cmd(struct net_device *dev, u16 * pbuffer, int maxsz, u16 pbuffer++; } if (size & 0x0001) { - //copy odd byte from fifo + /* copy odd byte from fifo */ tempword = ft1000_read_reg(dev, FT1000_REG_DPRAM_DATA); *pbuffer = ntohs(tempword); } spin_unlock_irqrestore(&info->dpram_lock, flags); - // Check if pseudo header checksum is good - // Calculate pseudo header checksum + /* + * Check if pseudo header checksum is good + * Calculate pseudo header checksum + */ tempword = *ppseudohdr++; for (i = 1; i < 7; i++) { tempword ^= *ppseudohdr++; @@ -989,37 +957,37 @@ BOOLEAN ft1000_receive_cmd(struct net_device *dev, u16 * pbuffer, int maxsz, u16 if ((tempword != *ppseudohdr)) { DEBUG(1, "FT1000:ft1000_receive_cmd:Pseudo header checksum mismatch\n"); - // Drop this message - return FALSE; + /* Drop this message */ + return false; } - return TRUE; + return true; } } -//--------------------------------------------------------------------------- -// -// Function: ft1000_proc_drvmsg -// Descripton: This function will process the various driver messages. -// Input: -// dev - device structure -// pnxtph - pointer to next pseudo header -// Output: -// none -// -//--------------------------------------------------------------------------- -void ft1000_proc_drvmsg(struct net_device *dev) +/*--------------------------------------------------------------------------- + + Function: ft1000_proc_drvmsg + Description: This function will process the various driver messages. + Input: + dev - device structure + pnxtph - pointer to next pseudo header + Output: + none + + -------------------------------------------------------------------------*/ +static void ft1000_proc_drvmsg(struct net_device *dev) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); u16 msgtype; u16 tempword; - PMEDIAMSG pmediamsg; - PDSPINITMSG pdspinitmsg; - PDRVMSG pdrvmsg; + struct media_msg *pmediamsg; + struct dsp_init_msg *pdspinitmsg; + struct drv_msg *pdrvmsg; u16 len; u16 i; - PPROV_RECORD ptr; - PPSEUDO_HDR ppseudo_hdr; - PUSHORT pmsg; + struct prov_record *ptr; + struct pseudo_hdr *ppseudo_hdr; + u16 *pmsg; struct timeval tv; union { u8 byte[2]; @@ -1034,8 +1002,8 @@ void ft1000_proc_drvmsg(struct net_device *dev) } if ( ft1000_receive_cmd(dev, &cmdbuffer[0], MAX_CMD_SQSIZE, &tempword) ) { - // Get the message type which is total_len + PSEUDO header + msgtype + message body - pdrvmsg = (PDRVMSG) & cmdbuffer[0]; + /* Get the message type which is total_len + PSEUDO header + msgtype + message body */ + pdrvmsg = (struct drv_msg *) & cmdbuffer[0]; msgtype = ntohs(pdrvmsg->type); DEBUG(1, "Command message type = 0x%x\n", msgtype); switch (msgtype) { @@ -1045,7 +1013,7 @@ void ft1000_proc_drvmsg(struct net_device *dev) mdelay(25); while (list_empty(&info->prov_list) == 0) { DEBUG(0, "Sending a provisioning message\n"); - // Make sure SLOWQ doorbell is clear + /* Make sure SLOWQ doorbell is clear */ tempword = ft1000_read_reg(dev, FT1000_REG_DOORBELL); i = 0; @@ -1058,16 +1026,16 @@ void ft1000_proc_drvmsg(struct net_device *dev) } ptr = list_entry(info->prov_list.next, - PROV_RECORD, list); + struct prov_record, list); len = *(u16 *) ptr->pprov_data; len = htons(len); - pmsg = (PUSHORT) ptr->pprov_data; - ppseudo_hdr = (PPSEUDO_HDR) pmsg; - // Insert slow queue sequence number + pmsg = (u16 *) ptr->pprov_data; + ppseudo_hdr = (struct pseudo_hdr *) pmsg; + /* Insert slow queue sequence number */ ppseudo_hdr->seq_num = info->squeseqnum++; ppseudo_hdr->portsrc = 0; - // Calculate new checksum + /* Calculate new checksum */ ppseudo_hdr->checksum = *pmsg++; DEBUG(1, "checksum = 0x%x\n", ppseudo_hdr->checksum); @@ -1082,12 +1050,14 @@ void ft1000_proc_drvmsg(struct net_device *dev) kfree(ptr->pprov_data); kfree(ptr); } - // Indicate adapter is ready to take application messages after all - // provisioning messages are sent + /* + * Indicate adapter is ready to take application messages after all + * provisioning messages are sent + */ info->CardReady = 1; break; case MEDIA_STATE: - pmediamsg = (PMEDIAMSG) & cmdbuffer[0]; + pmediamsg = (struct media_msg *) & cmdbuffer[0]; if (info->ProgConStat != 0xFF) { if (pmediamsg->state) { DEBUG(1, "Media is up\n"); @@ -1119,7 +1089,7 @@ void ft1000_proc_drvmsg(struct net_device *dev) } break; case DSP_INIT_MSG: - pdspinitmsg = (PDSPINITMSG) & cmdbuffer[0]; + pdspinitmsg = (struct dsp_init_msg *) & cmdbuffer[0]; memcpy(info->DspVer, pdspinitmsg->DspVer, DSPVERSZ); DEBUG(1, "DSPVER = 0x%2x 0x%2x 0x%2x 0x%2x\n", info->DspVer[0], info->DspVer[1], info->DspVer[2], @@ -1136,7 +1106,7 @@ void ft1000_proc_drvmsg(struct net_device *dev) dev->dev_addr[5] = info->eui64[7]; if (ntohs(pdspinitmsg->length) == - (sizeof(DSPINITMSG) - 20)) { + (sizeof(struct dsp_init_msg) - 20)) { memcpy(info->ProductMode, pdspinitmsg->ProductMode, MODESZ); memcpy(info->RfCalVer, pdspinitmsg->RfCalVer, @@ -1153,7 +1123,7 @@ void ft1000_proc_drvmsg(struct net_device *dev) tempword = ntohs(pdrvmsg->length); info->DSPInfoBlklen = tempword; if (tempword < (MAX_DSP_SESS_REC - 4)) { - pmsg = (PUSHORT) & pdrvmsg->data[0]; + pmsg = (u16 *) & pdrvmsg->data[0]; for (i = 0; i < ((tempword + 1) / 2); i++) { DEBUG(1, "FT1000:drivermsg:dsp info data = 0x%x\n", @@ -1164,9 +1134,10 @@ void ft1000_proc_drvmsg(struct net_device *dev) break; case DSP_GET_INFO: DEBUG(1, "FT1000:drivermsg:Got DSP_GET_INFO\n"); - // copy dsp info block to dsp - info->DrvMsgPend = 1; - // allow any outstanding ioctl to finish + /* + * copy dsp info block to dsp + * allow any outstanding ioctl to finish + */ mdelay(10); tempword = ft1000_read_reg(dev, FT1000_REG_DOORBELL); if (tempword & FT1000_DB_DPRAM_TX) { @@ -1179,10 +1150,12 @@ void ft1000_proc_drvmsg(struct net_device *dev) } if ((tempword & FT1000_DB_DPRAM_TX) == 0) { - // Put message into Slow Queue - // Form Pseudo header - pmsg = (PUSHORT) info->DSPInfoBlk; - ppseudo_hdr = (PPSEUDO_HDR) pmsg; + /* + * Put message into Slow Queue + * Form Pseudo header + */ + pmsg = (u16 *) info->DSPInfoBlk; + ppseudo_hdr = (struct pseudo_hdr *) pmsg; ppseudo_hdr->length = htons(info->DSPInfoBlklen + 4); ppseudo_hdr->source = 0x10; @@ -1194,11 +1167,11 @@ void ft1000_proc_drvmsg(struct net_device *dev) ppseudo_hdr->rsvd1 = 0; ppseudo_hdr->rsvd2 = 0; ppseudo_hdr->qos_class = 0; - // Insert slow queue sequence number + /* Insert slow queue sequence number */ ppseudo_hdr->seq_num = info->squeseqnum++; - // Insert application id + /* Insert application id */ ppseudo_hdr->portsrc = 0; - // Calculate new checksum + /* Calculate new checksum */ ppseudo_hdr->checksum = *pmsg++; for (i = 1; i < 7; i++) { ppseudo_hdr->checksum ^= *pmsg++; @@ -1206,16 +1179,16 @@ void ft1000_proc_drvmsg(struct net_device *dev) info->DSPInfoBlk[8] = 0x7200; info->DSPInfoBlk[9] = htons(info->DSPInfoBlklen); - ft1000_send_cmd (dev, (PUSHORT)info->DSPInfoBlk, (USHORT)(info->DSPInfoBlklen+4), 0); + ft1000_send_cmd (dev, (u16 *)info->DSPInfoBlk, (u16)(info->DSPInfoBlklen+4), 0); } - info->DrvMsgPend = 0; break; case GET_DRV_ERR_RPT_MSG: DEBUG(1, "FT1000:drivermsg:Got GET_DRV_ERR_RPT_MSG\n"); - // copy driver error message to dsp - info->DrvMsgPend = 1; - // allow any outstanding ioctl to finish + /* + * copy driver error message to dsp + * allow any outstanding ioctl to finish + */ mdelay(10); tempword = ft1000_read_reg(dev, FT1000_REG_DOORBELL); if (tempword & FT1000_DB_DPRAM_TX) { @@ -1228,10 +1201,12 @@ void ft1000_proc_drvmsg(struct net_device *dev) } if ((tempword & FT1000_DB_DPRAM_TX) == 0) { - // Put message into Slow Queue - // Form Pseudo header - pmsg = (PUSHORT) & tempbuffer[0]; - ppseudo_hdr = (PPSEUDO_HDR) pmsg; + /* + * Put message into Slow Queue + * Form Pseudo header + */ + pmsg = (u16 *) & tempbuffer[0]; + ppseudo_hdr = (struct pseudo_hdr *) pmsg; ppseudo_hdr->length = htons(0x0012); ppseudo_hdr->source = 0x10; ppseudo_hdr->destination = 0x20; @@ -1242,16 +1217,16 @@ void ft1000_proc_drvmsg(struct net_device *dev) ppseudo_hdr->rsvd1 = 0; ppseudo_hdr->rsvd2 = 0; ppseudo_hdr->qos_class = 0; - // Insert slow queue sequence number + /* Insert slow queue sequence number */ ppseudo_hdr->seq_num = info->squeseqnum++; - // Insert application id + /* Insert application id */ ppseudo_hdr->portsrc = 0; - // Calculate new checksum + /* Calculate new checksum */ ppseudo_hdr->checksum = *pmsg++; for (i=1; i<7; i++) { ppseudo_hdr->checksum ^= *pmsg++; } - pmsg = (PUSHORT) & tempbuffer[16]; + pmsg = (u16 *) & tempbuffer[16]; *pmsg++ = htons(RSP_DRV_ERR_RPT_MSG); *pmsg++ = htons(0x000e); *pmsg++ = htons(info->DSP_TIME[0]); @@ -1266,10 +1241,9 @@ void ft1000_proc_drvmsg(struct net_device *dev) *pmsg++ = convert.wrd; *pmsg++ = htons(info->DrvErrNum); - ft1000_send_cmd (dev, (PUSHORT)&tempbuffer[0], (USHORT)(0x0012), 0); + ft1000_send_cmd (dev, (u16 *)&tempbuffer[0], (u16)(0x0012), 0); info->DrvErrNum = 0; } - info->DrvMsgPend = 0; break; default: @@ -1278,21 +1252,21 @@ void ft1000_proc_drvmsg(struct net_device *dev) } } -//--------------------------------------------------------------------------- -// -// Function: ft1000_parse_dpram_msg -// Descripton: This function will parse the message received from the DSP -// via the DPRAM interface. -// Input: -// dev - device structure -// Output: -// status - FAILURE -// SUCCESS -// -//--------------------------------------------------------------------------- -int ft1000_parse_dpram_msg(struct net_device *dev) +/*--------------------------------------------------------------------------- + + Function: ft1000_parse_dpram_msg + Description: This function will parse the message received from the DSP + via the DPRAM interface. + Input: + dev - device structure + Output: + status - FAILURE + SUCCESS + + -------------------------------------------------------------------------*/ +static int ft1000_parse_dpram_msg(struct net_device *dev) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); u16 doorbell; u16 portid; u16 nxtph; @@ -1305,7 +1279,7 @@ int ft1000_parse_dpram_msg(struct net_device *dev) DEBUG(1, "Doorbell = 0x%x\n", doorbell); if (doorbell & FT1000_ASIC_RESET_REQ) { - // Copy DSP session record from info block + /* Copy DSP session record from info block */ spin_lock_irqsave(&info->dpram_lock, flags); if (info->AsicID == ELECTRABUZZ_ID) { ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, @@ -1324,7 +1298,7 @@ int ft1000_parse_dpram_msg(struct net_device *dev) } spin_unlock_irqrestore(&info->dpram_lock, flags); - // clear ASIC RESET request + /* clear ASIC RESET request */ ft1000_write_reg(dev, FT1000_REG_DOORBELL, FT1000_ASIC_RESET_REQ); DEBUG(1, "Got an ASIC RESET Request\n"); @@ -1332,17 +1306,15 @@ int ft1000_parse_dpram_msg(struct net_device *dev) FT1000_ASIC_RESET_DSP); if (info->AsicID == MAGNEMITE_ID) { - // Setting MAGNEMITE ASIC to big endian mode + /* Setting MAGNEMITE ASIC to big endian mode */ ft1000_write_reg(dev, FT1000_REG_SUP_CTRL, HOST_INTF_BE); } - info->DspAsicReset = 0; } if (doorbell & FT1000_DSP_ASIC_RESET) { DEBUG(0, "FT1000:ft1000_parse_dpram_msg: Got a dsp ASIC reset message\n"); - info->DspAsicReset = 1; ft1000_write_reg(dev, FT1000_REG_DOORBELL, FT1000_DSP_ASIC_RESET); udelay(200); @@ -1364,11 +1336,13 @@ int ft1000_parse_dpram_msg(struct net_device *dev) } DEBUG(1, "FT1000:ft1000_parse_dpram_msg:total length = %d\n", total_len); - if ((total_len < MAX_CMD_SQSIZE) && (total_len > PSEUDOSZ)) { + if ((total_len < MAX_CMD_SQSIZE) && (total_len > sizeof(struct pseudo_hdr))) { total_len += nxtph; cnt = 0; - // ft1000_read_reg will return a value that needs to be byteswap - // in order to get DSP_QID_OFFSET. + /* + * ft1000_read_reg will return a value that needs to be byteswap + * in order to get DSP_QID_OFFSET. + */ if (info->AsicID == ELECTRABUZZ_ID) { portid = (ft1000_read_dpram @@ -1384,7 +1358,7 @@ int ft1000_parse_dpram_msg(struct net_device *dev) DEBUG(1, "DSP_QID = 0x%x\n", portid); if (portid == DRIVERID) { - // We are assumming one driver message from the DSP at a time. + /* We are assumming one driver message from the DSP at a time. */ ft1000_proc_drvmsg(dev); } } @@ -1392,7 +1366,7 @@ int ft1000_parse_dpram_msg(struct net_device *dev) } if (doorbell & FT1000_DB_COND_RESET) { - // Reset ASIC and DSP + /* Reset ASIC and DSP */ if (info->AsicID == ELECTRABUZZ_ID) { info->DSP_TIME[0] = ft1000_read_dpram(dev, FT1000_DSP_TIMER0); @@ -1422,7 +1396,7 @@ int ft1000_parse_dpram_msg(struct net_device *dev) ft1000_write_reg(dev, FT1000_REG_DOORBELL, FT1000_DB_COND_RESET); } - // let's clear any unexpected doorbells from DSP + /* let's clear any unexpected doorbells from DSP */ doorbell = doorbell & ~(FT1000_DB_DPRAM_RX | FT1000_ASIC_RESET_REQ | FT1000_DB_COND_RESET | 0xff00); @@ -1435,27 +1409,28 @@ int ft1000_parse_dpram_msg(struct net_device *dev) } -//--------------------------------------------------------------------------- -// -// Function: ft1000_flush_fifo -// Descripton: This function will flush one packet from the downlink -// FIFO. -// Input: -// dev - device structure -// drv_err - driver error causing the flush fifo -// Output: -// None. -// -//--------------------------------------------------------------------------- +/*--------------------------------------------------------------------------- + + Function: ft1000_flush_fifo + Description: This function will flush one packet from the downlink + FIFO. + Input: + dev - device structure + drv_err - driver error causing the flush fifo + Output: + None. + + -------------------------------------------------------------------------*/ static void ft1000_flush_fifo(struct net_device *dev, u16 DrvErrNum) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); + struct ft1000_pcmcia *pcmcia = info->priv; u16 i; u32 templong; u16 tempword; DEBUG(1, "ft1000:ft1000_hw:ft1000_flush_fifo called\n"); - if (info->PktIntfErr > MAX_PH_ERR) { + if (pcmcia->PktIntfErr > MAX_PH_ERR) { if (info->AsicID == ELECTRABUZZ_ID) { info->DSP_TIME[0] = ft1000_read_dpram(dev, FT1000_DSP_TIMER0); @@ -1483,7 +1458,7 @@ static void ft1000_flush_fifo(struct net_device *dev, u16 DrvErrNum) ft1000_reset_card(dev); return; } else { - // Flush corrupted pkt from FIFO + /* Flush corrupted pkt from FIFO */ i = 0; do { if (info->AsicID == ELECTRABUZZ_ID) { @@ -1498,8 +1473,10 @@ static void ft1000_flush_fifo(struct net_device *dev, u16 DrvErrNum) inw(dev->base_addr + FT1000_REG_MAG_DFSR); } i++; - // This should never happen unless the ASIC is broken. - // We must reset to recover. + /* + * This should never happen unless the ASIC is broken. + * We must reset to recover. + */ if ((i > 2048) || (tempword == 0)) { if (info->AsicID == ELECTRABUZZ_ID) { info->DSP_TIME[0] = @@ -1533,18 +1510,20 @@ static void ft1000_flush_fifo(struct net_device *dev, u16 DrvErrNum) FT1000_MAG_DSP_TIMER3_INDX); } if (tempword == 0) { - // Let's check if ASIC reads are still ok by reading the Mask register - // which is never zero at this point of the code. + /* + * Let's check if ASIC reads are still ok by reading the Mask register + * which is never zero at this point of the code. + */ tempword = inw(dev->base_addr + FT1000_REG_SUP_IMASK); if (tempword == 0) { - // This indicates that we can not communicate with the ASIC + /* This indicates that we can not communicate with the ASIC */ info->DrvErrNum = FIFO_FLUSH_BADCNT; } else { - // Let's assume that we really flush the FIFO - info->PktIntfErr++; + /* Let's assume that we really flush the FIFO */ + pcmcia->PktIntfErr++; return; } } else { @@ -1557,9 +1536,9 @@ static void ft1000_flush_fifo(struct net_device *dev, u16 DrvErrNum) if (info->AsicID == ELECTRABUZZ_ID) { i++; DEBUG(0, "Flushing FIFO complete = %x\n", tempword); - // Flush last word in FIFO. + /* Flush last word in FIFO. */ tempword = ft1000_read_reg(dev, FT1000_REG_DFIFO); - // Update FIFO counter for DSP + /* Update FIFO counter for DSP */ i = i * 2; DEBUG(0, "Flush Data byte count to dsp = %d\n", i); info->fifo_cnt += i; @@ -1567,7 +1546,7 @@ static void ft1000_flush_fifo(struct net_device *dev, u16 DrvErrNum) info->fifo_cnt); } else { DEBUG(0, "Flushing FIFO complete = %x\n", tempword); - // Flush last word in FIFO + /* Flush last word in FIFO */ templong = inl(dev->base_addr + FT1000_REG_MAG_DFR); tempword = inw(dev->base_addr + FT1000_REG_SUP_STAT); DEBUG(0, "FT1000_REG_SUP_STAT = 0x%x\n", tempword); @@ -1575,28 +1554,28 @@ static void ft1000_flush_fifo(struct net_device *dev, u16 DrvErrNum) DEBUG(0, "FT1000_REG_MAG_DFSR = 0x%x\n", tempword); } if (DrvErrNum) { - info->PktIntfErr++; + pcmcia->PktIntfErr++; } } } -//--------------------------------------------------------------------------- -// -// Function: ft1000_copy_up_pkt -// Descripton: This function will pull Flarion packets out of the Downlink -// FIFO and convert it to an ethernet packet. The ethernet packet will -// then be deliver to the TCP/IP stack. -// Input: -// dev - device structure -// Output: -// status - FAILURE -// SUCCESS -// -//--------------------------------------------------------------------------- -int ft1000_copy_up_pkt(struct net_device *dev) +/*--------------------------------------------------------------------------- + + Function: ft1000_copy_up_pkt + Description: This function will pull Flarion packets out of the Downlink + FIFO and convert it to an ethernet packet. The ethernet packet will + then be deliver to the TCP/IP stack. + Input: + dev - device structure + Output: + status - FAILURE + SUCCESS + + -------------------------------------------------------------------------*/ +static int ft1000_copy_up_pkt(struct net_device *dev) { u16 tempword; - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); u16 len; struct sk_buff *skb; u16 i; @@ -1607,7 +1586,7 @@ int ft1000_copy_up_pkt(struct net_device *dev) u32 templong; DEBUG(1, "ft1000_copy_up_pkt\n"); - // Read length + /* Read length */ if (info->AsicID == ELECTRABUZZ_ID) { tempword = ft1000_read_reg(dev, FT1000_REG_DFIFO); len = tempword; @@ -1621,7 +1600,7 @@ int ft1000_copy_up_pkt(struct net_device *dev) if (len > ENET_MAX_SIZE) { DEBUG(0, "size of ethernet packet invalid\n"); if (info->AsicID == MAGNEMITE_ID) { - // Read High word to complete 32 bit access + /* Read High word to complete 32 bit access */ tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRH); } ft1000_flush_fifo(dev, DSP_PKTLEN_INFO); @@ -1633,7 +1612,7 @@ int ft1000_copy_up_pkt(struct net_device *dev) if (skb == NULL) { DEBUG(0, "No Network buffers available\n"); - // Read High word to complete 32 bit access + /* Read High word to complete 32 bit access */ if (info->AsicID == MAGNEMITE_ID) { tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRH); } @@ -1643,13 +1622,13 @@ int ft1000_copy_up_pkt(struct net_device *dev) } pbuffer = (u8 *) skb_put(skb, len + 12); - // Pseudo header + /* Pseudo header */ if (info->AsicID == ELECTRABUZZ_ID) { for (i = 1; i < 7; i++) { tempword = ft1000_read_reg(dev, FT1000_REG_DFIFO); chksum ^= tempword; } - // read checksum value + /* read checksum value */ tempword = ft1000_read_reg(dev, FT1000_REG_DFIFO); } else { tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRH); @@ -1676,7 +1655,7 @@ int ft1000_copy_up_pkt(struct net_device *dev) DEBUG(1, "Pseudo = 0x%x\n", tempword); chksum ^= tempword; - // read checksum value + /* read checksum value */ tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRH); DEBUG(1, "Pseudo = 0x%x\n", tempword); } @@ -1689,10 +1668,10 @@ int ft1000_copy_up_pkt(struct net_device *dev) kfree_skb(skb); return FAILURE; } - //subtract the number of bytes read already + /* subtract the number of bytes read already */ ptemp = pbuffer; - // fake MAC address + /* fake MAC address */ *pbuffer++ = dev->dev_addr[0]; *pbuffer++ = dev->dev_addr[1]; *pbuffer++ = dev->dev_addr[2]; @@ -1711,13 +1690,13 @@ int ft1000_copy_up_pkt(struct net_device *dev) tempword = ft1000_read_reg(dev, FT1000_REG_DFIFO); *pbuffer++ = (u8) (tempword >> 8); *pbuffer++ = (u8) tempword; - if (ft1000_chkcard(dev) == FALSE) { + if (ft1000_chkcard(dev) == false) { kfree_skb(skb); return FAILURE; } } - // Need to read one more word if odd byte + /* Need to read one more word if odd byte */ if (len & 0x0001) { tempword = ft1000_read_reg(dev, FT1000_REG_DFIFO); *pbuffer++ = (u8) (tempword >> 8); @@ -1730,7 +1709,7 @@ int ft1000_copy_up_pkt(struct net_device *dev) *ptemplong++ = templong; } - // Need to read one more word if odd align. + /* Need to read one more word if odd align. */ if (len & 0x0003) { templong = inl(dev->base_addr + FT1000_REG_MAG_DFR); DEBUG(1, "Data = 0x%8x\n", templong); @@ -1750,11 +1729,11 @@ int ft1000_copy_up_pkt(struct net_device *dev) netif_rx(skb); info->stats.rx_packets++; - // Add on 12 bytes for MAC address which was removed + /* Add on 12 bytes for MAC address which was removed */ info->stats.rx_bytes += (len + 12); if (info->AsicID == ELECTRABUZZ_ID) { - // track how many bytes have been read from FIFO - round up to 16 bit word + /* track how many bytes have been read from FIFO - round up to 16 bit word */ tempword = len + 16; if (tempword & 0x01) tempword++; @@ -1766,35 +1745,36 @@ int ft1000_copy_up_pkt(struct net_device *dev) return SUCCESS; } -//--------------------------------------------------------------------------- -// -// Function: ft1000_copy_down_pkt -// Descripton: This function will take an ethernet packet and convert it to -// a Flarion packet prior to sending it to the ASIC Downlink -// FIFO. -// Input: -// dev - device structure -// packet - address of ethernet packet -// len - length of IP packet -// Output: -// status - FAILURE -// SUCCESS -// -//--------------------------------------------------------------------------- -int ft1000_copy_down_pkt(struct net_device *dev, u16 * packet, u16 len) +/*--------------------------------------------------------------------------- + + Function: ft1000_copy_down_pkt + Description: This function will take an ethernet packet and convert it to + a Flarion packet prior to sending it to the ASIC Downlink + FIFO. + Input: + dev - device structure + packet - address of ethernet packet + len - length of IP packet + Output: + status - FAILURE + SUCCESS + + -------------------------------------------------------------------------*/ +static int ft1000_copy_down_pkt(struct net_device *dev, u16 * packet, u16 len) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); + struct ft1000_pcmcia *pcmcia = info->priv; union { - PSEUDO_HDR blk; - u16 buff[sizeof(PSEUDO_HDR) >> 1]; - u8 buffc[sizeof(PSEUDO_HDR)]; + struct pseudo_hdr blk; + u16 buff[sizeof(struct pseudo_hdr) >> 1]; + u8 buffc[sizeof(struct pseudo_hdr)]; } pseudo; int i; u32 *plong; DEBUG(1, "ft1000_hw: copy_down_pkt()\n"); - // Check if there is room on the FIFO + /* Check if there is room on the FIFO */ if (len > ft1000_read_fifo_len(dev)) { udelay(10); if (len > ft1000_read_fifo_len(dev)) { @@ -1819,21 +1799,21 @@ int ft1000_copy_down_pkt(struct net_device *dev, u16 * packet, u16 len) return SUCCESS; } } - // Create pseudo header and send pseudo/ip to hardware + /* Create pseudo header and send pseudo/ip to hardware */ if (info->AsicID == ELECTRABUZZ_ID) { pseudo.blk.length = len; } else { pseudo.blk.length = ntohs(len); } - pseudo.blk.source = DSPID; // Need to swap to get in correct order + pseudo.blk.source = DSPID; /* Need to swap to get in correct order */ pseudo.blk.destination = HOSTID; - pseudo.blk.portdest = NETWORKID; // Need to swap to get in correct order + pseudo.blk.portdest = NETWORKID; /* Need to swap to get in correct order */ pseudo.blk.portsrc = DSPAIRID; pseudo.blk.sh_str_id = 0; pseudo.blk.control = 0; pseudo.blk.rsvd1 = 0; pseudo.blk.seq_num = 0; - pseudo.blk.rsvd2 = info->packetseqnum++; + pseudo.blk.rsvd2 = pcmcia->packetseqnum++; pseudo.blk.qos_class = 0; /* Calculate pseudo header checksum */ pseudo.blk.checksum = pseudo.buff[0]; @@ -1841,14 +1821,14 @@ int ft1000_copy_down_pkt(struct net_device *dev, u16 * packet, u16 len) pseudo.blk.checksum ^= pseudo.buff[i]; } - // Production Mode + /* Production Mode */ if (info->AsicID == ELECTRABUZZ_ID) { - // copy first word to UFIFO_BEG reg + /* copy first word to UFIFO_BEG reg */ ft1000_write_reg(dev, FT1000_REG_UFIFO_BEG, pseudo.buff[0]); DEBUG(1, "ft1000_hw:ft1000_copy_down_pkt:data 0 BEG = 0x%04x\n", pseudo.buff[0]); - // copy subsequent words to UFIFO_MID reg + /* copy subsequent words to UFIFO_MID reg */ ft1000_write_reg(dev, FT1000_REG_UFIFO_MID, pseudo.buff[1]); DEBUG(1, "ft1000_hw:ft1000_copy_down_pkt:data 1 MID = 0x%04x\n", pseudo.buff[1]); @@ -1871,7 +1851,7 @@ int ft1000_copy_down_pkt(struct net_device *dev, u16 * packet, u16 len) DEBUG(1, "ft1000_hw:ft1000_copy_down_pkt:data 7 MID = 0x%04x\n", pseudo.buff[7]); - // Write PPP type + IP Packet into Downlink FIFO + /* Write PPP type + IP Packet into Downlink FIFO */ for (i = 0; i < (len >> 1) - 1; i++) { ft1000_write_reg(dev, FT1000_REG_UFIFO_MID, htons(*packet)); @@ -1881,7 +1861,7 @@ int ft1000_copy_down_pkt(struct net_device *dev, u16 * packet, u16 len) packet++; } - // Check for odd byte + /* Check for odd byte */ if (len & 0x0001) { ft1000_write_reg(dev, FT1000_REG_UFIFO_MID, htons(*packet)); @@ -1920,12 +1900,12 @@ int ft1000_copy_down_pkt(struct net_device *dev, u16 * packet, u16 len) *(u32 *) & pseudo.buff[6]); plong = (u32 *) packet; - // Write PPP type + IP Packet into Downlink FIFO + /* Write PPP type + IP Packet into Downlink FIFO */ for (i = 0; i < (len >> 2); i++) { outl(*plong++, dev->base_addr + FT1000_REG_MAG_UFDR); } - // Check for odd alignment + /* Check for odd alignment */ if (len & 0x0003) { DEBUG(1, "ft1000_hw:ft1000_copy_down_pkt:data = 0x%8x\n", @@ -1936,14 +1916,14 @@ int ft1000_copy_down_pkt(struct net_device *dev, u16 * packet, u16 len) } info->stats.tx_packets++; - // Add 14 bytes for MAC adddress plus ethernet type + /* Add 14 bytes for MAC address plus ethernet type */ info->stats.tx_bytes += (len + 14); return SUCCESS; } static struct net_device_stats *ft1000_stats(struct net_device *dev) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); return (&info->stats); } @@ -1967,7 +1947,7 @@ static int ft1000_open(struct net_device *dev) static int ft1000_close(struct net_device *dev) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); DEBUG(0, "ft1000_hw: ft1000_close()\n"); @@ -1981,7 +1961,7 @@ static int ft1000_close(struct net_device *dev) ft1000_disable_interrupts(dev); ft1000_write_reg(dev, FT1000_REG_RESET, DSP_RESET_BIT); - //reset ASIC + /* reset ASIC */ ft1000_reset_asic(dev); } return 0; @@ -1989,7 +1969,7 @@ static int ft1000_close(struct net_device *dev) static int ft1000_start_xmit(struct sk_buff *skb, struct net_device *dev) { - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); u8 *pdata; DEBUG(1, "ft1000_hw: ft1000_start_xmit()\n"); @@ -2026,7 +2006,7 @@ static int ft1000_start_xmit(struct sk_buff *skb, struct net_device *dev) static irqreturn_t ft1000_interrupt(int irq, void *dev_id) { struct net_device *dev = (struct net_device *)dev_id; - FT1000_INFO *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(dev); u16 tempword; u16 inttype; int cnt; @@ -2038,62 +2018,63 @@ static irqreturn_t ft1000_interrupt(int irq, void *dev_id) return IRQ_HANDLED; } - if (ft1000_chkcard(dev) == FALSE) { + if (ft1000_chkcard(dev) == false) { ft1000_disable_interrupts(dev); return IRQ_HANDLED; } ft1000_disable_interrupts(dev); - // Read interrupt type + /* Read interrupt type */ inttype = ft1000_read_reg(dev, FT1000_REG_SUP_ISR); - // Make sure we process all interrupt before leaving the ISR due to the edge trigger interrupt type - while (inttype) { - if (inttype & ISR_DOORBELL_PEND) { - ft1000_parse_dpram_msg(dev); - } + /* Make sure we process all interrupt before leaving the ISR due to the edge trigger interrupt type */ + while (inttype) { + if (inttype & ISR_DOORBELL_PEND) + ft1000_parse_dpram_msg(dev); - if (inttype & ISR_RCV) { - DEBUG(1, "Data in FIFO\n"); + if (inttype & ISR_RCV) { + DEBUG(1, "Data in FIFO\n"); - cnt = 0; - do { - // Check if we have packets in the Downlink FIFO - if (info->AsicID == ELECTRABUZZ_ID) { - tempword = - ft1000_read_reg(dev, FT1000_REG_DFIFO_STAT); - } else { - tempword = - ft1000_read_reg(dev, FT1000_REG_MAG_DFSR); - } - if (tempword & 0x1f) { - ft1000_copy_up_pkt(dev); - } else { - break; - } - cnt++; - } while (cnt < MAX_RCV_LOOP); + cnt = 0; + do { + /* Check if we have packets in the Downlink FIFO */ + if (info->AsicID == ELECTRABUZZ_ID) { + tempword = + ft1000_read_reg(dev, + FT1000_REG_DFIFO_STAT); + } else { + tempword = + ft1000_read_reg(dev, + FT1000_REG_MAG_DFSR); + } + if (tempword & 0x1f) { + ft1000_copy_up_pkt(dev); + } else { + break; + } + cnt++; + } while (cnt < MAX_RCV_LOOP); + } + /* clear interrupts */ + tempword = ft1000_read_reg(dev, FT1000_REG_SUP_ISR); + DEBUG(1, "ft1000_hw: interrupt status register = 0x%x\n", tempword); + ft1000_write_reg(dev, FT1000_REG_SUP_ISR, tempword); + + /* Read interrupt type */ + inttype = ft1000_read_reg (dev, FT1000_REG_SUP_ISR); + DEBUG(1,"ft1000_hw: interrupt status register after clear = 0x%x\n",inttype); } - // clear interrupts - tempword = ft1000_read_reg(dev, FT1000_REG_SUP_ISR); - DEBUG(1, "ft1000_hw: interrupt status register = 0x%x\n", tempword); - ft1000_write_reg(dev, FT1000_REG_SUP_ISR, tempword); - - // Read interrupt type - inttype = ft1000_read_reg (dev, FT1000_REG_SUP_ISR); - DEBUG(1,"ft1000_hw: interrupt status register after clear = 0x%x\n",inttype); - } ft1000_enable_interrupts(dev); return IRQ_HANDLED; } void stop_ft1000_card(struct net_device *dev) { - FT1000_INFO *info = netdev_priv(dev); - PPROV_RECORD ptr; -// int cnt; + struct ft1000_info *info = netdev_priv(dev); + struct prov_record *ptr; + /* int cnt; */ DEBUG(0, "ft1000_hw: stop_ft1000_card()\n"); @@ -2102,14 +2083,16 @@ void stop_ft1000_card(struct net_device *dev) netif_stop_queue(dev); ft1000_disable_interrupts(dev); - // Make sure we free any memory reserve for provisioning + /* Make sure we free any memory reserve for provisioning */ while (list_empty(&info->prov_list) == 0) { - ptr = list_entry(info->prov_list.next, PROV_RECORD, list); + ptr = list_entry(info->prov_list.next, struct prov_record, list); list_del(&ptr->list); kfree(ptr->pprov_data); kfree(ptr); } + kfree(info->priv); + if (info->registered) { unregister_netdev(dev); info->registered = 0; @@ -2126,19 +2109,20 @@ void stop_ft1000_card(struct net_device *dev) static void ft1000_get_drvinfo(struct net_device *dev, struct ethtool_drvinfo *info) { - FT1000_INFO *ft_info; + struct ft1000_info *ft_info; ft_info = netdev_priv(dev); - snprintf(info->driver, 32, "ft1000"); - snprintf(info->bus_info, ETHTOOL_BUSINFO_LEN, "PCMCIA 0x%lx", + strlcpy(info->driver, "ft1000", sizeof(info->driver)); + snprintf(info->bus_info, sizeof(info->bus_info), "PCMCIA 0x%lx", dev->base_addr); - snprintf(info->fw_version, 32, "%d.%d.%d.%d", ft_info->DspVer[0], - ft_info->DspVer[1], ft_info->DspVer[2], ft_info->DspVer[3]); + snprintf(info->fw_version, sizeof(info->fw_version), "%d.%d.%d.%d", + ft_info->DspVer[0], ft_info->DspVer[1], ft_info->DspVer[2], + ft_info->DspVer[3]); } static u32 ft1000_get_link(struct net_device *dev) { - FT1000_INFO *info; + struct ft1000_info *info; info = netdev_priv(dev); return info->mediastate; } @@ -2148,15 +2132,14 @@ static const struct ethtool_ops ops = { .get_link = ft1000_get_link }; -struct net_device *init_ft1000_card(unsigned short irq, int port, - unsigned char *mac_addr, void *ft1000_reset, - void *link, struct device *fdev) +struct net_device *init_ft1000_card(struct pcmcia_device *link, + void *ft1000_reset) { - FT1000_INFO *info; + struct ft1000_info *info; + struct ft1000_pcmcia *pcmcia; struct net_device *dev; - int i; - static const struct net_device_ops ft1000ops = // Slavius 21.10.2009 due to kernel changes + static const struct net_device_ops ft1000ops = /* Slavius 21.10.2009 due to kernel changes */ { .ndo_open = &ft1000_open, .ndo_stop = &ft1000_close, @@ -2165,8 +2148,8 @@ struct net_device *init_ft1000_card(unsigned short irq, int port, }; DEBUG(1, "ft1000_hw: init_ft1000_card()\n"); - DEBUG(1, "ft1000_hw: irq = %d\n", irq); - DEBUG(1, "ft1000_hw: port = 0x%04x\n", port); + DEBUG(1, "ft1000_hw: irq = %d\n", link->irq); + DEBUG(1, "ft1000_hw: port = 0x%04x\n", link->resource[0]->start); flarion_ft1000_cnt++; @@ -2178,16 +2161,16 @@ struct net_device *init_ft1000_card(unsigned short irq, int port, return NULL; } - dev = alloc_etherdev(sizeof(FT1000_INFO)); + dev = alloc_etherdev(sizeof(struct ft1000_info)); if (!dev) { printk(KERN_ERR "ft1000: failed to allocate etherdev\n"); return NULL; } - SET_NETDEV_DEV(dev, fdev); + SET_NETDEV_DEV(dev, &link->dev); info = netdev_priv(dev); - memset(info, 0, sizeof(FT1000_INFO)); + memset(info, 0, sizeof(struct ft1000_info)); DEBUG(1, "address of dev = 0x%8x\n", (u32) dev); DEBUG(1, "address of dev info = 0x%8x\n", (u32) info); @@ -2195,18 +2178,16 @@ struct net_device *init_ft1000_card(unsigned short irq, int port, memset(&info->stats, 0, sizeof(struct net_device_stats)); + info->priv = kzalloc(sizeof(struct ft1000_pcmcia), GFP_KERNEL); + pcmcia = info->priv; + pcmcia->link = link; + spin_lock_init(&info->dpram_lock); info->DrvErrNum = 0; - info->ASICResetNum = 0; info->registered = 1; - info->link = link; info->ft1000_reset = ft1000_reset; info->mediastate = 0; info->fifo_cnt = 0; - info->DeviceCreated = FALSE; - info->DeviceMajor = 0; - info->CurrentInterruptEnableMask = ISR_DEFAULT_MASK; - info->InterruptsEnabled = FALSE; info->CardReady = 0; info->DSP_TIME[0] = 0; info->DSP_TIME[1] = 0; @@ -2218,24 +2199,22 @@ struct net_device *init_ft1000_card(unsigned short irq, int port, info->squeseqnum = 0; -// dev->hard_start_xmit = &ft1000_start_xmit; -// dev->get_stats = &ft1000_stats; -// dev->open = &ft1000_open; -// dev->stop = &ft1000_close; + /* dev->hard_start_xmit = &ft1000_start_xmit; */ + /* dev->get_stats = &ft1000_stats; */ + /* dev->open = &ft1000_open; */ + /* dev->stop = &ft1000_close; */ - dev->netdev_ops = &ft1000ops; // Slavius 21.10.2009 due to kernel changes + dev->netdev_ops = &ft1000ops; /* Slavius 21.10.2009 due to kernel changes */ DEBUG(0, "device name = %s\n", dev->name); - for (i = 0; i < 6; i++) { - dev->dev_addr[i] = mac_addr[i]; - DEBUG(1, "ft1000_hw: mac_addr %d = 0x%02x\n", i, mac_addr[i]); + dev->irq = link->irq; + dev->base_addr = link->resource[0]->start; + if (pcmcia_get_mac_from_cis(link, dev)) { + printk(KERN_ERR "ft1000: Could not read mac address\n"); + goto err_dev; } - netif_stop_queue(dev); - dev->irq = irq; - dev->base_addr = port; - if (request_irq(dev->irq, ft1000_interrupt, IRQF_SHARED, dev->name, dev)) { printk(KERN_ERR "ft1000: Could not request_irq\n"); goto err_dev; @@ -2254,13 +2233,13 @@ struct net_device *init_ft1000_card(unsigned short irq, int port, info->AsicID = ft1000_read_reg(dev, FT1000_REG_ASIC_ID); if (info->AsicID == ELECTRABUZZ_ID) { DEBUG(0, "ft1000_hw: ELECTRABUZZ ASIC\n"); - if (request_firmware(&fw_entry, "ft1000.img", fdev) != 0) { + if (request_firmware(&fw_entry, "ft1000.img", &link->dev) != 0) { printk(KERN_INFO "ft1000: Could not open ft1000.img\n"); goto err_unreg; } } else { DEBUG(0, "ft1000_hw: MAGNEMITE ASIC\n"); - if (request_firmware(&fw_entry, "ft2000.img", fdev) != 0) { + if (request_firmware(&fw_entry, "ft2000.img", &link->dev) != 0) { printk(KERN_INFO "ft1000: Could not open ft2000.img\n"); goto err_unreg; } @@ -2270,12 +2249,9 @@ struct net_device *init_ft1000_card(unsigned short irq, int port, ft1000InitProc(dev); ft1000_card_present = 1; - SET_ETHTOOL_OPS(dev, &ops); - printk(KERN_INFO - "ft1000: %s: addr 0x%04lx irq %d, MAC addr %02x:%02x:%02x:%02x:%02x:%02x\n", - dev->name, dev->base_addr, dev->irq, dev->dev_addr[0], - dev->dev_addr[1], dev->dev_addr[2], dev->dev_addr[3], - dev->dev_addr[4], dev->dev_addr[5]); + dev->ethtool_ops = &ops; + printk(KERN_INFO "ft1000: %s: addr 0x%04lx irq %d, MAC addr %pM\n", + dev->name, dev->base_addr, dev->irq, dev->dev_addr); return dev; err_unreg: @@ -2288,7 +2264,3 @@ err_dev: free_netdev(dev); return NULL; } - -EXPORT_SYMBOL(init_ft1000_card); -EXPORT_SYMBOL(stop_ft1000_card); -EXPORT_SYMBOL(flarion_ft1000_cnt); diff --git a/drivers/staging/ft1000/ft1000-pcmcia/ft1000_proc.c b/drivers/staging/ft1000/ft1000-pcmcia/ft1000_proc.c index 935608e7200..88f6f9ce304 100644 --- a/drivers/staging/ft1000/ft1000-pcmcia/ft1000_proc.c +++ b/drivers/staging/ft1000/ft1000-pcmcia/ft1000_proc.c @@ -19,83 +19,66 @@ #include <linux/module.h> #include <linux/kernel.h> #include <linux/proc_fs.h> +#include <linux/seq_file.h> #include <linux/string.h> #include <linux/vmalloc.h> #include <linux/netdevice.h> +#include <asm/io.h> #include <asm/uaccess.h> #include "ft1000.h" #define FT1000_PROC "ft1000" #define MAX_FILE_LEN 255 -#define PUTM_TO_PAGE(len,page,args...) \ - len += snprintf(page+len, PAGE_SIZE - len, args) - -#define PUTX_TO_PAGE(len,page,message,size,var) \ - len += snprintf(page+len, PAGE_SIZE - len, message); \ - for(i = 0; i < (size - 1); i++) \ - { \ - len += snprintf(page+len, PAGE_SIZE - len, "%02x:", var[i]); \ +#define seq_putx(m, message, size, var) \ + seq_printf(m, message); \ + for (i = 0; i < (size - 1); i++) { \ + seq_printf(m, "%02x:", var[i]); \ } \ - len += snprintf(page+len, PAGE_SIZE - len, "%02x\n", var[i]) + seq_printf(m, "%02x\n", var[i]) -#define PUTD_TO_PAGE(len,page,message,size,var) \ - len += snprintf(page+len, PAGE_SIZE - len, message); \ - for(i = 0; i < (size - 1); i++) \ - { \ - len += snprintf(page+len, PAGE_SIZE - len, "%d.", var[i]); \ +#define seq_putd(m, message, size, var) \ + seq_printf(m, message); \ + for (i = 0; i < (size - 1); i++) { \ + seq_printf(m, "%d.", var[i]); \ } \ - len += snprintf(page+len, PAGE_SIZE - len, "%d\n", var[i]) + seq_printf(m, "%d\n", var[i]) -int ft1000ReadProc(char *page, char **start, off_t off, - int count, int *eof, void *data) +static int ft1000ReadProc(struct seq_file *m, void *v) { - struct net_device *dev; - int len; - int i; - FT1000_INFO *info; - char *status[] = - { "Idle (Disconnect)", "Searching", "Active (Connected)", + static const char *status[] = { + "Idle (Disconnect)", "Searching", "Active (Connected)", "Waiting for L2", "Sleep", "No Coverage", "", "" }; - char *signal[] = { "", "*", "**", "***", "****" }; + static const char *signal[] = { "", "*", "**", "***", "****" }; + + struct net_device *dev = m->private; + struct ft1000_info *info = netdev_priv(dev); + int i; int strength; int quality; struct timeval tv; time_t delta; - dev = (struct net_device *)data; - info = netdev_priv(dev); - - if (off > 0) { - *eof = 1; - return 0; - } - - /* Wrap-around */ - if (info->AsicID == ELECTRABUZZ_ID) { - if (info->DspHibernateFlag == 0) { - if (info->ProgConStat != 0xFF) { - info->LedStat = - ft1000_read_dpram(dev, FT1000_DSP_LED); - info->ConStat = - ft1000_read_dpram(dev, - FT1000_DSP_CON_STATE); - } else { - info->ConStat = 0xf; - } + if (info->ProgConStat != 0xFF) { + info->LedStat = + ft1000_read_dpram(dev, FT1000_DSP_LED); + info->ConStat = + ft1000_read_dpram(dev, FT1000_DSP_CON_STATE); + } else { + info->ConStat = 0xf; } } else { if (info->ProgConStat != 0xFF) { info->LedStat = - ntohs(ft1000_read_dpram_mag_16 - (dev, FT1000_MAG_DSP_LED, - FT1000_MAG_DSP_LED_INDX)); + ntohs(ft1000_read_dpram_mag_16( + dev, FT1000_MAG_DSP_LED, + FT1000_MAG_DSP_LED_INDX)); info->ConStat = - ntohs(ft1000_read_dpram_mag_16 - (dev, FT1000_MAG_DSP_CON_STATE, - FT1000_MAG_DSP_CON_STATE_INDX)); + ntohs(ft1000_read_dpram_mag_16( + dev, FT1000_MAG_DSP_CON_STATE, + FT1000_MAG_DSP_CON_STATE_INDX)); } else { info->ConStat = 0xf; } @@ -138,49 +121,59 @@ int ft1000ReadProc(char *page, char **start, off_t off, } do_gettimeofday(&tv); - delta = (tv.tv_sec - info->ConTm); - len = 0; - PUTM_TO_PAGE(len, page, "Connection Time: %02ld:%02ld:%02ld\n", + delta = tv.tv_sec - info->ConTm; + seq_printf(m, "Connection Time: %02ld:%02ld:%02ld\n", ((delta / 3600) % 24), ((delta / 60) % 60), (delta % 60)); - PUTM_TO_PAGE(len, page, "Connection Time[s]: %ld\n", delta); - PUTM_TO_PAGE(len, page, "Asic ID: %s\n", - (info->AsicID) == + seq_printf(m, "Connection Time[s]: %ld\n", delta); + seq_printf(m, "Asic ID: %s\n", + info->AsicID == ELECTRABUZZ_ID ? "ELECTRABUZZ ASIC" : "MAGNEMITE ASIC"); - PUTX_TO_PAGE(len, page, "SKU: ", SKUSZ, info->Sku); - PUTX_TO_PAGE(len, page, "EUI64: ", EUISZ, info->eui64); - PUTD_TO_PAGE(len, page, "DSP version number: ", DSPVERSZ, info->DspVer); - PUTX_TO_PAGE(len, page, "Hardware Serial Number: ", HWSERNUMSZ, - info->HwSerNum); - PUTX_TO_PAGE(len, page, "Caliberation Version: ", CALVERSZ, - info->RfCalVer); - PUTD_TO_PAGE(len, page, "Caliberation Date: ", CALDATESZ, - info->RfCalDate); - PUTM_TO_PAGE(len, page, "Media State: %s\n", + seq_putx(m, "SKU: ", SKUSZ, info->Sku); + seq_putx(m, "EUI64: ", EUISZ, info->eui64); + seq_putd(m, "DSP version number: ", DSPVERSZ, info->DspVer); + seq_putx(m, "Hardware Serial Number: ", HWSERNUMSZ, info->HwSerNum); + seq_putx(m, "Caliberation Version: ", CALVERSZ, info->RfCalVer); + seq_putd(m, "Caliberation Date: ", CALDATESZ, info->RfCalDate); + seq_printf(m, "Media State: %s\n", (info->mediastate) ? "link" : "no link"); - PUTM_TO_PAGE(len, page, "Connection Status: %s\n", - status[((info->ConStat) & 0x7)]); - PUTM_TO_PAGE(len, page, "RX packets: %ld\n", info->stats.rx_packets); - PUTM_TO_PAGE(len, page, "TX packets: %ld\n", info->stats.tx_packets); - PUTM_TO_PAGE(len, page, "RX bytes: %ld\n", info->stats.rx_bytes); - PUTM_TO_PAGE(len, page, "TX bytes: %ld\n", info->stats.tx_bytes); - PUTM_TO_PAGE(len, page, "Signal Strength: %s\n", signal[strength]); - PUTM_TO_PAGE(len, page, "Signal Quality: %s\n", signal[quality]); - return len; + seq_printf(m, "Connection Status: %s\n", status[info->ConStat & 0x7]); + seq_printf(m, "RX packets: %ld\n", info->stats.rx_packets); + seq_printf(m, "TX packets: %ld\n", info->stats.tx_packets); + seq_printf(m, "RX bytes: %ld\n", info->stats.rx_bytes); + seq_printf(m, "TX bytes: %ld\n", info->stats.tx_bytes); + seq_printf(m, "Signal Strength: %s\n", signal[strength]); + seq_printf(m, "Signal Quality: %s\n", signal[quality]); + return 0; +} + +/* + * seq_file wrappers for procfile show routines. + */ +static int ft1000_proc_open(struct inode *inode, struct file *file) +{ + return single_open(file, ft1000ReadProc, PDE_DATA(inode)); } +static const struct file_operations ft1000_proc_fops = { + .open = ft1000_proc_open, + .read = seq_read, + .llseek = seq_lseek, + .release = single_release, +}; + static int ft1000NotifyProc(struct notifier_block *this, unsigned long event, void *ptr) { - struct net_device *dev = ptr; - FT1000_INFO *info; + struct net_device *dev = netdev_notifier_info_to_dev(ptr); + struct ft1000_info *info; info = netdev_priv(dev); switch (event) { case NETDEV_CHANGENAME: - remove_proc_entry(info->netdevname, info->proc_ft1000); - create_proc_read_entry(dev->name, 0644, info->proc_ft1000, - ft1000ReadProc, dev); + remove_proc_entry(info->netdevname, info->ft1000_proc_dir); + proc_create_data(dev->name, 0644, info->ft1000_proc_dir, + &ft1000_proc_fops, dev); snprintf(info->netdevname, IFNAMSIZ, "%s", dev->name); break; } @@ -193,27 +186,26 @@ static struct notifier_block ft1000_netdev_notifier = { void ft1000InitProc(struct net_device *dev) { - FT1000_INFO *info; + struct ft1000_info *info; info = netdev_priv(dev); - info->proc_ft1000 = proc_mkdir(FT1000_PROC, init_net.proc_net); - create_proc_read_entry(dev->name, 0644, info->proc_ft1000, - ft1000ReadProc, dev); + info->ft1000_proc_dir = proc_mkdir(FT1000_PROC, init_net.proc_net); + + proc_create_data(dev->name, 0644, info->ft1000_proc_dir, + &ft1000_proc_fops, dev); + snprintf(info->netdevname, IFNAMSIZ, "%s", dev->name); register_netdevice_notifier(&ft1000_netdev_notifier); } void ft1000CleanupProc(struct net_device *dev) { - FT1000_INFO *info; + struct ft1000_info *info; info = netdev_priv(dev); - remove_proc_entry(dev->name, info->proc_ft1000); + remove_proc_entry(dev->name, info->ft1000_proc_dir); remove_proc_entry(FT1000_PROC, init_net.proc_net); unregister_netdevice_notifier(&ft1000_netdev_notifier); } - -EXPORT_SYMBOL(ft1000InitProc); -EXPORT_SYMBOL(ft1000CleanupProc); diff --git a/drivers/staging/ft1000/ft1000-usb/ft1000_debug.c b/drivers/staging/ft1000/ft1000-usb/ft1000_debug.c index 149ba59f96b..a8945b78596 100644 --- a/drivers/staging/ft1000/ft1000-usb/ft1000_debug.c +++ b/drivers/staging/ft1000/ft1000-usb/ft1000_debug.c @@ -1,29 +1,31 @@ -//--------------------------------------------------------------------------- -// FT1000 driver for Flarion Flash OFDM NIC Device -// -// Copyright (C) 2006 Flarion Technologies, All rights reserved. -// -// This program is free software; you can redistribute it and/or modify it -// under the terms of the GNU General Public License as published by the Free -// Software Foundation; either version 2 of the License, or (at your option) any -// later version. This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY -// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for -// more details. You should have received a copy of the GNU General Public -// License along with this program; if not, write to the -// Free Software Foundation, Inc., 59 Temple Place - -// Suite 330, Boston, MA 02111-1307, USA. -//--------------------------------------------------------------------------- -// -// File: ft1000_chdev.c -// -// Description: Custom character device dispatch routines. -// -// History: -// 8/29/02 Whc Ported to Linux. -// 6/05/06 Whc Porting to Linux 2.6.9 -// -//--------------------------------------------------------------------------- +/* +*--------------------------------------------------------------------------- +* FT1000 driver for Flarion Flash OFDM NIC Device +* +* Copyright (C) 2006 Flarion Technologies, All rights reserved. +* +* This program is free software; you can redistribute it and/or modify it +* under the terms of the GNU General Public License as published by the Free +* Software Foundation; either version 2 of the License, or (at your option) any +* later version. This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY +* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for +* more details. You should have received a copy of the GNU General Public +* License along with this program; if not, write to the +* Free Software Foundation, Inc., 59 Temple Place - +* Suite 330, Boston, MA 02111-1307, USA. +*--------------------------------------------------------------------------- +* +* File: ft1000_chdev.c +* +* Description: Custom character device dispatch routines. +* +* History: +* 8/29/02 Whc Ported to Linux. +* 6/05/06 Whc Porting to Linux 2.6.9 +* +*--------------------------------------------------------------------------- +*/ #include <linux/module.h> #include <linux/kernel.h> #include <linux/sched.h> @@ -38,25 +40,24 @@ static int ft1000_flarion_cnt = 0; -static int ft1000_open (struct inode *inode, struct file *file); +static int ft1000_open(struct inode *inode, struct file *file); static unsigned int ft1000_poll_dev(struct file *file, poll_table *wait); static long ft1000_ioctl(struct file *file, unsigned int command, unsigned long argument); -static int ft1000_release (struct inode *inode, struct file *file); +static int ft1000_release(struct inode *inode, struct file *file); -// List to free receive command buffer pool +/* List to free receive command buffer pool */ struct list_head freercvpool; -// lock to arbitrate free buffer list for receive command data +/* lock to arbitrate free buffer list for receive command data */ spinlock_t free_buff_lock; int numofmsgbuf = 0; -// -// Table of entry-point routines for char device -// -static struct file_operations ft1000fops = -{ +/* +* Table of entry-point routines for char device +*/ +static const struct file_operations ft1000fops = { .unlocked_ioctl = ft1000_ioctl, .poll = ft1000_poll_dev, .open = ft1000_open, @@ -64,34 +65,35 @@ static struct file_operations ft1000fops = .llseek = no_llseek, }; -//--------------------------------------------------------------------------- -// Function: ft1000_get_buffer -// -// Parameters: -// -// Returns: -// -// Description: -// -// Notes: -// -//--------------------------------------------------------------------------- +/* +--------------------------------------------------------------------------- +* Function: ft1000_get_buffer +* +* Parameters: +* +* Returns: +* +* Description: +* +* Notes: +* +*--------------------------------------------------------------------------- +*/ struct dpram_blk *ft1000_get_buffer(struct list_head *bufflist) { unsigned long flags; struct dpram_blk *ptr; spin_lock_irqsave(&free_buff_lock, flags); - // Check if buffer is available - if ( list_empty(bufflist) ) { + /* Check if buffer is available */ + if (list_empty(bufflist)) { DEBUG("ft1000_get_buffer: No more buffer - %d\n", numofmsgbuf); ptr = NULL; - } - else { + } else { numofmsgbuf--; ptr = list_entry(bufflist->next, struct dpram_blk, list); list_del(&ptr->list); - //DEBUG("ft1000_get_buffer: number of free msg buffers = %d\n", numofmsgbuf); + /* DEBUG("ft1000_get_buffer: number of free msg buffers = %d\n", numofmsgbuf); */ } spin_unlock_irqrestore(&free_buff_lock, flags); @@ -101,65 +103,67 @@ struct dpram_blk *ft1000_get_buffer(struct list_head *bufflist) -//--------------------------------------------------------------------------- -// Function: ft1000_free_buffer -// -// Parameters: -// -// Returns: -// -// Description: -// -// Notes: -// -//--------------------------------------------------------------------------- +/* +*--------------------------------------------------------------------------- +* Function: ft1000_free_buffer +* +* Parameters: +* +* Returns: +* +* Description: +* +* Notes: +* +*--------------------------------------------------------------------------- +*/ void ft1000_free_buffer(struct dpram_blk *pdpram_blk, struct list_head *plist) { unsigned long flags; spin_lock_irqsave(&free_buff_lock, flags); - // Put memory back to list + /* Put memory back to list */ list_add_tail(&pdpram_blk->list, plist); numofmsgbuf++; - //DEBUG("ft1000_free_buffer: number of free msg buffers = %d\n", numofmsgbuf); + /*DEBUG("ft1000_free_buffer: number of free msg buffers = %d\n", numofmsgbuf); */ spin_unlock_irqrestore(&free_buff_lock, flags); } -//--------------------------------------------------------------------------- -// Function: ft1000_CreateDevice -// -// Parameters: dev - pointer to adapter object -// -// Returns: 0 if successful -// -// Description: Creates a private char device. -// -// Notes: Only called by init_module(). -// -//--------------------------------------------------------------------------- -int ft1000_create_dev(struct ft1000_device *dev) +/* +*--------------------------------------------------------------------------- +* Function: ft1000_CreateDevice +* +* Parameters: dev - pointer to adapter object +* +* Returns: 0 if successful +* +* Description: Creates a private char device. +* +* Notes: Only called by init_module(). +* +*--------------------------------------------------------------------------- +*/ +int ft1000_create_dev(struct ft1000_usb *dev) { - struct ft1000_info *info = netdev_priv(dev->net); int result; int i; struct dentry *dir, *file; struct ft1000_debug_dirs *tmp; - // make a new device name - sprintf(info->DeviceName, "%s%d", "FT1000_", info->CardNumber); + /* make a new device name */ + sprintf(dev->DeviceName, "%s%d", "FT1000_", dev->CardNumber); DEBUG("%s: number of instance = %d\n", __func__, ft1000_flarion_cnt); - DEBUG("DeviceCreated = %x\n", info->DeviceCreated); + DEBUG("DeviceCreated = %x\n", dev->DeviceCreated); - if (info->DeviceCreated) - { - DEBUG("%s: \"%s\" already registered\n", __func__, info->DeviceName); + if (dev->DeviceCreated) { + DEBUG("%s: \"%s\" already registered\n", __func__, dev->DeviceName); return -EIO; } - // register the device - DEBUG("%s: \"%s\" debugfs device registration\n", __func__, info->DeviceName); + /* register the device */ + DEBUG("%s: \"%s\" debugfs device registration\n", __func__, dev->DeviceName); tmp = kmalloc(sizeof(struct ft1000_debug_dirs), GFP_KERNEL); if (tmp == NULL) { @@ -167,7 +171,7 @@ int ft1000_create_dev(struct ft1000_device *dev) goto fail; } - dir = debugfs_create_dir(info->DeviceName, 0); + dir = debugfs_create_dir(dev->DeviceName, NULL); if (IS_ERR(dir)) { result = PTR_ERR(dir); goto debug_dir_fail; @@ -182,27 +186,27 @@ int ft1000_create_dev(struct ft1000_device *dev) tmp->dent = dir; tmp->file = file; - tmp->int_number = info->CardNumber; - list_add(&(tmp->list), &(info->nodes.list)); + tmp->int_number = dev->CardNumber; + list_add(&(tmp->list), &(dev->nodes.list)); - DEBUG("%s: registered debugfs directory \"%s\"\n", __func__, info->DeviceName); + DEBUG("%s: registered debugfs directory \"%s\"\n", __func__, dev->DeviceName); - // initialize application information - info->appcnt = 0; + /* initialize application information */ + dev->appcnt = 0; for (i=0; i<MAX_NUM_APP; i++) { - info->app_info[i].nTxMsg = 0; - info->app_info[i].nRxMsg = 0; - info->app_info[i].nTxMsgReject = 0; - info->app_info[i].nRxMsgMiss = 0; - info->app_info[i].fileobject = NULL; - info->app_info[i].app_id = i+1; - info->app_info[i].DspBCMsgFlag = 0; - info->app_info[i].NumOfMsg = 0; - init_waitqueue_head(&info->app_info[i].wait_dpram_msg); - INIT_LIST_HEAD (&info->app_info[i].app_sqlist); + dev->app_info[i].nTxMsg = 0; + dev->app_info[i].nRxMsg = 0; + dev->app_info[i].nTxMsgReject = 0; + dev->app_info[i].nRxMsgMiss = 0; + dev->app_info[i].fileobject = NULL; + dev->app_info[i].app_id = i+1; + dev->app_info[i].DspBCMsgFlag = 0; + dev->app_info[i].NumOfMsg = 0; + init_waitqueue_head(&dev->app_info[i].wait_dpram_msg); + INIT_LIST_HEAD(&dev->app_info[i].app_sqlist); } - info->DeviceCreated = TRUE; + dev->DeviceCreated = TRUE; ft1000_flarion_cnt++; return 0; @@ -215,19 +219,22 @@ fail: return result; } -//--------------------------------------------------------------------------- -// Function: ft1000_DestroyDeviceDEBUG -// -// Parameters: dev - pointer to adapter object -// -// Description: Destroys a private char device. -// -// Notes: Only called by cleanup_module(). -// -//--------------------------------------------------------------------------- -void ft1000_destroy_dev(struct net_device *dev) +/* +*--------------------------------------------------------------------------- +* Function: ft1000_DestroyDeviceDEBUG +* +* Parameters: dev - pointer to adapter object +* +* Description: Destroys a private char device. +* +* Notes: Only called by cleanup_module(). +* +*--------------------------------------------------------------------------- +*/ +void ft1000_destroy_dev(struct net_device *netdev) { - struct ft1000_info *info = netdev_priv(dev); + struct ft1000_info *info = netdev_priv(netdev); + struct ft1000_usb *dev = info->priv; int i; struct dpram_blk *pdpram_blk; struct dpram_blk *ptr; @@ -238,12 +245,11 @@ void ft1000_destroy_dev(struct net_device *dev) - if (info->DeviceCreated) - { + if (dev->DeviceCreated) { ft1000_flarion_cnt--; - list_for_each_safe(pos, q, &info->nodes.list) { + list_for_each_safe(pos, q, &dev->nodes.list) { dir = list_entry(pos, struct ft1000_debug_dirs, list); - if (dir->int_number == info->CardNumber) { + if (dir->int_number == dev->CardNumber) { debugfs_remove(dir->file); debugfs_remove(dir->dent); list_del(pos); @@ -251,20 +257,20 @@ void ft1000_destroy_dev(struct net_device *dev) } } DEBUG("%s: unregistered device \"%s\"\n", __func__, - info->DeviceName); + dev->DeviceName); - // Make sure we free any memory reserve for slow Queue + /* Make sure we free any memory reserve for slow Queue */ for (i=0; i<MAX_NUM_APP; i++) { - while (list_empty(&info->app_info[i].app_sqlist) == 0) { - pdpram_blk = list_entry(info->app_info[i].app_sqlist.next, struct dpram_blk, list); + while (list_empty(&dev->app_info[i].app_sqlist) == 0) { + pdpram_blk = list_entry(dev->app_info[i].app_sqlist.next, struct dpram_blk, list); list_del(&pdpram_blk->list); ft1000_free_buffer(pdpram_blk, &freercvpool); } - wake_up_interruptible(&info->app_info[i].wait_dpram_msg); + wake_up_interruptible(&dev->app_info[i].wait_dpram_msg); } - // Remove buffer allocated for receive command data + /* Remove buffer allocated for receive command data */ if (ft1000_flarion_cnt == 0) { while (list_empty(&freercvpool) == 0) { ptr = list_entry(freercvpool.next, struct dpram_blk, list); @@ -273,26 +279,28 @@ void ft1000_destroy_dev(struct net_device *dev) kfree(ptr); } } - info->DeviceCreated = FALSE; + dev->DeviceCreated = FALSE; } } -//--------------------------------------------------------------------------- -// Function: ft1000_open -// -// Parameters: -// -// Description: -// -// Notes: -// -//--------------------------------------------------------------------------- -static int ft1000_open (struct inode *inode, struct file *file) +/* +*--------------------------------------------------------------------------- +* Function: ft1000_open +* +* Parameters: +* +* Description: +* +* Notes: +* +*--------------------------------------------------------------------------- +*/ +static int ft1000_open(struct inode *inode, struct file *file) { struct ft1000_info *info; - struct ft1000_device *dev = (struct ft1000_device *)inode->i_private; + struct ft1000_usb *dev = (struct ft1000_usb *)inode->i_private; int i,num; DEBUG("%s called\n", __func__); @@ -301,113 +309,116 @@ static int ft1000_open (struct inode *inode, struct file *file) info = file->private_data = netdev_priv(dev->net); - DEBUG("f_owner = %p number of application = %d\n", (&file->f_owner), info->appcnt ); + DEBUG("f_owner = %p number of application = %d\n", (&file->f_owner), dev->appcnt); - // Check if maximum number of application exceeded - if (info->appcnt > MAX_NUM_APP) { + /* Check if maximum number of application exceeded */ + if (dev->appcnt > MAX_NUM_APP) { DEBUG("Maximum number of application exceeded\n"); return -EACCES; } - // Search for available application info block + /* Search for available application info block */ for (i=0; i<MAX_NUM_APP; i++) { - if ( (info->app_info[i].fileobject == NULL) ) { + if ((dev->app_info[i].fileobject == NULL)) { break; } } - // Fail due to lack of application info block + /* Fail due to lack of application info block */ if (i == MAX_NUM_APP) { DEBUG("Could not find an application info block\n"); return -EACCES; } - info->appcnt++; - info->app_info[i].fileobject = &file->f_owner; - info->app_info[i].nTxMsg = 0; - info->app_info[i].nRxMsg = 0; - info->app_info[i].nTxMsgReject = 0; - info->app_info[i].nRxMsgMiss = 0; + dev->appcnt++; + dev->app_info[i].fileobject = &file->f_owner; + dev->app_info[i].nTxMsg = 0; + dev->app_info[i].nRxMsg = 0; + dev->app_info[i].nTxMsgReject = 0; + dev->app_info[i].nRxMsgMiss = 0; nonseekable_open(inode, file); return 0; } -//--------------------------------------------------------------------------- -// Function: ft1000_poll_dev -// -// Parameters: -// -// Description: -// -// Notes: -// -//--------------------------------------------------------------------------- +/* +*--------------------------------------------------------------------------- +* Function: ft1000_poll_dev +* +* Parameters: +* +* Description: +* +* Notes: +* +*--------------------------------------------------------------------------- +*/ static unsigned int ft1000_poll_dev(struct file *file, poll_table *wait) { - struct net_device *dev = file->private_data; - struct ft1000_info *info; + struct net_device *netdev = file->private_data; + struct ft1000_info *info = netdev_priv(netdev); + struct ft1000_usb *dev = info->priv; int i; - //DEBUG("ft1000_poll_dev called\n"); + /* DEBUG("ft1000_poll_dev called\n"); */ if (ft1000_flarion_cnt == 0) { DEBUG("FT1000:ft1000_poll_dev called when ft1000_flarion_cnt is zero\n"); return (-EBADF); } - info = netdev_priv(dev); - - // Search for matching file object + /* Search for matching file object */ for (i=0; i<MAX_NUM_APP; i++) { - if ( info->app_info[i].fileobject == &file->f_owner) { - //DEBUG("FT1000:ft1000_ioctl: Message is for AppId = %d\n", info->app_info[i].app_id); + if (dev->app_info[i].fileobject == &file->f_owner) { + /* DEBUG("FT1000:ft1000_ioctl: Message is for AppId = %d\n", dev->app_info[i].app_id); */ break; } } - // Could not find application info block + /* Could not find application info block */ if (i == MAX_NUM_APP) { DEBUG("FT1000:ft1000_ioctl:Could not find application info block\n"); - return ( -EACCES ); + return (-EACCES); } - if (list_empty(&info->app_info[i].app_sqlist) == 0) { + if (list_empty(&dev->app_info[i].app_sqlist) == 0) { DEBUG("FT1000:ft1000_poll_dev:Message detected in slow queue\n"); return(POLLIN | POLLRDNORM | POLLPRI); } - poll_wait (file, &info->app_info[i].wait_dpram_msg, wait); - //DEBUG("FT1000:ft1000_poll_dev:Polling for data from DSP\n"); + poll_wait(file, &dev->app_info[i].wait_dpram_msg, wait); + /* DEBUG("FT1000:ft1000_poll_dev:Polling for data from DSP\n"); */ return (0); } -//--------------------------------------------------------------------------- -// Function: ft1000_ioctl -// -// Parameters: -// -// Description: -// -// Notes: -// -//--------------------------------------------------------------------------- -static long ft1000_ioctl (struct file *file, unsigned int command, +/* +*--------------------------------------------------------------------------- +* Function: ft1000_ioctl +* +* Parameters: +* +* Description: +* +* Notes: +* +*--------------------------------------------------------------------------- +*/ +static long ft1000_ioctl(struct file *file, unsigned int command, unsigned long argument) { void __user *argp = (void __user *)argument; struct ft1000_info *info; - struct ft1000_device *ft1000dev; + struct ft1000_usb *ft1000dev; int result=0; int cmd; int i; u16 tempword; unsigned long flags; struct timeval tv; - IOCTL_GET_VER get_ver_data; - IOCTL_GET_DSP_STAT get_stat_data; + struct IOCTL_GET_VER get_ver_data; + struct IOCTL_GET_DSP_STAT get_stat_data; u8 ConnectionMsg[] = {0x00,0x44,0x10,0x20,0x80,0x00,0x00,0x00,0x00,0x00,0x03,0x00,0x00,0x00,0x93,0x64, 0x00,0x00,0x02,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x05,0x00,0x00,0x00,0x0a, 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x02,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, @@ -418,21 +429,21 @@ static long ft1000_ioctl (struct file *file, unsigned int command, unsigned short ledStat=0; unsigned short conStat=0; - //DEBUG("ft1000_ioctl called\n"); + /* DEBUG("ft1000_ioctl called\n"); */ if (ft1000_flarion_cnt == 0) { DEBUG("FT1000:ft1000_ioctl called when ft1000_flarion_cnt is zero\n"); return (-EBADF); } - //DEBUG("FT1000:ft1000_ioctl:command = 0x%x argument = 0x%8x\n", command, (u32)argument); + /* DEBUG("FT1000:ft1000_ioctl:command = 0x%x argument = 0x%8x\n", command, (u32)argument); */ info = file->private_data; - ft1000dev = info->pFt1000Dev; + ft1000dev = info->priv; cmd = _IOC_NR(command); - //DEBUG("FT1000:ft1000_ioctl:cmd = 0x%x\n", cmd); + /* DEBUG("FT1000:ft1000_ioctl:cmd = 0x%x\n", cmd); */ - // process the command + /* process the command */ switch (cmd) { case IOCTL_REGISTER_CMD: DEBUG("FT1000:ft1000_ioctl: IOCTL_FT1000_REGISTER called\n"); @@ -442,10 +453,10 @@ static long ft1000_ioctl (struct file *file, unsigned int command, break; } if (tempword == DSPBCMSGID) { - // Search for matching file object + /* Search for matching file object */ for (i=0; i<MAX_NUM_APP; i++) { - if ( info->app_info[i].fileobject == &file->f_owner) { - info->app_info[i].DspBCMsgFlag = 1; + if (ft1000dev->app_info[i].fileobject == &file->f_owner) { + ft1000dev->app_info[i].DspBCMsgFlag = 1; DEBUG("FT1000:ft1000_ioctl:Registered for broadcast messages\n"); break; } @@ -458,7 +469,7 @@ static long ft1000_ioctl (struct file *file, unsigned int command, get_ver_data.drv_ver = FT1000_DRV_VER; - if (copy_to_user(argp, &get_ver_data, sizeof(get_ver_data)) ) { + if (copy_to_user(argp, &get_ver_data, sizeof(get_ver_data))) { DEBUG("FT1000:ft1000_ioctl: copy fault occurred\n"); result = -EFAULT; break; @@ -468,20 +479,20 @@ static long ft1000_ioctl (struct file *file, unsigned int command, break; case IOCTL_CONNECT: - // Connect Message + /* Connect Message */ DEBUG("FT1000:ft1000_ioctl: IOCTL_FT1000_CONNECT\n"); ConnectionMsg[79] = 0xfc; - CardSendCommand(ft1000dev, (unsigned short *)ConnectionMsg, 0x4c); + card_send_command(ft1000dev, (unsigned short *)ConnectionMsg, 0x4c); break; case IOCTL_DISCONNECT: - // Disconnect Message + /* Disconnect Message */ DEBUG("FT1000:ft1000_ioctl: IOCTL_FT1000_DISCONNECT\n"); ConnectionMsg[79] = 0xfd; - CardSendCommand(ft1000dev, (unsigned short *)ConnectionMsg, 0x4c); + card_send_command(ft1000dev, (unsigned short *)ConnectionMsg, 0x4c); break; case IOCTL_GET_DSP_STAT_CMD: - //DEBUG("FT1000:ft1000_ioctl: IOCTL_FT1000_GET_DSP_STAT called\n"); + /* DEBUG("FT1000:ft1000_ioctl: IOCTL_FT1000_GET_DSP_STAT called\n"); */ memset(&get_stat_data, 0, sizeof(get_stat_data)); memcpy(get_stat_data.DspVer, info->DspVer, DSPVERSZ); memcpy(get_stat_data.HwSerNum, info->HwSerNum, HWSERNUMSZ); @@ -495,8 +506,7 @@ static long ft1000_ioctl (struct file *file, unsigned int command, ft1000_read_dpram16(ft1000dev, FT1000_MAG_DSP_CON_STATE, (u8 *)&conStat, FT1000_MAG_DSP_CON_STATE_INDX); get_stat_data.ConStat = ntohs(conStat); DEBUG("FT1000:ft1000_ioctl: ConStat = 0x%x\n", get_stat_data.ConStat); - } - else { + } else { get_stat_data.ConStat = 0x0f; } @@ -505,10 +515,10 @@ static long ft1000_ioctl (struct file *file, unsigned int command, get_stat_data.nRxPkts = info->stats.rx_packets; get_stat_data.nTxBytes = info->stats.tx_bytes; get_stat_data.nRxBytes = info->stats.rx_bytes; - do_gettimeofday ( &tv ); + do_gettimeofday(&tv); get_stat_data.ConTm = (u32)(tv.tv_sec - info->ConTm); DEBUG("Connection Time = %d\n", (int)get_stat_data.ConTm); - if (copy_to_user(argp, &get_stat_data, sizeof(get_stat_data)) ) { + if (copy_to_user(argp, &get_stat_data, sizeof(get_stat_data))) { DEBUG("FT1000:ft1000_ioctl: copy fault occurred\n"); result = -EFAULT; break; @@ -517,8 +527,8 @@ static long ft1000_ioctl (struct file *file, unsigned int command, break; case IOCTL_SET_DPRAM_CMD: { - IOCTL_DPRAM_BLK *dpram_data = NULL; - //IOCTL_DPRAM_COMMAND dpram_command; + struct IOCTL_DPRAM_BLK *dpram_data = NULL; + /* struct IOCTL_DPRAM_COMMAND dpram_command; */ u16 qtype; u16 msgsz; struct pseudo_hdr *ppseudo_hdr; @@ -527,31 +537,33 @@ static long ft1000_ioctl (struct file *file, unsigned int command, u16 app_index; u16 status; - //DEBUG("FT1000:ft1000_ioctl: IOCTL_FT1000_SET_DPRAM called\n"); + /* DEBUG("FT1000:ft1000_ioctl: IOCTL_FT1000_SET_DPRAM called\n");*/ if (ft1000_flarion_cnt == 0) { return (-EBADF); } - if (info->DrvMsgPend) { + if (ft1000dev->DrvMsgPend) { return (-ENOTTY); } - if ( (info->DspAsicReset) || (info->fProvComplete == 0) ) { + if (ft1000dev->fProvComplete == 0) { return (-EACCES); } - info->fAppMsgPend = 1; + ft1000dev->fAppMsgPend = 1; if (info->CardReady) { - //DEBUG("FT1000:ft1000_ioctl: try to SET_DPRAM \n"); + /* DEBUG("FT1000:ft1000_ioctl: try to SET_DPRAM \n"); */ - // Get the length field to see how many bytes to copy + /* Get the length field to see how many bytes to copy */ result = get_user(msgsz, (__u16 __user *)argp); - msgsz = ntohs (msgsz); - //DEBUG("FT1000:ft1000_ioctl: length of message = %d\n", msgsz); + if (result) + break; + msgsz = ntohs(msgsz); + /* DEBUG("FT1000:ft1000_ioctl: length of message = %d\n", msgsz); */ if (msgsz > MAX_CMD_SQSIZE) { DEBUG("FT1000:ft1000_ioctl: bad message length = %d\n", msgsz); @@ -564,14 +576,13 @@ static long ft1000_ioctl (struct file *file, unsigned int command, if (!dpram_data) break; - if ( copy_from_user(dpram_data, argp, msgsz+2) ) { + if (copy_from_user(dpram_data, argp, msgsz+2)) { DEBUG("FT1000:ft1000_ChIoctl: copy fault occurred\n"); result = -EFAULT; - } - else { - // Check if this message came from a registered application + } else { + /* Check if this message came from a registered application */ for (i=0; i<MAX_NUM_APP; i++) { - if ( info->app_info[i].fileobject == &file->f_owner) { + if (ft1000dev->app_info[i].fileobject == &file->f_owner) { break; } } @@ -583,28 +594,27 @@ static long ft1000_ioctl (struct file *file, unsigned int command, } app_index = i; - // Check message qtype type which is the lower byte within qos_class + /* Check message qtype type which is the lower byte within qos_class */ qtype = ntohs(dpram_data->pseudohdr.qos_class) & 0xff; - //DEBUG("FT1000_ft1000_ioctl: qtype = %d\n", qtype); + /* DEBUG("FT1000_ft1000_ioctl: qtype = %d\n", qtype); */ if (qtype) { - } - else { - // Put message into Slow Queue - // Only put a message into the DPRAM if msg doorbell is available + } else { + /* Put message into Slow Queue */ + /* Only put a message into the DPRAM if msg doorbell is available */ status = ft1000_read_register(ft1000dev, &tempword, FT1000_REG_DOORBELL); - //DEBUG("FT1000_ft1000_ioctl: READ REGISTER tempword=%x\n", tempword); + /* DEBUG("FT1000_ft1000_ioctl: READ REGISTER tempword=%x\n", tempword); */ if (tempword & FT1000_DB_DPRAM_TX) { - // Suspend for 2ms and try again due to DSP doorbell busy + /* Suspend for 2ms and try again due to DSP doorbell busy */ mdelay(2); status = ft1000_read_register(ft1000dev, &tempword, FT1000_REG_DOORBELL); if (tempword & FT1000_DB_DPRAM_TX) { - // Suspend for 1ms and try again due to DSP doorbell busy + /* Suspend for 1ms and try again due to DSP doorbell busy */ mdelay(1); status = ft1000_read_register(ft1000dev, &tempword, FT1000_REG_DOORBELL); if (tempword & FT1000_DB_DPRAM_TX) { status = ft1000_read_register(ft1000dev, &tempword, FT1000_REG_DOORBELL); if (tempword & FT1000_DB_DPRAM_TX) { - // Suspend for 3ms and try again due to DSP doorbell busy + /* Suspend for 3ms and try again due to DSP doorbell busy */ mdelay(3); status = ft1000_read_register(ft1000dev, &tempword, FT1000_REG_DOORBELL); if (tempword & FT1000_DB_DPRAM_TX) { @@ -618,11 +628,11 @@ static long ft1000_ioctl (struct file *file, unsigned int command, } } - //DEBUG("FT1000_ft1000_ioctl: finished reading register\n"); + /*DEBUG("FT1000_ft1000_ioctl: finished reading register\n"); */ - // Make sure we are within the limits of the slow queue memory limitation - if ( (msgsz < MAX_CMD_SQSIZE) && (msgsz > PSEUDOSZ) ) { - // Need to put sequence number plus new checksum for message + /* Make sure we are within the limits of the slow queue memory limitation */ + if ((msgsz < MAX_CMD_SQSIZE) && (msgsz > PSEUDOSZ)) { + /* Need to put sequence number plus new checksum for message */ pmsg = (u16 *)&dpram_data->pseudohdr; ppseudo_hdr = (struct pseudo_hdr *)pmsg; total_len = msgsz+2; @@ -630,30 +640,28 @@ static long ft1000_ioctl (struct file *file, unsigned int command, total_len++; } - // Insert slow queue sequence number + /* Insert slow queue sequence number */ ppseudo_hdr->seq_num = info->squeseqnum++; - ppseudo_hdr->portsrc = info->app_info[app_index].app_id; - // Calculate new checksum + ppseudo_hdr->portsrc = ft1000dev->app_info[app_index].app_id; + /* Calculate new checksum */ ppseudo_hdr->checksum = *pmsg++; - //DEBUG("checksum = 0x%x\n", ppseudo_hdr->checksum); + /* DEBUG("checksum = 0x%x\n", ppseudo_hdr->checksum); */ for (i=1; i<7; i++) { ppseudo_hdr->checksum ^= *pmsg++; - //DEBUG("checksum = 0x%x\n", ppseudo_hdr->checksum); + /* DEBUG("checksum = 0x%x\n", ppseudo_hdr->checksum); */ } pmsg++; ppseudo_hdr = (struct pseudo_hdr *)pmsg; - CardSendCommand(ft1000dev,(unsigned short*)dpram_data,total_len+2); + card_send_command(ft1000dev,(unsigned short*)dpram_data,total_len+2); - info->app_info[app_index].nTxMsg++; - } - else { + ft1000dev->app_info[app_index].nTxMsg++; + } else { result = -EINVAL; } } } - } - else { + } else { DEBUG("FT1000:ft1000_ioctl: Card not ready take messages\n"); result = -EACCES; } @@ -664,24 +672,24 @@ static long ft1000_ioctl (struct file *file, unsigned int command, case IOCTL_GET_DPRAM_CMD: { struct dpram_blk *pdpram_blk; - IOCTL_DPRAM_BLK __user *pioctl_dpram; + struct IOCTL_DPRAM_BLK __user *pioctl_dpram; int msglen; - //DEBUG("FT1000:ft1000_ioctl: IOCTL_FT1000_GET_DPRAM called\n"); + /* DEBUG("FT1000:ft1000_ioctl: IOCTL_FT1000_GET_DPRAM called\n"); */ if (ft1000_flarion_cnt == 0) { return (-EBADF); } - // Search for matching file object + /* Search for matching file object */ for (i=0; i<MAX_NUM_APP; i++) { - if ( info->app_info[i].fileobject == &file->f_owner) { - //DEBUG("FT1000:ft1000_ioctl: Message is for AppId = %d\n", info->app_info[i].app_id); + if (ft1000dev->app_info[i].fileobject == &file->f_owner) { + /*DEBUG("FT1000:ft1000_ioctl: Message is for AppId = %d\n", ft1000dev->app_info[i].app_id); */ break; } } - // Could not find application info block + /* Could not find application info block */ if (i == MAX_NUM_APP) { DEBUG("FT1000:ft1000_ioctl:Could not find application info block\n"); result = -EBADF; @@ -690,31 +698,30 @@ static long ft1000_ioctl (struct file *file, unsigned int command, result = 0; pioctl_dpram = argp; - if (list_empty(&info->app_info[i].app_sqlist) == 0) { - //DEBUG("FT1000:ft1000_ioctl:Message detected in slow queue\n"); + if (list_empty(&ft1000dev->app_info[i].app_sqlist) == 0) { + /* DEBUG("FT1000:ft1000_ioctl:Message detected in slow queue\n"); */ spin_lock_irqsave(&free_buff_lock, flags); - pdpram_blk = list_entry(info->app_info[i].app_sqlist.next, struct dpram_blk, list); + pdpram_blk = list_entry(ft1000dev->app_info[i].app_sqlist.next, struct dpram_blk, list); list_del(&pdpram_blk->list); - info->app_info[i].NumOfMsg--; - //DEBUG("FT1000:ft1000_ioctl:NumOfMsg for app %d = %d\n", i, info->app_info[i].NumOfMsg); + ft1000dev->app_info[i].NumOfMsg--; + /* DEBUG("FT1000:ft1000_ioctl:NumOfMsg for app %d = %d\n", i, ft1000dev->app_info[i].NumOfMsg); */ spin_unlock_irqrestore(&free_buff_lock, flags); msglen = ntohs(*(u16 *)pdpram_blk->pbuffer) + PSEUDOSZ; result = get_user(msglen, &pioctl_dpram->total_len); if (result) break; msglen = htons(msglen); - //DEBUG("FT1000:ft1000_ioctl:msg length = %x\n", msglen); - if(copy_to_user (&pioctl_dpram->pseudohdr, pdpram_blk->pbuffer, msglen)) - { + /* DEBUG("FT1000:ft1000_ioctl:msg length = %x\n", msglen); */ + if (copy_to_user (&pioctl_dpram->pseudohdr, pdpram_blk->pbuffer, msglen)) { DEBUG("FT1000:ft1000_ioctl: copy fault occurred\n"); - result = -EFAULT; - break; + result = -EFAULT; + break; } ft1000_free_buffer(pdpram_blk, &freercvpool); result = msglen; } - //DEBUG("FT1000:ft1000_ioctl: IOCTL_FT1000_GET_DPRAM no message\n"); + /* DEBUG("FT1000:ft1000_ioctl: IOCTL_FT1000_GET_DPRAM no message\n"); */ } break; @@ -723,24 +730,27 @@ static long ft1000_ioctl (struct file *file, unsigned int command, result = -ENOTTY; break; } - info->fAppMsgPend = 0; + ft1000dev->fAppMsgPend = 0; return result; } -//--------------------------------------------------------------------------- -// Function: ft1000_release -// -// Parameters: -// -// Description: -// -// Notes: -// -//--------------------------------------------------------------------------- -static int ft1000_release (struct inode *inode, struct file *file) +/* +*--------------------------------------------------------------------------- +* Function: ft1000_release +* +* Parameters: +* +* Description: +* +* Notes: +* +*--------------------------------------------------------------------------- +*/ +static int ft1000_release(struct inode *inode, struct file *file) { struct ft1000_info *info; struct net_device *dev; + struct ft1000_usb *ft1000dev; int i; struct dpram_blk *pdpram_blk; @@ -748,16 +758,17 @@ static int ft1000_release (struct inode *inode, struct file *file) dev = file->private_data; info = netdev_priv(dev); + ft1000dev = info->priv; if (ft1000_flarion_cnt == 0) { - info->appcnt--; + ft1000dev->appcnt--; return (-EBADF); } - // Search for matching file object + /* Search for matching file object */ for (i=0; i<MAX_NUM_APP; i++) { - if ( info->app_info[i].fileobject == &file->f_owner) { - //DEBUG("FT1000:ft1000_ioctl: Message is for AppId = %d\n", info->app_info[i].app_id); + if (ft1000dev->app_info[i].fileobject == &file->f_owner) { + /* DEBUG("FT1000:ft1000_ioctl: Message is for AppId = %d\n", ft1000dev->app_info[i].app_id); */ break; } } @@ -765,18 +776,17 @@ static int ft1000_release (struct inode *inode, struct file *file) if (i==MAX_NUM_APP) return 0; - while (list_empty(&info->app_info[i].app_sqlist) == 0) { + while (list_empty(&ft1000dev->app_info[i].app_sqlist) == 0) { DEBUG("Remove and free memory queue up on slow queue\n"); - pdpram_blk = list_entry(info->app_info[i].app_sqlist.next, struct dpram_blk, list); + pdpram_blk = list_entry(ft1000dev->app_info[i].app_sqlist.next, struct dpram_blk, list); list_del(&pdpram_blk->list); ft1000_free_buffer(pdpram_blk, &freercvpool); } - // initialize application information - info->appcnt--; - DEBUG("ft1000_chdev:%s:appcnt = %d\n", __FUNCTION__, info->appcnt); - info->app_info[i].fileobject = NULL; + /* initialize application information */ + ft1000dev->appcnt--; + DEBUG("ft1000_chdev:%s:appcnt = %d\n", __func__, ft1000dev->appcnt); + ft1000dev->app_info[i].fileobject = NULL; return 0; } - diff --git a/drivers/staging/ft1000/ft1000-usb/ft1000_download.c b/drivers/staging/ft1000/ft1000-usb/ft1000_download.c index 17546d8ec08..65f98016713 100644 --- a/drivers/staging/ft1000/ft1000-usb/ft1000_download.c +++ b/drivers/staging/ft1000/ft1000-usb/ft1000_download.c @@ -1,14 +1,9 @@ -//===================================================== -// CopyRight (C) 2007 Qualcomm Inc. All Rights Reserved. -// -// -// This file is part of Express Card USB Driver -// -// $Id: -//==================================================== -// 20090926; aelias; removed compiler warnings; ubuntu 9.04; 2.6.28-15-generic - -#include <linux/init.h> +/* +* CopyRight (C) 2007 Qualcomm Inc. All Rights Reserved. +* +* This file is part of Express Card USB Driver +*/ + #include <linux/kernel.h> #include <linux/module.h> #include <linux/netdevice.h> @@ -59,7 +54,7 @@ #define MAX_LENGTH 0x7f0 -// Temporary download mechanism for Magnemite +/* Temporary download mechanism for Magnemite */ #define DWNLD_MAG_TYPE_LOC 0x00 #define DWNLD_MAG_LEN_LOC 0x01 #define DWNLD_MAG_ADDR_LOC 0x02 @@ -78,1171 +73,1002 @@ #define HANDSHAKE_MAG_TIMEOUT_VALUE 0xF1F1 -// New Magnemite downloader +/* New Magnemite downloader */ #define DWNLD_MAG1_HANDSHAKE_LOC 0x00 #define DWNLD_MAG1_TYPE_LOC 0x01 #define DWNLD_MAG1_SIZE_LOC 0x02 #define DWNLD_MAG1_PS_HDR_LOC 0x03 struct dsp_file_hdr { - long version_id; // Version ID of this image format. - long package_id; // Package ID of code release. - long build_date; // Date/time stamp when file was built. - long commands_offset; // Offset to attached commands in Pseudo Hdr format. - long loader_offset; // Offset to bootloader code. - long loader_code_address; // Start address of bootloader. - long loader_code_end; // Where bootloader code ends. - long loader_code_size; - long version_data_offset; // Offset were scrambled version data begins. - long version_data_size; // Size, in words, of scrambled version data. - long nDspImages; // Number of DSP images in file. + long version_id; /* Version ID of this image format. */ + long package_id; /* Package ID of code release. */ + long build_date; /* Date/time stamp when file was built. */ + long commands_offset; /* Offset to attached commands in Pseudo Hdr format. */ + long loader_offset; /* Offset to bootloader code. */ + long loader_code_address; /* Start address of bootloader. */ + long loader_code_end; /* Where bootloader code ends. */ + long loader_code_size; + long version_data_offset; /* Offset were scrambled version data begins. */ + long version_data_size; /* Size, in words, of scrambled version data. */ + long nDspImages; /* Number of DSP images in file. */ }; #pragma pack(1) struct dsp_image_info { - long coff_date; // Date/time when DSP Coff image was built. - long begin_offset; // Offset in file where image begins. - long end_offset; // Offset in file where image begins. - long run_address; // On chip Start address of DSP code. - long image_size; // Size of image. - long version; // Embedded version # of DSP code. - unsigned short checksum; // DSP File checksum - unsigned short pad1; + long coff_date; /* Date/time when DSP Coff image was built. */ + long begin_offset; /* Offset in file where image begins. */ + long end_offset; /* Offset in file where image begins. */ + long run_address; /* On chip Start address of DSP code. */ + long image_size; /* Size of image. */ + long version; /* Embedded version # of DSP code. */ + unsigned short checksum; /* DSP File checksum */ + unsigned short pad1; }; -//--------------------------------------------------------------------------- -// Function: check_usb_db -// -// Parameters: struct ft1000_device - device structure -// -// Returns: 0 - success -// -// Description: This function checks if the doorbell register is cleared -// -// Notes: -// -//--------------------------------------------------------------------------- -static u32 check_usb_db (struct ft1000_device *ft1000dev) +/* checks if the doorbell register is cleared */ +static int check_usb_db(struct ft1000_usb *ft1000dev) { - int loopcnt; - u16 temp; - u32 status; - - loopcnt = 0; - while (loopcnt < 10) - { - - status = ft1000_read_register (ft1000dev, &temp, FT1000_REG_DOORBELL); - DEBUG("check_usb_db: read FT1000_REG_DOORBELL value is %x\n", temp); - if (temp & 0x0080) - { - DEBUG("FT1000:Got checkusb doorbell\n"); - status = ft1000_write_register (ft1000dev, 0x0080, FT1000_REG_DOORBELL); - status = ft1000_write_register (ft1000dev, 0x0100, FT1000_REG_DOORBELL); - status = ft1000_write_register (ft1000dev, 0x8000, FT1000_REG_DOORBELL); - break; - } - else - { - loopcnt++; - msleep (10); - } + int loopcnt; + u16 temp; + int status; + + loopcnt = 0; + + while (loopcnt < 10) { + status = ft1000_read_register(ft1000dev, &temp, + FT1000_REG_DOORBELL); + DEBUG("check_usb_db: read FT1000_REG_DOORBELL value is %x\n", + temp); + if (temp & 0x0080) { + DEBUG("FT1000:Got checkusb doorbell\n"); + status = ft1000_write_register(ft1000dev, 0x0080, + FT1000_REG_DOORBELL); + status = ft1000_write_register(ft1000dev, 0x0100, + FT1000_REG_DOORBELL); + status = ft1000_write_register(ft1000dev, 0x8000, + FT1000_REG_DOORBELL); + break; + } else { + loopcnt++; + msleep(10); + } - } //end of while + } + + loopcnt = 0; + while (loopcnt < 20) { + status = ft1000_read_register(ft1000dev, &temp, + FT1000_REG_DOORBELL); + DEBUG("FT1000:check_usb_db:Doorbell = 0x%x\n", temp); + if (temp & 0x8000) { + loopcnt++; + msleep(10); + } else { + DEBUG("check_usb_db: door bell is cleared, return 0\n"); + return 0; + } + } + return -1; +} - loopcnt = 0; - while (loopcnt < 20) - { +/* gets the handshake and compares it with the expected value */ +static u16 get_handshake(struct ft1000_usb *ft1000dev, u16 expected_value) +{ + u16 handshake; + int loopcnt; + int status = 0; + + loopcnt = 0; + + while (loopcnt < 100) { + /* Need to clear downloader doorbell if Hartley ASIC */ + status = ft1000_write_register(ft1000dev, FT1000_DB_DNLD_RX, + FT1000_REG_DOORBELL); + if (ft1000dev->fcodeldr) { + DEBUG(" get_handshake: fcodeldr is %d\n", + ft1000dev->fcodeldr); + ft1000dev->fcodeldr = 0; + status = check_usb_db(ft1000dev); + if (status != 0) { + DEBUG("get_handshake: check_usb_db failed\n"); + break; + } + status = ft1000_write_register(ft1000dev, + FT1000_DB_DNLD_RX, + FT1000_REG_DOORBELL); + } - status = ft1000_read_register (ft1000dev, &temp, FT1000_REG_DOORBELL); - DEBUG("FT1000:check_usb_db:Doorbell = 0x%x\n", temp); - if (temp & 0x8000) - { - loopcnt++; - msleep (10); - } - else - { - DEBUG("check_usb_db: door bell is cleared, return 0\n"); - return 0; - } -#if 0 - // Check if Card is present - status = ft1000_read_register (ft1000dev, &temp, FT1000_REG_SUP_IMASK); - if (temp == 0x0000) { - break; - } + status = ft1000_read_dpram16(ft1000dev, + DWNLD_MAG1_HANDSHAKE_LOC, (u8 *)&handshake, 1); + handshake = ntohs(handshake); - status = ft1000_read_register (ft1000dev, &temp, FT1000_REG_ASIC_ID); - if (temp == 0xffff) { - break; - } -#endif - } + if (status) + return HANDSHAKE_TIMEOUT_VALUE; - return HANDSHAKE_MAG_TIMEOUT_VALUE; + if ((handshake == expected_value) || + (handshake == HANDSHAKE_RESET_VALUE_USB)) { + return handshake; + } else { + loopcnt++; + msleep(10); + } + } + return HANDSHAKE_TIMEOUT_VALUE; } -//--------------------------------------------------------------------------- -// Function: get_handshake -// -// Parameters: struct ft1000_device - device structure -// u16 expected_value - the handshake value expected -// -// Returns: handshakevalue - success -// HANDSHAKE_TIMEOUT_VALUE - failure -// -// Description: This function gets the handshake and compare with the expected value -// -// Notes: -// -//--------------------------------------------------------------------------- -static u16 get_handshake(struct ft1000_device *ft1000dev, u16 expected_value) +/* write the handshake value to the handshake location */ +static void put_handshake(struct ft1000_usb *ft1000dev, u16 handshake_value) { - u16 handshake; - int loopcnt; - u32 status=0; - struct ft1000_info *pft1000info = netdev_priv(ft1000dev->net); - - loopcnt = 0; - while (loopcnt < 100) - { - - // Need to clear downloader doorbell if Hartley ASIC - status = ft1000_write_register (ft1000dev, FT1000_DB_DNLD_RX, FT1000_REG_DOORBELL); - //DEBUG("FT1000:get_handshake:doorbell = 0x%x\n", temp); - if (pft1000info->fcodeldr) - { - DEBUG(" get_handshake: fcodeldr is %d\n", pft1000info->fcodeldr); - pft1000info->fcodeldr = 0; - status = check_usb_db(ft1000dev); - if (status != STATUS_SUCCESS) - { - DEBUG("get_handshake: check_usb_db failed\n"); - status = STATUS_FAILURE; - break; - } - status = ft1000_write_register (ft1000dev, FT1000_DB_DNLD_RX, FT1000_REG_DOORBELL); - } - - status = ft1000_read_dpram16 (ft1000dev, DWNLD_MAG1_HANDSHAKE_LOC, (u8 *)&handshake, 1); - //DEBUG("get_handshake: handshake is %x\n", tempx); - handshake = ntohs(handshake); - //DEBUG("get_handshake: after swap, handshake is %x\n", handshake); - - if (status) - return HANDSHAKE_TIMEOUT_VALUE; - - //DEBUG("get_handshake: handshake= %x\n", handshake); - if ((handshake == expected_value) || (handshake == HANDSHAKE_RESET_VALUE_USB)) - { - //DEBUG("get_handshake: return handshake %x\n", handshake); - return handshake; - } - else - { - loopcnt++; - msleep (10); - } - //DEBUG("HANDSHKE LOOP: %d\n", loopcnt); - - } - - //DEBUG("get_handshake: return handshake time out\n"); - return HANDSHAKE_TIMEOUT_VALUE; + u32 tempx; + u16 tempword; + int status; + + tempx = (u32)handshake_value; + tempx = ntohl(tempx); + + tempword = (u16)(tempx & 0xffff); + status = ft1000_write_dpram16(ft1000dev, DWNLD_MAG1_HANDSHAKE_LOC, + tempword, 0); + tempword = (u16)(tempx >> 16); + status = ft1000_write_dpram16(ft1000dev, DWNLD_MAG1_HANDSHAKE_LOC, + tempword, 1); + status = ft1000_write_register(ft1000dev, FT1000_DB_DNLD_TX, + FT1000_REG_DOORBELL); } -//--------------------------------------------------------------------------- -// Function: put_handshake -// -// Parameters: struct ft1000_device - device structure -// u16 handshake_value - handshake to be written -// -// Returns: none -// -// Description: This function write the handshake value to the handshake location -// in DPRAM -// -// Notes: -// -//--------------------------------------------------------------------------- -static void put_handshake(struct ft1000_device *ft1000dev,u16 handshake_value) +static u16 get_handshake_usb(struct ft1000_usb *ft1000dev, u16 expected_value) { - u32 tempx; - u16 tempword; - u32 status; - - + u16 handshake; + int loopcnt; + u16 temp; + int status = 0; + + loopcnt = 0; + handshake = 0; + + while (loopcnt < 100) { + if (ft1000dev->usbboot == 2) { + status = ft1000_read_dpram32(ft1000dev, 0, + (u8 *)&(ft1000dev->tempbuf[0]), 64); + for (temp = 0; temp < 16; temp++) { + DEBUG("tempbuf %d = 0x%x\n", temp, + ft1000dev->tempbuf[temp]); + } + status = ft1000_read_dpram16(ft1000dev, + DWNLD_MAG1_HANDSHAKE_LOC, + (u8 *)&handshake, 1); + DEBUG("handshake from read_dpram16 = 0x%x\n", + handshake); + if (ft1000dev->dspalive == ft1000dev->tempbuf[6]) { + handshake = 0; + } else { + handshake = ft1000dev->tempbuf[1]; + ft1000dev->dspalive = + ft1000dev->tempbuf[6]; + } + } else { + status = ft1000_read_dpram16(ft1000dev, + DWNLD_MAG1_HANDSHAKE_LOC, + (u8 *)&handshake, 1); + } - tempx = (u32)handshake_value; - tempx = ntohl(tempx); + loopcnt++; + msleep(10); + handshake = ntohs(handshake); + if ((handshake == expected_value) || + (handshake == HANDSHAKE_RESET_VALUE_USB)) + return handshake; + } - tempword = (u16)(tempx & 0xffff); - status = ft1000_write_dpram16 (ft1000dev, DWNLD_MAG1_HANDSHAKE_LOC, tempword, 0); - tempword = (u16)(tempx >> 16); - status = ft1000_write_dpram16 (ft1000dev, DWNLD_MAG1_HANDSHAKE_LOC, tempword, 1); - status = ft1000_write_register(ft1000dev, FT1000_DB_DNLD_TX, FT1000_REG_DOORBELL); + return HANDSHAKE_TIMEOUT_VALUE; } -static u16 get_handshake_usb(struct ft1000_device *ft1000dev, u16 expected_value) +static void put_handshake_usb(struct ft1000_usb *ft1000dev, u16 handshake_value) { - u16 handshake; - int loopcnt; - u16 temp; - u32 status=0; + int i; - struct ft1000_info *pft1000info = netdev_priv(ft1000dev->net); - loopcnt = 0; - handshake = 0; - while (loopcnt < 100) - { - if (pft1000info->usbboot == 2) { - status = ft1000_read_dpram32 (ft1000dev, 0, (u8 *)&(pft1000info->tempbuf[0]), 64); - for (temp=0; temp<16; temp++) - DEBUG("tempbuf %d = 0x%x\n", temp, pft1000info->tempbuf[temp]); - status = ft1000_read_dpram16 (ft1000dev, DWNLD_MAG1_HANDSHAKE_LOC, (u8 *)&handshake, 1); - DEBUG("handshake from read_dpram16 = 0x%x\n", handshake); - if (pft1000info->dspalive == pft1000info->tempbuf[6]) - handshake = 0; - else { - handshake = pft1000info->tempbuf[1]; - pft1000info->dspalive = pft1000info->tempbuf[6]; - } - } - else { - status = ft1000_read_dpram16 (ft1000dev, DWNLD_MAG1_HANDSHAKE_LOC, (u8 *)&handshake, 1); - } - loopcnt++; - msleep(10); - handshake = ntohs(handshake); - if ((handshake == expected_value) || (handshake == HANDSHAKE_RESET_VALUE_USB)) - { - return handshake; - } - } - - return HANDSHAKE_TIMEOUT_VALUE; + for (i = 0; i < 1000; i++) + ; } -static void put_handshake_usb(struct ft1000_device *ft1000dev,u16 handshake_value) +static u16 get_request_type(struct ft1000_usb *ft1000dev) { - int i; - - for (i=0; i<1000; i++); + u16 request_type; + int status; + u16 tempword; + u32 tempx; + + if (ft1000dev->bootmode == 1) { + status = fix_ft1000_read_dpram32(ft1000dev, + DWNLD_MAG1_TYPE_LOC, (u8 *)&tempx); + tempx = ntohl(tempx); + } else { + tempx = 0; + status = ft1000_read_dpram16(ft1000dev, + DWNLD_MAG1_TYPE_LOC, (u8 *)&tempword, 1); + tempx |= (tempword << 16); + tempx = ntohl(tempx); + } + request_type = (u16)tempx; + + return request_type; } -//--------------------------------------------------------------------------- -// Function: get_request_type -// -// Parameters: struct ft1000_device - device structure -// -// Returns: request type - success -// -// Description: This function returns the request type -// -// Notes: -// -//--------------------------------------------------------------------------- -static u16 get_request_type(struct ft1000_device *ft1000dev) +static u16 get_request_type_usb(struct ft1000_usb *ft1000dev) { - u16 request_type; - u32 status; - u16 tempword; - u32 tempx; - struct ft1000_info *pft1000info = netdev_priv(ft1000dev->net); - - if ( pft1000info->bootmode == 1) - { - status = fix_ft1000_read_dpram32 (ft1000dev, DWNLD_MAG1_TYPE_LOC, (u8 *)&tempx); - tempx = ntohl(tempx); - } - else - { - tempx = 0; - - status = ft1000_read_dpram16 (ft1000dev, DWNLD_MAG1_TYPE_LOC, (u8 *)&tempword, 1); - tempx |= (tempword << 16); - tempx = ntohl(tempx); - } - request_type = (u16)tempx; - - //DEBUG("get_request_type: request_type is %x\n", request_type); - return request_type; + u16 request_type; + int status; + u16 tempword; + u32 tempx; + + if (ft1000dev->bootmode == 1) { + status = fix_ft1000_read_dpram32(ft1000dev, + DWNLD_MAG1_TYPE_LOC, (u8 *)&tempx); + tempx = ntohl(tempx); + } else { + if (ft1000dev->usbboot == 2) { + tempx = ft1000dev->tempbuf[2]; + tempword = ft1000dev->tempbuf[3]; + } else { + tempx = 0; + status = ft1000_read_dpram16(ft1000dev, + DWNLD_MAG1_TYPE_LOC, + (u8 *)&tempword, 1); + } + tempx |= (tempword << 16); + tempx = ntohl(tempx); + } + request_type = (u16)tempx; + return request_type; } -static u16 get_request_type_usb(struct ft1000_device *ft1000dev) +static long get_request_value(struct ft1000_usb *ft1000dev) { - u16 request_type; - u32 status; - u16 tempword; - u32 tempx; - struct ft1000_info *pft1000info = netdev_priv(ft1000dev->net); - if ( pft1000info->bootmode == 1) - { - status = fix_ft1000_read_dpram32 (ft1000dev, DWNLD_MAG1_TYPE_LOC, (u8 *)&tempx); - tempx = ntohl(tempx); - } - else - { - if (pft1000info->usbboot == 2) { - tempx = pft1000info->tempbuf[2]; - tempword = pft1000info->tempbuf[3]; - } - else { - tempx = 0; - status = ft1000_read_dpram16 (ft1000dev, DWNLD_MAG1_TYPE_LOC, (u8 *)&tempword, 1); - } - tempx |= (tempword << 16); - tempx = ntohl(tempx); - } - request_type = (u16)tempx; - - //DEBUG("get_request_type: request_type is %x\n", request_type); - return request_type; - + u32 value; + u16 tempword; + int status; + + if (ft1000dev->bootmode == 1) { + status = fix_ft1000_read_dpram32(ft1000dev, + DWNLD_MAG1_SIZE_LOC, (u8 *)&value); + value = ntohl(value); + } else { + status = ft1000_read_dpram16(ft1000dev, + DWNLD_MAG1_SIZE_LOC, (u8 *)&tempword, 0); + value = tempword; + status = ft1000_read_dpram16(ft1000dev, + DWNLD_MAG1_SIZE_LOC, (u8 *)&tempword, 1); + value |= (tempword << 16); + value = ntohl(value); + } + + return value; } -//--------------------------------------------------------------------------- -// Function: get_request_value -// -// Parameters: struct ft1000_device - device structure -// -// Returns: request value - success -// -// Description: This function returns the request value -// -// Notes: -// -//--------------------------------------------------------------------------- -static long get_request_value(struct ft1000_device *ft1000dev) -{ - u32 value; - u16 tempword; - u32 status; - struct ft1000_info *pft1000info = netdev_priv(ft1000dev->net); - - - if ( pft1000info->bootmode == 1) - { - status = fix_ft1000_read_dpram32(ft1000dev, DWNLD_MAG1_SIZE_LOC, (u8 *)&value); - value = ntohl(value); - } - else - { - status = ft1000_read_dpram16(ft1000dev, DWNLD_MAG1_SIZE_LOC, (u8 *)&tempword, 0); - value = tempword; - status = ft1000_read_dpram16(ft1000dev, DWNLD_MAG1_SIZE_LOC, (u8 *)&tempword, 1); - value |= (tempword << 16); - value = ntohl(value); - } - - //DEBUG("get_request_value: value is %x\n", value); - return value; - -} - -#if 0 -static long get_request_value_usb(struct ft1000_device *ft1000dev) +/* writes a value to DWNLD_MAG1_SIZE_LOC */ +static void put_request_value(struct ft1000_usb *ft1000dev, long lvalue) { - u32 value; - u16 tempword; - u32 status; - struct ft1000_info * pft1000info = netdev_priv(ft1000dev->net); + u32 tempx; + int status; - if (pft1000info->usbboot == 2) { - value = pft1000info->tempbuf[4]; - tempword = pft1000info->tempbuf[5]; - } - else { - value = 0; - status = ft1000_read_dpram16(ft1000dev, DWNLD_MAG1_SIZE_LOC, (u8 *)&tempword, 1); - } - - value |= (tempword << 16); - value = ntohl(value); + tempx = ntohl(lvalue); + status = fix_ft1000_write_dpram32(ft1000dev, DWNLD_MAG1_SIZE_LOC, + (u8 *)&tempx); +} - if (pft1000info->usbboot == 1) - pft1000info->usbboot = 2; - //DEBUG("get_request_value_usb: value is %x\n", value); - return value; -} -#endif - -//--------------------------------------------------------------------------- -// Function: put_request_value -// -// Parameters: struct ft1000_device - device structure -// long lvalue - value to be put into DPRAM location DWNLD_MAG1_SIZE_LOC -// -// Returns: none -// -// Description: This function writes a value to DWNLD_MAG1_SIZE_LOC -// -// Notes: -// -//--------------------------------------------------------------------------- -static void put_request_value(struct ft1000_device *ft1000dev, long lvalue) +/* returns the checksum of the pseudo header */ +static u16 hdr_checksum(struct pseudo_hdr *pHdr) { - u32 tempx; - u32 status; - - tempx = ntohl(lvalue); - status = fix_ft1000_write_dpram32(ft1000dev, DWNLD_MAG1_SIZE_LOC, (u8 *)&tempx); - + u16 *usPtr = (u16 *)pHdr; + u16 chksum; - //DEBUG("put_request_value: value is %x\n", lvalue); + chksum = ((((((usPtr[0] ^ usPtr[1]) ^ usPtr[2]) ^ usPtr[3]) ^ + usPtr[4]) ^ usPtr[5]) ^ usPtr[6]); + return chksum; } - - -//--------------------------------------------------------------------------- -// Function: hdr_checksum -// -// Parameters: struct pseudo_hdr *pHdr - Pseudo header pointer -// -// Returns: checksum - success -// -// Description: This function returns the checksum of the pseudo header -// -// Notes: -// -//--------------------------------------------------------------------------- -static u16 hdr_checksum(struct pseudo_hdr *pHdr) +static int check_buffers(u16 *buff_w, u16 *buff_r, int len, int offset) { - u16 *usPtr = (u16 *)pHdr; - u16 chksum; + int i; + for (i = 0; i < len; i++) { + if (buff_w[i] != buff_r[i + offset]) + return -EREMOTEIO; + } - chksum = ((((((usPtr[0] ^ usPtr[1]) ^ usPtr[2]) ^ usPtr[3]) ^ - usPtr[4]) ^ usPtr[5]) ^ usPtr[6]); - - return chksum; + return 0; } - -//--------------------------------------------------------------------------- -// Function: write_blk -// -// Parameters: struct ft1000_device - device structure -// u16 **pUsFile - DSP image file pointer in u16 -// u8 **pUcFile - DSP image file pointer in u8 -// long word_length - lenght of the buffer to be written -// to DPRAM -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function writes a block of DSP image to DPRAM -// -// Notes: -// -//--------------------------------------------------------------------------- -static u32 write_blk (struct ft1000_device *ft1000dev, u16 **pUsFile, u8 **pUcFile, long word_length) +static int write_dpram32_and_check(struct ft1000_usb *ft1000dev, + u16 tempbuffer[], u16 dpram) { - u32 Status = STATUS_SUCCESS; - u16 dpram; - long temp_word_length; - int loopcnt, i, j; - u16 *pTempFile; - u16 tempword; - u16 tempbuffer[64]; - u16 resultbuffer[64]; - struct ft1000_info *pft1000info = netdev_priv(ft1000dev->net); - - //DEBUG("FT1000:download:start word_length = %d\n",(int)word_length); - dpram = (u16)DWNLD_MAG1_PS_HDR_LOC; - tempword = *(*pUsFile); - (*pUsFile)++; - Status = ft1000_write_dpram16(ft1000dev, dpram, tempword, 0); - tempword = *(*pUsFile); - (*pUsFile)++; - Status = ft1000_write_dpram16(ft1000dev, dpram++, tempword, 1); - - *pUcFile = *pUcFile + 4; - word_length--; - tempword = (u16)word_length; - word_length = (word_length / 16) + 1; - pTempFile = *pUsFile; - temp_word_length = word_length; - for (; word_length > 0; word_length--) /* In words */ - { - loopcnt = 0; - - for (i=0; i<32; i++) - { - if (tempword != 0) - { - tempbuffer[i++] = *(*pUsFile); - (*pUsFile)++; - tempbuffer[i] = *(*pUsFile); - (*pUsFile)++; - *pUcFile = *pUcFile + 4; - loopcnt++; - tempword--; - } - else - { - tempbuffer[i++] = 0; - tempbuffer[i] = 0; - } - } - - //DEBUG("write_blk: loopcnt is %d\n", loopcnt); - //DEBUG("write_blk: bootmode = %d\n", bootmode); - //DEBUG("write_blk: dpram = %x\n", dpram); - if (pft1000info->bootmode == 0) - { - if (dpram >= 0x3F4) - Status = ft1000_write_dpram32 (ft1000dev, dpram, (u8 *)&tempbuffer[0], 8); - else - Status = ft1000_write_dpram32 (ft1000dev, dpram, (u8 *)&tempbuffer[0], 64); - } - else - { - for (j=0; j<10; j++) - { - Status = ft1000_write_dpram32 (ft1000dev, dpram, (u8 *)&tempbuffer[0], 64); - if (Status == STATUS_SUCCESS) - { - // Work around for ASIC bit stuffing problem. - if ( (tempbuffer[31] & 0xfe00) == 0xfe00) - { - Status = ft1000_write_dpram32(ft1000dev, dpram+12, (u8 *)&tempbuffer[24], 64); - } - // Let's check the data written - Status = ft1000_read_dpram32 (ft1000dev, dpram, (u8 *)&resultbuffer[0], 64); - if ( (tempbuffer[31] & 0xfe00) == 0xfe00) - { - for (i=0; i<28; i++) - { - if (resultbuffer[i] != tempbuffer[i]) - { - //NdisMSleep (100); - DEBUG("FT1000:download:DPRAM write failed 1 during bootloading\n"); - msleep(10); - Status = STATUS_FAILURE; - break; + int status; + u16 resultbuffer[64]; + int i; + + for (i = 0; i < 10; i++) { + status = ft1000_write_dpram32(ft1000dev, dpram, + (u8 *)&tempbuffer[0], 64); + if (status == 0) { + /* Work around for ASIC bit stuffing problem. */ + if ((tempbuffer[31] & 0xfe00) == 0xfe00) { + status = ft1000_write_dpram32(ft1000dev, + dpram+12, (u8 *)&tempbuffer[24], + 64); + } + /* Let's check the data written */ + status = ft1000_read_dpram32(ft1000dev, dpram, + (u8 *)&resultbuffer[0], 64); + if ((tempbuffer[31] & 0xfe00) == 0xfe00) { + if (check_buffers(tempbuffer, resultbuffer, 28, + 0)) { + DEBUG("FT1000:download:DPRAM write failed 1 during bootloading\n"); + usleep_range(9000, 11000); + break; } - } - Status = ft1000_read_dpram32 (ft1000dev, dpram+12, (u8 *)&resultbuffer[0], 64); - for (i=0; i<16; i++) - { - if (resultbuffer[i] != tempbuffer[i+24]) - { - //NdisMSleep (100); - DEBUG("FT1000:download:DPRAM write failed 2 during bootloading\n"); - msleep(10); - Status = STATUS_FAILURE; - break; + status = ft1000_read_dpram32(ft1000dev, + dpram+12, + (u8 *)&resultbuffer[0], 64); + + if (check_buffers(tempbuffer, resultbuffer, 16, + 24)) { + DEBUG("FT1000:download:DPRAM write failed 2 during bootloading\n"); + usleep_range(9000, 11000); + break; } - } - } - else - { - for (i=0; i<32; i++) - { - if (resultbuffer[i] != tempbuffer[i]) - { - //NdisMSleep (100); - DEBUG("FT1000:download:DPRAM write failed 3 during bootloading\n"); - msleep(10); - Status = STATUS_FAILURE; - break; + } else { + if (check_buffers(tempbuffer, resultbuffer, 32, + 0)) { + DEBUG("FT1000:download:DPRAM write failed 3 during bootloading\n"); + usleep_range(9000, 11000); + break; } - } } + if (status == 0) + break; + } + } + return status; +} - if (Status == STATUS_SUCCESS) - break; - - } +/* writes a block of DSP image to DPRAM + * Parameters: struct ft1000_usb - device structure + * u16 **pUsFile - DSP image file pointer in u16 + * u8 **pUcFile - DSP image file pointer in u8 + * long word_length - length of the buffer to be written to DPRAM + */ +static int write_blk(struct ft1000_usb *ft1000dev, u16 **pUsFile, u8 **pUcFile, + long word_length) +{ + int status = 0; + u16 dpram; + int loopcnt, i; + u16 tempword; + u16 tempbuffer[64]; + + /*DEBUG("FT1000:download:start word_length = %d\n",(int)word_length); */ + dpram = (u16)DWNLD_MAG1_PS_HDR_LOC; + tempword = *(*pUsFile); + (*pUsFile)++; + status = ft1000_write_dpram16(ft1000dev, dpram, tempword, 0); + tempword = *(*pUsFile); + (*pUsFile)++; + status = ft1000_write_dpram16(ft1000dev, dpram++, tempword, 1); + + *pUcFile = *pUcFile + 4; + word_length--; + tempword = (u16)word_length; + word_length = (word_length / 16) + 1; + for (; word_length > 0; word_length--) { /* In words */ + loopcnt = 0; + for (i = 0; i < 32; i++) { + if (tempword != 0) { + tempbuffer[i++] = *(*pUsFile); + (*pUsFile)++; + tempbuffer[i] = *(*pUsFile); + (*pUsFile)++; + *pUcFile = *pUcFile + 4; + loopcnt++; + tempword--; + } else { + tempbuffer[i++] = 0; + tempbuffer[i] = 0; + } } - if (Status != STATUS_SUCCESS) - { - DEBUG("FT1000:download:Write failed tempbuffer[31] = 0x%x\n", tempbuffer[31]); - break; + /*DEBUG("write_blk: loopcnt is %d\n", loopcnt); */ + /*DEBUG("write_blk: bootmode = %d\n", bootmode); */ + /*DEBUG("write_blk: dpram = %x\n", dpram); */ + if (ft1000dev->bootmode == 0) { + if (dpram >= 0x3F4) + status = ft1000_write_dpram32(ft1000dev, dpram, + (u8 *)&tempbuffer[0], 8); + else + status = ft1000_write_dpram32(ft1000dev, dpram, + (u8 *)&tempbuffer[0], 64); + } else { + status = write_dpram32_and_check(ft1000dev, tempbuffer, + dpram); + if (status != 0) { + DEBUG("FT1000:download:Write failed tempbuffer[31] = 0x%x\n", tempbuffer[31]); + break; + } } + dpram = dpram + loopcnt; + } + return status; +} + +static void usb_dnld_complete(struct urb *urb) +{ + /* DEBUG("****** usb_dnld_complete\n"); */ +} + +/* writes a block of DSP image to DPRAM + * Parameters: struct ft1000_usb - device structure + * u16 **pUsFile - DSP image file pointer in u16 + * u8 **pUcFile - DSP image file pointer in u8 + * long word_length - length of the buffer to be written to DPRAM + */ +static int write_blk_fifo(struct ft1000_usb *ft1000dev, u16 **pUsFile, + u8 **pUcFile, long word_length) +{ + int byte_length; + + byte_length = word_length * 4; + + if (byte_length && ((byte_length % 64) == 0)) + byte_length += 4; + + if (byte_length < 64) + byte_length = 68; + + usb_init_urb(ft1000dev->tx_urb); + memcpy(ft1000dev->tx_buf, *pUcFile, byte_length); + usb_fill_bulk_urb(ft1000dev->tx_urb, + ft1000dev->dev, + usb_sndbulkpipe(ft1000dev->dev, + ft1000dev->bulk_out_endpointAddr), + ft1000dev->tx_buf, byte_length, usb_dnld_complete, + (void *)ft1000dev); - } - dpram = dpram + loopcnt; - } + usb_submit_urb(ft1000dev->tx_urb, GFP_ATOMIC); - return Status; + *pUsFile = *pUsFile + (word_length << 1); + *pUcFile = *pUcFile + (word_length << 2); + + return 0; } -static void usb_dnld_complete (struct urb *urb) +static int scram_start_dwnld(struct ft1000_usb *ft1000dev, u16 *hshake, + u32 *state) { - //DEBUG("****** usb_dnld_complete\n"); + int status = 0; + + DEBUG("FT1000:STATE_START_DWNLD\n"); + if (ft1000dev->usbboot) + *hshake = get_handshake_usb(ft1000dev, HANDSHAKE_DSP_BL_READY); + else + *hshake = get_handshake(ft1000dev, HANDSHAKE_DSP_BL_READY); + if (*hshake == HANDSHAKE_DSP_BL_READY) { + DEBUG("scram_dnldr: handshake is HANDSHAKE_DSP_BL_READY, call put_handshake(HANDSHAKE_DRIVER_READY)\n"); + put_handshake(ft1000dev, HANDSHAKE_DRIVER_READY); + } else if (*hshake == HANDSHAKE_TIMEOUT_VALUE) { + status = -ETIMEDOUT; + } else { + DEBUG("FT1000:download:Download error: Handshake failed\n"); + status = -ENETRESET; + } + *state = STATE_BOOT_DWNLD; + return status; } -//--------------------------------------------------------------------------- -// Function: write_blk_fifo -// -// Parameters: struct ft1000_device - device structure -// u16 **pUsFile - DSP image file pointer in u16 -// u8 **pUcFile - DSP image file pointer in u8 -// long word_length - lenght of the buffer to be written -// to DPRAM -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function writes a block of DSP image to DPRAM -// -// Notes: -// -//--------------------------------------------------------------------------- -static u32 write_blk_fifo (struct ft1000_device *ft1000dev, u16 **pUsFile, u8 **pUcFile, long word_length) +static int request_code_segment(struct ft1000_usb *ft1000dev, u16 **s_file, + u8 **c_file, const u8 *endpoint, bool boot_case) { - u32 Status = STATUS_SUCCESS; - int byte_length; - long aligncnt; - - byte_length = word_length * 4; - - if (byte_length % 4) - aligncnt = 4 - (byte_length % 4); - else - aligncnt = 0; - byte_length += aligncnt; - - if (byte_length && ((byte_length % 64) == 0)) { - byte_length += 4; - } - - if (byte_length < 64) - byte_length = 68; - -#if 0 - pblk = kzalloc(byte_length, GFP_KERNEL); - memcpy (pblk, *pUcFile, byte_length); - - pipe = usb_sndbulkpipe (ft1000dev->dev, ft1000dev->bulk_out_endpointAddr); - - Status = usb_bulk_msg (ft1000dev->dev, - pipe, - pblk, - byte_length, - &cnt, - 10); - DEBUG("write_blk_fifo Status = 0x%8x Bytes Transfer = %d Data = 0x%x\n", Status, cnt, *pblk); - - kfree(pblk); -#else - usb_init_urb(ft1000dev->tx_urb); - memcpy (ft1000dev->tx_buf, *pUcFile, byte_length); - usb_fill_bulk_urb(ft1000dev->tx_urb, - ft1000dev->dev, - usb_sndbulkpipe(ft1000dev->dev, ft1000dev->bulk_out_endpointAddr), - ft1000dev->tx_buf, - byte_length, - usb_dnld_complete, - (void*)ft1000dev); - - usb_submit_urb(ft1000dev->tx_urb, GFP_ATOMIC); -#endif - - *pUsFile = *pUsFile + (word_length << 1); - *pUcFile = *pUcFile + (word_length << 2); - - return Status; + long word_length; + int status = 0; + + /*DEBUG("FT1000:REQUEST_CODE_SEGMENT\n");i*/ + word_length = get_request_value(ft1000dev); + /*DEBUG("FT1000:word_length = 0x%x\n", (int)word_length); */ + /*NdisMSleep (100); */ + if (word_length > MAX_LENGTH) { + DEBUG("FT1000:download:Download error: Max length exceeded\n"); + return -1; + } + if ((word_length * 2 + (long)c_file) > (long)endpoint) { + /* Error, beyond boot code range.*/ + DEBUG("FT1000:download:Download error: Requested len=%d exceeds BOOT code boundary.\n", (int)word_length); + return -1; + } + if (word_length & 0x1) + word_length++; + word_length = word_length / 2; + + if (boot_case) { + status = write_blk(ft1000dev, s_file, c_file, word_length); + /*DEBUG("write_blk returned %d\n", status); */ + } else { + status = write_blk_fifo(ft1000dev, s_file, c_file, word_length); + if (ft1000dev->usbboot == 0) + ft1000dev->usbboot++; + if (ft1000dev->usbboot == 1) + status |= ft1000_write_dpram16(ft1000dev, + DWNLD_MAG1_PS_HDR_LOC, 0, 0); + } + return status; } -//--------------------------------------------------------------------------- -// -// Function: scram_dnldr -// -// Synopsis: Scramble downloader for Harley based ASIC via USB interface -// -// Arguments: pFileStart - pointer to start of file -// FileLength - file length -// -// Returns: status - return code -//--------------------------------------------------------------------------- - -u16 scram_dnldr(struct ft1000_device *ft1000dev, void *pFileStart, u32 FileLength) +/* Scramble downloader for Harley based ASIC via USB interface */ +int scram_dnldr(struct ft1000_usb *ft1000dev, void *pFileStart, + u32 FileLength) { - u16 status = STATUS_SUCCESS; - u32 state; - u16 handshake; + int status = 0; + u32 state; + u16 handshake; struct pseudo_hdr *pseudo_header; - u16 pseudo_header_len; - long word_length; - u16 request; - u16 temp; - u16 tempword; + u16 pseudo_header_len; + long word_length; + u16 request; + u16 temp; struct dsp_file_hdr *file_hdr; struct dsp_image_info *dsp_img_info = NULL; - long requested_version; - bool correct_version; + long requested_version; + bool correct_version; struct drv_msg *mailbox_data; - u16 *data = NULL; - u16 *s_file = NULL; - u8 *c_file = NULL; - u8 *boot_end = NULL, *code_end= NULL; - int image; - long loader_code_address, loader_code_size = 0; - long run_address = 0, run_size = 0; - - u32 templong; - u32 image_chksum = 0; - - u16 dpram = 0; - u8 *pbuffer; + u16 *data = NULL; + u16 *s_file = NULL; + u8 *c_file = NULL; + u8 *boot_end = NULL, *code_end = NULL; + int image; + long loader_code_address, loader_code_size = 0; + long run_address = 0, run_size = 0; + + u32 templong; + u32 image_chksum = 0; + + u16 dpram = 0; + u8 *pbuffer; struct prov_record *pprov_record; struct ft1000_info *pft1000info = netdev_priv(ft1000dev->net); - DEBUG("Entered scram_dnldr...\n"); - - pft1000info->fcodeldr = 0; - pft1000info->usbboot = 0; - pft1000info->dspalive = 0xffff; - - - // - // Get version id of file, at first 4 bytes of file, for newer files. - // - - state = STATE_START_DWNLD; - - file_hdr = (struct dsp_file_hdr *)pFileStart; - - ft1000_write_register (ft1000dev, 0x800, FT1000_REG_MAG_WATERMARK); - - s_file = (u16 *)(pFileStart + file_hdr->loader_offset); - c_file = (u8 *)(pFileStart + file_hdr->loader_offset); - - boot_end = (u8 *)(pFileStart + file_hdr->loader_code_end); - - loader_code_address = file_hdr->loader_code_address; - loader_code_size = file_hdr->loader_code_size; - correct_version = FALSE; - - while ((status == STATUS_SUCCESS) && (state != STATE_DONE_FILE)) - { - switch (state) - { - case STATE_START_DWNLD: - DEBUG("FT1000:STATE_START_DWNLD\n"); - if (pft1000info->usbboot) - handshake = get_handshake_usb(ft1000dev, HANDSHAKE_DSP_BL_READY); - else - handshake = get_handshake(ft1000dev, HANDSHAKE_DSP_BL_READY); - - if (handshake == HANDSHAKE_DSP_BL_READY) - { - DEBUG("scram_dnldr: handshake is HANDSHAKE_DSP_BL_READY, call put_handshake(HANDSHAKE_DRIVER_READY)\n"); - put_handshake(ft1000dev, HANDSHAKE_DRIVER_READY); - } - else - { - DEBUG("FT1000:download:Download error: Handshake failed\n"); - status = STATUS_FAILURE; - } - - state = STATE_BOOT_DWNLD; - - break; - - case STATE_BOOT_DWNLD: - DEBUG("FT1000:STATE_BOOT_DWNLD\n"); - pft1000info->bootmode = 1; - handshake = get_handshake(ft1000dev, HANDSHAKE_REQUEST); - if (handshake == HANDSHAKE_REQUEST) - { - /* - * Get type associated with the request. - */ - request = get_request_type(ft1000dev); - switch (request) - { - case REQUEST_RUN_ADDRESS: - DEBUG("FT1000:REQUEST_RUN_ADDRESS\n"); - put_request_value(ft1000dev, loader_code_address); - break; - case REQUEST_CODE_LENGTH: - DEBUG("FT1000:REQUEST_CODE_LENGTH\n"); - put_request_value(ft1000dev, loader_code_size); - break; - case REQUEST_DONE_BL: - DEBUG("FT1000:REQUEST_DONE_BL\n"); - /* Reposition ptrs to beginning of code section */ - s_file = (u16 *)(boot_end); - c_file = (u8 *)(boot_end); - //DEBUG("FT1000:download:s_file = 0x%8x\n", (int)s_file); - //DEBUG("FT1000:download:c_file = 0x%8x\n", (int)c_file); - state = STATE_CODE_DWNLD; - pft1000info->fcodeldr = 1; - break; - case REQUEST_CODE_SEGMENT: - //DEBUG("FT1000:REQUEST_CODE_SEGMENT\n"); - word_length = get_request_value(ft1000dev); - //DEBUG("FT1000:word_length = 0x%x\n", (int)word_length); - //NdisMSleep (100); - if (word_length > MAX_LENGTH) - { - DEBUG("FT1000:download:Download error: Max length exceeded\n"); - status = STATUS_FAILURE; - break; - } - if ( (word_length*2 + c_file) > boot_end) - { - /* - * Error, beyond boot code range. - */ - DEBUG("FT1000:download:Download error: Requested len=%d exceeds BOOT code boundry.\n", - (int)word_length); - status = STATUS_FAILURE; - break; - } - /* - * Position ASIC DPRAM auto-increment pointer. - */ - dpram = (u16)DWNLD_MAG1_PS_HDR_LOC; + DEBUG("Entered scram_dnldr...\n"); + + ft1000dev->fcodeldr = 0; + ft1000dev->usbboot = 0; + ft1000dev->dspalive = 0xffff; + + /* + * Get version id of file, at first 4 bytes of file, for newer files. + */ + + state = STATE_START_DWNLD; + + file_hdr = (struct dsp_file_hdr *)pFileStart; + + ft1000_write_register(ft1000dev, 0x800, FT1000_REG_MAG_WATERMARK); + + s_file = (u16 *) (pFileStart + file_hdr->loader_offset); + c_file = (u8 *) (pFileStart + file_hdr->loader_offset); + + boot_end = (u8 *) (pFileStart + file_hdr->loader_code_end); + + loader_code_address = file_hdr->loader_code_address; + loader_code_size = file_hdr->loader_code_size; + correct_version = false; + + while ((status == 0) && (state != STATE_DONE_FILE)) { + switch (state) { + case STATE_START_DWNLD: + status = scram_start_dwnld(ft1000dev, &handshake, + &state); + break; + + case STATE_BOOT_DWNLD: + DEBUG("FT1000:STATE_BOOT_DWNLD\n"); + ft1000dev->bootmode = 1; + handshake = get_handshake(ft1000dev, HANDSHAKE_REQUEST); + if (handshake == HANDSHAKE_REQUEST) { + /* + * Get type associated with the request. + */ + request = get_request_type(ft1000dev); + switch (request) { + case REQUEST_RUN_ADDRESS: + DEBUG("FT1000:REQUEST_RUN_ADDRESS\n"); + put_request_value(ft1000dev, + loader_code_address); + break; + case REQUEST_CODE_LENGTH: + DEBUG("FT1000:REQUEST_CODE_LENGTH\n"); + put_request_value(ft1000dev, + loader_code_size); + break; + case REQUEST_DONE_BL: + DEBUG("FT1000:REQUEST_DONE_BL\n"); + /* Reposition ptrs to beginning of code section */ + s_file = (u16 *) (boot_end); + c_file = (u8 *) (boot_end); + /* DEBUG("FT1000:download:s_file = 0x%8x\n", (int)s_file); */ + /* DEBUG("FT1000:download:c_file = 0x%8x\n", (int)c_file); */ + state = STATE_CODE_DWNLD; + ft1000dev->fcodeldr = 1; + break; + case REQUEST_CODE_SEGMENT: + status = request_code_segment(ft1000dev, + &s_file, &c_file, + (const u8 *)boot_end, + true); + break; + default: + DEBUG + ("FT1000:download:Download error: Bad request type=%d in BOOT download state.\n", + request); + status = -1; + break; + } + if (ft1000dev->usbboot) + put_handshake_usb(ft1000dev, + HANDSHAKE_RESPONSE); + else + put_handshake(ft1000dev, + HANDSHAKE_RESPONSE); + } else { + DEBUG + ("FT1000:download:Download error: Handshake failed\n"); + status = -1; + } + + break; + + case STATE_CODE_DWNLD: + /* DEBUG("FT1000:STATE_CODE_DWNLD\n"); */ + ft1000dev->bootmode = 0; + if (ft1000dev->usbboot) + handshake = + get_handshake_usb(ft1000dev, + HANDSHAKE_REQUEST); + else + handshake = + get_handshake(ft1000dev, HANDSHAKE_REQUEST); + if (handshake == HANDSHAKE_REQUEST) { + /* + * Get type associated with the request. + */ + if (ft1000dev->usbboot) + request = + get_request_type_usb(ft1000dev); + else + request = get_request_type(ft1000dev); + switch (request) { + case REQUEST_FILE_CHECKSUM: + DEBUG + ("FT1000:download:image_chksum = 0x%8x\n", + image_chksum); + put_request_value(ft1000dev, + image_chksum); + break; + case REQUEST_RUN_ADDRESS: + DEBUG + ("FT1000:download: REQUEST_RUN_ADDRESS\n"); + if (correct_version) { + DEBUG + ("FT1000:download:run_address = 0x%8x\n", + (int)run_address); + put_request_value(ft1000dev, + run_address); + } else { + DEBUG + ("FT1000:download:Download error: Got Run address request before image offset request.\n"); + status = -1; + break; + } + break; + case REQUEST_CODE_LENGTH: + DEBUG + ("FT1000:download:REQUEST_CODE_LENGTH\n"); + if (correct_version) { + DEBUG + ("FT1000:download:run_size = 0x%8x\n", + (int)run_size); + put_request_value(ft1000dev, + run_size); + } else { + DEBUG + ("FT1000:download:Download error: Got Size request before image offset request.\n"); + status = -1; + break; + } + break; + case REQUEST_DONE_CL: + ft1000dev->usbboot = 3; + /* Reposition ptrs to beginning of provisioning section */ + s_file = + (u16 *) (pFileStart + + file_hdr->commands_offset); + c_file = + (u8 *) (pFileStart + + file_hdr->commands_offset); + state = STATE_DONE_DWNLD; + break; + case REQUEST_CODE_SEGMENT: + /* DEBUG("FT1000:download: REQUEST_CODE_SEGMENT - CODELOADER\n"); */ + if (!correct_version) { + DEBUG + ("FT1000:download:Download error: Got Code Segment request before image offset request.\n"); + status = -1; + break; + } + + status = request_code_segment(ft1000dev, + &s_file, &c_file, + (const u8 *)code_end, + false); + + break; + + case REQUEST_MAILBOX_DATA: + DEBUG + ("FT1000:download: REQUEST_MAILBOX_DATA\n"); + /* Convert length from byte count to word count. Make sure we round up. */ + word_length = + (long)(pft1000info->DSPInfoBlklen + + 1) / 2; + put_request_value(ft1000dev, + word_length); + mailbox_data = + (struct drv_msg *)&(pft1000info-> + DSPInfoBlk[0]); + /* + * Position ASIC DPRAM auto-increment pointer. + */ + + data = (u16 *) &mailbox_data->data[0]; + dpram = (u16) DWNLD_MAG1_PS_HDR_LOC; + if (word_length & 0x1) + word_length++; + + word_length = (word_length / 2); + + for (; word_length > 0; word_length--) { /* In words */ + + templong = *data++; + templong |= (*data++ << 16); + status = + fix_ft1000_write_dpram32 + (ft1000dev, dpram++, + (u8 *) &templong); + + } + break; + + case REQUEST_VERSION_INFO: + DEBUG + ("FT1000:download:REQUEST_VERSION_INFO\n"); + word_length = + file_hdr->version_data_size; + put_request_value(ft1000dev, + word_length); + /* + * Position ASIC DPRAM auto-increment pointer. + */ + + s_file = + (u16 *) (pFileStart + + file_hdr-> + version_data_offset); + + dpram = (u16) DWNLD_MAG1_PS_HDR_LOC; if (word_length & 0x1) word_length++; - word_length = word_length / 2; - - status = write_blk(ft1000dev, &s_file, &c_file, word_length); - //DEBUG("write_blk returned %d\n", status); - break; - default: - DEBUG("FT1000:download:Download error: Bad request type=%d in BOOT download state.\n",request); - status = STATUS_FAILURE; - break; - } - if (pft1000info->usbboot) - put_handshake_usb(ft1000dev, HANDSHAKE_RESPONSE); - else - put_handshake(ft1000dev, HANDSHAKE_RESPONSE); - } - else - { - DEBUG("FT1000:download:Download error: Handshake failed\n"); - status = STATUS_FAILURE; - } - - break; - - case STATE_CODE_DWNLD: - //DEBUG("FT1000:STATE_CODE_DWNLD\n"); - pft1000info->bootmode = 0; - if (pft1000info->usbboot) - handshake = get_handshake_usb(ft1000dev, HANDSHAKE_REQUEST); - else - handshake = get_handshake(ft1000dev, HANDSHAKE_REQUEST); - if (handshake == HANDSHAKE_REQUEST) - { - /* - * Get type associated with the request. - */ - if (pft1000info->usbboot) - request = get_request_type_usb(ft1000dev); - else - request = get_request_type(ft1000dev); - switch (request) - { - case REQUEST_FILE_CHECKSUM: - DEBUG("FT1000:download:image_chksum = 0x%8x\n", image_chksum); - put_request_value(ft1000dev, image_chksum); - break; - case REQUEST_RUN_ADDRESS: - DEBUG("FT1000:download: REQUEST_RUN_ADDRESS\n"); - if (correct_version) - { - DEBUG("FT1000:download:run_address = 0x%8x\n", (int)run_address); - put_request_value(ft1000dev, run_address); - } - else - { - DEBUG("FT1000:download:Download error: Got Run address request before image offset request.\n"); - status = STATUS_FAILURE; - break; - } - break; - case REQUEST_CODE_LENGTH: - DEBUG("FT1000:download:REQUEST_CODE_LENGTH\n"); - if (correct_version) - { - DEBUG("FT1000:download:run_size = 0x%8x\n", (int)run_size); - put_request_value(ft1000dev, run_size); - } - else - { - DEBUG("FT1000:download:Download error: Got Size request before image offset request.\n"); - status = STATUS_FAILURE; - break; - } - break; - case REQUEST_DONE_CL: - pft1000info->usbboot = 3; - /* Reposition ptrs to beginning of provisioning section */ - s_file = (u16 *)(pFileStart + file_hdr->commands_offset); - c_file = (u8 *)(pFileStart + file_hdr->commands_offset); - state = STATE_DONE_DWNLD; - break; - case REQUEST_CODE_SEGMENT: - //DEBUG("FT1000:download: REQUEST_CODE_SEGMENT - CODELOADER\n"); - if (!correct_version) - { - DEBUG("FT1000:download:Download error: Got Code Segment request before image offset request.\n"); - status = STATUS_FAILURE; - break; - } -#if 0 - word_length = get_request_value_usb(ft1000dev); - //DEBUG("FT1000:download:word_length = %d\n", (int)word_length); - if (word_length > MAX_LENGTH/2) -#else - word_length = get_request_value(ft1000dev); - //DEBUG("FT1000:download:word_length = %d\n", (int)word_length); - if (word_length > MAX_LENGTH) -#endif - { - DEBUG("FT1000:download:Download error: Max length exceeded\n"); - status = STATUS_FAILURE; - break; - } - if ( (word_length*2 + c_file) > code_end) - { - /* - * Error, beyond boot code range. - */ - DEBUG("FT1000:download:Download error: Requested len=%d exceeds DSP code boundry.\n", - (int)word_length); - status = STATUS_FAILURE; - break; - } - /* - * Position ASIC DPRAM auto-increment pointer. - */ - dpram = (u16)DWNLD_MAG1_PS_HDR_LOC; - if (word_length & 0x1) - word_length++; - word_length = word_length / 2; - - write_blk_fifo (ft1000dev, &s_file, &c_file, word_length); - if (pft1000info->usbboot == 0) - pft1000info->usbboot++; - if (pft1000info->usbboot == 1) { - tempword = 0; - ft1000_write_dpram16 (ft1000dev, DWNLD_MAG1_PS_HDR_LOC, tempword, 0); - } - - break; - - case REQUEST_MAILBOX_DATA: - DEBUG("FT1000:download: REQUEST_MAILBOX_DATA\n"); - // Convert length from byte count to word count. Make sure we round up. - word_length = (long)(pft1000info->DSPInfoBlklen + 1)/2; - put_request_value(ft1000dev, word_length); - mailbox_data = (struct drv_msg *)&(pft1000info->DSPInfoBlk[0]); - /* - * Position ASIC DPRAM auto-increment pointer. - */ - - - data = (u16 *)&mailbox_data->data[0]; - dpram = (u16)DWNLD_MAG1_PS_HDR_LOC; - if (word_length & 0x1) - word_length++; - - word_length = (word_length / 2); - - - for (; word_length > 0; word_length--) /* In words */ - { - - templong = *data++; - templong |= (*data++ << 16); - status = fix_ft1000_write_dpram32 (ft1000dev, dpram++, (u8 *)&templong); - - } - break; - - case REQUEST_VERSION_INFO: - DEBUG("FT1000:download:REQUEST_VERSION_INFO\n"); - word_length = file_hdr->version_data_size; - put_request_value(ft1000dev, word_length); - /* - * Position ASIC DPRAM auto-increment pointer. - */ - - s_file = (u16 *)(pFileStart + file_hdr->version_data_offset); - - - dpram = (u16)DWNLD_MAG1_PS_HDR_LOC; - if (word_length & 0x1) - word_length++; - - word_length = (word_length / 2); - - - for (; word_length > 0; word_length--) /* In words */ - { - - templong = ntohs(*s_file++); - temp = ntohs(*s_file++); - templong |= (temp << 16); - status = fix_ft1000_write_dpram32 (ft1000dev, dpram++, (u8 *)&templong); - - } - break; - - case REQUEST_CODE_BY_VERSION: - DEBUG("FT1000:download:REQUEST_CODE_BY_VERSION\n"); - correct_version = FALSE; - requested_version = get_request_value(ft1000dev); - - dsp_img_info = (struct dsp_image_info *)(pFileStart + sizeof(struct dsp_file_hdr )); - - for (image = 0; image < file_hdr->nDspImages; image++) - { - - temp = (u16)(dsp_img_info->version); - templong = temp; - temp = (u16)(dsp_img_info->version >> 16); - templong |= (temp << 16); - if (templong == (u32)requested_version) - { - correct_version = TRUE; - DEBUG("FT1000:download: correct_version is TRUE\n"); - s_file = (u16 *)(pFileStart + dsp_img_info->begin_offset); - c_file = (u8 *)(pFileStart + dsp_img_info->begin_offset); - code_end = (u8 *)(pFileStart + dsp_img_info->end_offset); - run_address = dsp_img_info->run_address; - run_size = dsp_img_info->image_size; - image_chksum = (u32)dsp_img_info->checksum; - break; - } - dsp_img_info++; - - - } //end of for - - if (!correct_version) - { - /* - * Error, beyond boot code range. - */ - DEBUG("FT1000:download:Download error: Bad Version Request = 0x%x.\n",(int)requested_version); - status = STATUS_FAILURE; - break; - } - break; - - default: - DEBUG("FT1000:download:Download error: Bad request type=%d in CODE download state.\n",request); - status = STATUS_FAILURE; - break; - } - if (pft1000info->usbboot) - put_handshake_usb(ft1000dev, HANDSHAKE_RESPONSE); - else - put_handshake(ft1000dev, HANDSHAKE_RESPONSE); - } - else - { - DEBUG("FT1000:download:Download error: Handshake failed\n"); - status = STATUS_FAILURE; - } - - break; - - case STATE_DONE_DWNLD: - DEBUG("FT1000:download:Code loader is done...\n"); - state = STATE_SECTION_PROV; - break; - - case STATE_SECTION_PROV: - DEBUG("FT1000:download:STATE_SECTION_PROV\n"); - pseudo_header = (struct pseudo_hdr *)c_file; - - if (pseudo_header->checksum == hdr_checksum(pseudo_header)) - { - if (pseudo_header->portdest != 0x80 /* Dsp OAM */) - { - state = STATE_DONE_PROV; - break; - } - pseudo_header_len = ntohs(pseudo_header->length); /* Byte length for PROV records */ - - // Get buffer for provisioning data - pbuffer = kmalloc((pseudo_header_len + sizeof(struct pseudo_hdr)), GFP_ATOMIC); - if (pbuffer) { - memcpy(pbuffer, (void *)c_file, (u32)(pseudo_header_len + sizeof(struct pseudo_hdr))); - // link provisioning data - pprov_record = kmalloc(sizeof(struct prov_record), GFP_ATOMIC); - if (pprov_record) { - pprov_record->pprov_data = pbuffer; - list_add_tail (&pprov_record->list, &pft1000info->prov_list); - // Move to next entry if available - c_file = (u8 *)((unsigned long)c_file + (u32)((pseudo_header_len + 1) & 0xFFFFFFFE) + sizeof(struct pseudo_hdr)); - if ( (unsigned long)(c_file) - (unsigned long)(pFileStart) >= (unsigned long)FileLength) { - state = STATE_DONE_FILE; - } - } - else { - kfree(pbuffer); - status = STATUS_FAILURE; - } - } - else { - status = STATUS_FAILURE; - } - } - else - { - /* Checksum did not compute */ - status = STATUS_FAILURE; - } - DEBUG("ft1000:download: after STATE_SECTION_PROV, state = %d, status= %d\n", state, status); - break; - - case STATE_DONE_PROV: - DEBUG("FT1000:download:STATE_DONE_PROV\n"); - state = STATE_DONE_FILE; - break; - - - default: - status = STATUS_FAILURE; - break; - } /* End Switch */ - - if (status != STATUS_SUCCESS) { - break; - } + + word_length = (word_length / 2); + + for (; word_length > 0; word_length--) { /* In words */ + + templong = ntohs(*s_file++); + temp = ntohs(*s_file++); + templong |= (temp << 16); + status = + fix_ft1000_write_dpram32 + (ft1000dev, dpram++, + (u8 *) &templong); + + } + break; + + case REQUEST_CODE_BY_VERSION: + DEBUG + ("FT1000:download:REQUEST_CODE_BY_VERSION\n"); + correct_version = false; + requested_version = + get_request_value(ft1000dev); + + dsp_img_info = + (struct dsp_image_info *)(pFileStart + + + sizeof + (struct + dsp_file_hdr)); + + for (image = 0; + image < file_hdr->nDspImages; + image++) { + + if (dsp_img_info->version == + requested_version) { + correct_version = true; + DEBUG + ("FT1000:download: correct_version is TRUE\n"); + s_file = + (u16 *) (pFileStart + + + dsp_img_info-> + begin_offset); + c_file = + (u8 *) (pFileStart + + dsp_img_info-> + begin_offset); + code_end = + (u8 *) (pFileStart + + dsp_img_info-> + end_offset); + run_address = + dsp_img_info-> + run_address; + run_size = + dsp_img_info-> + image_size; + image_chksum = + (u32) dsp_img_info-> + checksum; + break; + } + dsp_img_info++; + + } /* end of for */ + + if (!correct_version) { + /* + * Error, beyond boot code range. + */ + DEBUG + ("FT1000:download:Download error: Bad Version Request = 0x%x.\n", + (int)requested_version); + status = -1; + break; + } + break; + + default: + DEBUG + ("FT1000:download:Download error: Bad request type=%d in CODE download state.\n", + request); + status = -1; + break; + } + if (ft1000dev->usbboot) + put_handshake_usb(ft1000dev, + HANDSHAKE_RESPONSE); + else + put_handshake(ft1000dev, + HANDSHAKE_RESPONSE); + } else { + DEBUG + ("FT1000:download:Download error: Handshake failed\n"); + status = -1; + } + + break; + + case STATE_DONE_DWNLD: + DEBUG("FT1000:download:Code loader is done...\n"); + state = STATE_SECTION_PROV; + break; + + case STATE_SECTION_PROV: + DEBUG("FT1000:download:STATE_SECTION_PROV\n"); + pseudo_header = (struct pseudo_hdr *)c_file; + + if (pseudo_header->checksum == + hdr_checksum(pseudo_header)) { + if (pseudo_header->portdest != + 0x80 /* Dsp OAM */) { + state = STATE_DONE_PROV; + break; + } + pseudo_header_len = ntohs(pseudo_header->length); /* Byte length for PROV records */ + + /* Get buffer for provisioning data */ + pbuffer = + kmalloc((pseudo_header_len + + sizeof(struct pseudo_hdr)), + GFP_ATOMIC); + if (pbuffer) { + memcpy(pbuffer, (void *)c_file, + (u32) (pseudo_header_len + + sizeof(struct + pseudo_hdr))); + /* link provisioning data */ + pprov_record = + kmalloc(sizeof(struct prov_record), + GFP_ATOMIC); + if (pprov_record) { + pprov_record->pprov_data = + pbuffer; + list_add_tail(&pprov_record-> + list, + &pft1000info-> + prov_list); + /* Move to next entry if available */ + c_file = + (u8 *) ((unsigned long) + c_file + + (u32) ((pseudo_header_len + 1) & 0xFFFFFFFE) + sizeof(struct pseudo_hdr)); + if ((unsigned long)(c_file) - + (unsigned long)(pFileStart) + >= + (unsigned long)FileLength) { + state = STATE_DONE_FILE; + } + } else { + kfree(pbuffer); + status = -1; + } + } else { + status = -1; + } + } else { + /* Checksum did not compute */ + status = -1; + } + DEBUG + ("ft1000:download: after STATE_SECTION_PROV, state = %d, status= %d\n", + state, status); + break; + + case STATE_DONE_PROV: + DEBUG("FT1000:download:STATE_DONE_PROV\n"); + state = STATE_DONE_FILE; + break; + + default: + status = -1; + break; + } /* End Switch */ + + if (status != 0) + break; /**** // Check if Card is present status = Harley_Read_Register(&temp, FT1000_REG_SUP_IMASK); if ( (status != NDIS_STATUS_SUCCESS) || (temp == 0x0000) ) { - break; + break; } status = Harley_Read_Register(&temp, FT1000_REG_ASIC_ID); if ( (status != NDIS_STATUS_SUCCESS) || (temp == 0xffff) ) { - break; + break; } ****/ - } /* End while */ + } /* End while */ - DEBUG("Download exiting with status = 0x%8x\n", status); - ft1000_write_register(ft1000dev, FT1000_DB_DNLD_TX, FT1000_REG_DOORBELL); + DEBUG("Download exiting with status = 0x%8x\n", status); + ft1000_write_register(ft1000dev, FT1000_DB_DNLD_TX, + FT1000_REG_DOORBELL); - return status; + return status; } - diff --git a/drivers/staging/ft1000/ft1000-usb/ft1000_hw.c b/drivers/staging/ft1000/ft1000-usb/ft1000_hw.c index 643a63794ad..b6a77088cfe 100644 --- a/drivers/staging/ft1000/ft1000-usb/ft1000_hw.c +++ b/drivers/staging/ft1000/ft1000-usb/ft1000_hw.c @@ -1,14 +1,9 @@ -//===================================================== -// CopyRight (C) 2007 Qualcomm Inc. All Rights Reserved. -// -// -// This file is part of Express Card USB Driver -// -// $Id: -//==================================================== -// 20090926; aelias; removed compiler warnings & errors; ubuntu 9.04; 2.6.28-15-generic - -#include <linux/init.h> +/* CopyRight (C) 2007 Qualcomm Inc. All Rights Reserved. +* +* +* This file is part of Express Card USB Driver +*/ + #include <linux/kernel.h> #include <linux/module.h> #include <linux/netdevice.h> @@ -29,863 +24,742 @@ #define HARLEY_READ_OPERATION 0xc1 #define HARLEY_WRITE_OPERATION 0x41 -//#define JDEBUG +#if 0 +#define JDEBUG +#endif -static int ft1000_reset(struct net_device *ft1000dev); static int ft1000_submit_rx_urb(struct ft1000_info *info); -static int ft1000_start_xmit(struct sk_buff *skb, struct net_device *dev); -static int ft1000_open (struct net_device *dev); -static struct net_device_stats *ft1000_netdev_stats(struct net_device *dev); -static int ft1000_chkcard (struct ft1000_device *dev); - -//Jim static u8 tempbuffer[1600]; #define MAX_RCV_LOOP 100 -//--------------------------------------------------------------------------- -// Function: ft1000_control -// -// Parameters: ft1000_device - device structure -// pipe - usb control message pipe -// request - control request -// requesttype - control message request type -// value - value to be written or 0 -// index - register index -// data - data buffer to hold the read/write values -// size - data size -// timeout - control message time out value -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function sends a control message via USB interface synchronously -// -// Notes: -// -//--------------------------------------------------------------------------- -static int ft1000_control(struct ft1000_device *ft1000dev,unsigned int pipe, - u8 request, - u8 requesttype, - u16 value, - u16 index, - void *data, - u16 size, - int timeout) +/* send a control message via USB interface synchronously +* Parameters: ft1000_usb - device structure +* pipe - usb control message pipe +* request - control request +* requesttype - control message request type +* value - value to be written or 0 +* index - register index +* data - data buffer to hold the read/write values +* size - data size +* timeout - control message time out value +*/ +static int ft1000_control(struct ft1000_usb *ft1000dev, unsigned int pipe, + u8 request, u8 requesttype, u16 value, u16 index, + void *data, u16 size, int timeout) { - u16 ret; - - if (ft1000dev == NULL ) - { - DEBUG("NULL ft1000dev, failure\n"); - return -ENODEV; - } - else if ( ft1000dev->dev == NULL ) - { - DEBUG("NULL ft1000dev->dev, failure\n"); - return -ENODEV; - } - - ret = usb_control_msg(ft1000dev->dev, - pipe, - request, - requesttype, - value, - index, - data, - size, - LARGE_TIMEOUT); + int ret; + + if ((ft1000dev == NULL) || (ft1000dev->dev == NULL)) { + DEBUG("ft1000dev or ft1000dev->dev == NULL, failure\n"); + return -ENODEV; + } + + ret = usb_control_msg(ft1000dev->dev, pipe, request, requesttype, + value, index, data, size, timeout); if (ret > 0) ret = 0; - return ret; + return ret; +} + +/* returns the value in a register */ +int ft1000_read_register(struct ft1000_usb *ft1000dev, u16 *Data, + u16 nRegIndx) +{ + int ret = 0; + + ret = ft1000_control(ft1000dev, + usb_rcvctrlpipe(ft1000dev->dev, 0), + HARLEY_READ_REGISTER, + HARLEY_READ_OPERATION, + 0, + nRegIndx, + Data, + 2, + USB_CTRL_GET_TIMEOUT); + + return ret; +} +/* writes the value in a register */ +int ft1000_write_register(struct ft1000_usb *ft1000dev, u16 value, + u16 nRegIndx) +{ + int ret = 0; + + ret = ft1000_control(ft1000dev, + usb_sndctrlpipe(ft1000dev->dev, 0), + HARLEY_WRITE_REGISTER, + HARLEY_WRITE_OPERATION, + value, + nRegIndx, + NULL, + 0, + USB_CTRL_SET_TIMEOUT); + return ret; } -//--------------------------------------------------------------------------- -// Function: ft1000_read_register -// -// Parameters: ft1000_device - device structure -// Data - data buffer to hold the value read -// nRegIndex - register index -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function returns the value in a register -// -// Notes: -// -//--------------------------------------------------------------------------- - -u16 ft1000_read_register(struct ft1000_device *ft1000dev, u16* Data, u16 nRegIndx) + +/* read a number of bytes from DPRAM */ +int ft1000_read_dpram32(struct ft1000_usb *ft1000dev, u16 indx, u8 *buffer, + u16 cnt) { - u16 ret = STATUS_SUCCESS; + int ret = 0; + + ret = ft1000_control(ft1000dev, + usb_rcvctrlpipe(ft1000dev->dev, 0), + HARLEY_READ_DPRAM_32, + HARLEY_READ_OPERATION, + 0, + indx, + buffer, + cnt, + USB_CTRL_GET_TIMEOUT); - //DEBUG("ft1000_read_register: reg index is %d\n", nRegIndx); - //DEBUG("ft1000_read_register: spin_lock locked\n"); - ret = ft1000_control(ft1000dev, - usb_rcvctrlpipe(ft1000dev->dev,0), - HARLEY_READ_REGISTER, //request --READ_REGISTER - HARLEY_READ_OPERATION, //requestType - 0, //value - nRegIndx, //index - Data, //data - 2, //data size - LARGE_TIMEOUT ); //timeout + return ret; +} - //DEBUG("ft1000_read_register: ret is %d \n", ret); +/* writes into DPRAM a number of bytes */ +int ft1000_write_dpram32(struct ft1000_usb *ft1000dev, u16 indx, u8 *buffer, + u16 cnt) +{ + int ret = 0; - //DEBUG("ft1000_read_register: data is %x \n", *Data); + if (cnt % 4) + cnt += cnt - (cnt % 4); - return ret; + ret = ft1000_control(ft1000dev, + usb_sndctrlpipe(ft1000dev->dev, 0), + HARLEY_WRITE_DPRAM_32, + HARLEY_WRITE_OPERATION, + 0, + indx, + buffer, + cnt, + USB_CTRL_SET_TIMEOUT); + return ret; } -//--------------------------------------------------------------------------- -// Function: ft1000_write_register -// -// Parameters: ft1000_device - device structure -// value - value to write into a register -// nRegIndex - register index -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function writes the value in a register -// -// Notes: -// -//--------------------------------------------------------------------------- -u16 ft1000_write_register(struct ft1000_device *ft1000dev, u16 value, u16 nRegIndx) +/* read 16 bits from DPRAM */ +int ft1000_read_dpram16(struct ft1000_usb *ft1000dev, u16 indx, u8 *buffer, + u8 highlow) { - u16 ret = STATUS_SUCCESS; + int ret = 0; + u8 request; + + if (highlow == 0) + request = HARLEY_READ_DPRAM_LOW; + else + request = HARLEY_READ_DPRAM_HIGH; + + ret = ft1000_control(ft1000dev, + usb_rcvctrlpipe(ft1000dev->dev, 0), + request, + HARLEY_READ_OPERATION, + 0, + indx, + buffer, + 2, + USB_CTRL_GET_TIMEOUT); - //DEBUG("ft1000_write_register: value is: %d, reg index is: %d\n", value, nRegIndx); + return ret; +} - ret = ft1000_control(ft1000dev, - usb_sndctrlpipe(ft1000dev->dev, 0), - HARLEY_WRITE_REGISTER, //request -- WRITE_REGISTER - HARLEY_WRITE_OPERATION, //requestType - value, - nRegIndx, - NULL, - 0, - LARGE_TIMEOUT ); +/* write into DPRAM a number of bytes */ +int ft1000_write_dpram16(struct ft1000_usb *ft1000dev, u16 indx, u16 value, + u8 highlow) +{ + int ret = 0; + u8 request; + + if (highlow == 0) + request = HARLEY_WRITE_DPRAM_LOW; + else + request = HARLEY_WRITE_DPRAM_HIGH; + + ret = ft1000_control(ft1000dev, + usb_sndctrlpipe(ft1000dev->dev, 0), + request, + HARLEY_WRITE_OPERATION, + value, + indx, + NULL, + 0, + USB_CTRL_SET_TIMEOUT); - return ret; + return ret; } -//--------------------------------------------------------------------------- -// Function: ft1000_read_dpram32 -// -// Parameters: ft1000_device - device structure -// indx - starting address to read -// buffer - data buffer to hold the data read -// cnt - number of byte read from DPRAM -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function read a number of bytes from DPRAM -// -// Notes: -// -//--------------------------------------------------------------------------- - -u16 ft1000_read_dpram32(struct ft1000_device *ft1000dev, u16 indx, u8 *buffer, u16 cnt) +/* read DPRAM 4 words at a time */ +int fix_ft1000_read_dpram32(struct ft1000_usb *ft1000dev, u16 indx, + u8 *buffer) { - u16 ret = STATUS_SUCCESS; + u8 buf[16]; + u16 pos; + int ret = 0; + + pos = (indx / 4) * 4; + ret = ft1000_read_dpram32(ft1000dev, pos, buf, 16); + + if (ret == 0) { + pos = (indx % 4) * 4; + *buffer++ = buf[pos++]; + *buffer++ = buf[pos++]; + *buffer++ = buf[pos++]; + *buffer++ = buf[pos++]; + } else { + DEBUG("fix_ft1000_read_dpram32: DPRAM32 Read failed\n"); + *buffer++ = 0; + *buffer++ = 0; + *buffer++ = 0; + *buffer++ = 0; + } - //DEBUG("ft1000_read_dpram32: indx: %d cnt: %d\n", indx, cnt); - ret =ft1000_control(ft1000dev, - usb_rcvctrlpipe(ft1000dev->dev,0), - HARLEY_READ_DPRAM_32, //request --READ_DPRAM_32 - HARLEY_READ_OPERATION, //requestType - 0, //value - indx, //index - buffer, //data - cnt, //data size - LARGE_TIMEOUT ); //timeout + return ret; +} - //DEBUG("ft1000_read_dpram32: ret is %d \n", ret); - //DEBUG("ft1000_read_dpram32: ret=%d \n", ret); +/* Description: This function write to DPRAM 4 words at a time */ +int fix_ft1000_write_dpram32(struct ft1000_usb *ft1000dev, u16 indx, u8 *buffer) +{ + u16 pos1; + u16 pos2; + u16 i; + u8 buf[32]; + u8 resultbuffer[32]; + u8 *pdata; + int ret = 0; + + pos1 = (indx / 4) * 4; + pdata = buffer; + ret = ft1000_read_dpram32(ft1000dev, pos1, buf, 16); + + if (ret == 0) { + pos2 = (indx % 4)*4; + buf[pos2++] = *buffer++; + buf[pos2++] = *buffer++; + buf[pos2++] = *buffer++; + buf[pos2++] = *buffer++; + ret = ft1000_write_dpram32(ft1000dev, pos1, buf, 16); + } else { + DEBUG("fix_ft1000_write_dpram32: DPRAM32 Read failed\n"); + return ret; + } + + ret = ft1000_read_dpram32(ft1000dev, pos1, (u8 *)&resultbuffer[0], 16); + + if (ret == 0) { + buffer = pdata; + for (i = 0; i < 16; i++) { + if (buf[i] != resultbuffer[i]) + ret = -1; + } + } - return ret; + if (ret == -1) { + ret = ft1000_write_dpram32(ft1000dev, pos1, + (u8 *)&tempbuffer[0], 16); + ret = ft1000_read_dpram32(ft1000dev, pos1, + (u8 *)&resultbuffer[0], 16); + if (ret == 0) { + buffer = pdata; + for (i = 0; i < 16; i++) { + if (tempbuffer[i] != resultbuffer[i]) { + ret = -1; + DEBUG("%s Failed to write\n", + __func__); + } + } + } + } + return ret; } -//--------------------------------------------------------------------------- -// Function: ft1000_write_dpram32 -// -// Parameters: ft1000_device - device structure -// indx - starting address to write the data -// buffer - data buffer to write into DPRAM -// cnt - number of bytes to write -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function writes into DPRAM a number of bytes -// -// Notes: -// -//--------------------------------------------------------------------------- -u16 ft1000_write_dpram32(struct ft1000_device *ft1000dev, u16 indx, u8 *buffer, u16 cnt) +/* reset or activate the DSP */ +static void card_reset_dsp(struct ft1000_usb *ft1000dev, bool value) { - u16 ret = STATUS_SUCCESS; - - //DEBUG("ft1000_write_dpram32: indx: %d buffer: %x cnt: %d\n", indx, buffer, cnt); - if ( cnt % 4) - cnt += cnt - (cnt % 4); - - ret = ft1000_control(ft1000dev, - usb_sndctrlpipe(ft1000dev->dev, 0), - HARLEY_WRITE_DPRAM_32, //request -- WRITE_DPRAM_32 - HARLEY_WRITE_OPERATION, //requestType - 0, //value - indx, //index - buffer, //buffer - cnt, //buffer size - LARGE_TIMEOUT ); - - return ret; + int status = 0; + u16 tempword; + + status = ft1000_write_register(ft1000dev, HOST_INTF_BE, + FT1000_REG_SUP_CTRL); + status = ft1000_read_register(ft1000dev, &tempword, + FT1000_REG_SUP_CTRL); + + if (value) { + DEBUG("Reset DSP\n"); + status = ft1000_read_register(ft1000dev, &tempword, + FT1000_REG_RESET); + tempword |= DSP_RESET_BIT; + status = ft1000_write_register(ft1000dev, tempword, + FT1000_REG_RESET); + } else { + DEBUG("Activate DSP\n"); + status = ft1000_read_register(ft1000dev, &tempword, + FT1000_REG_RESET); + tempword |= DSP_ENCRYPTED; + tempword &= ~DSP_UNENCRYPTED; + status = ft1000_write_register(ft1000dev, tempword, + FT1000_REG_RESET); + status = ft1000_read_register(ft1000dev, &tempword, + FT1000_REG_RESET); + tempword &= ~EFUSE_MEM_DISABLE; + tempword &= ~DSP_RESET_BIT; + status = ft1000_write_register(ft1000dev, tempword, + FT1000_REG_RESET); + status = ft1000_read_register(ft1000dev, &tempword, + FT1000_REG_RESET); + } } -//--------------------------------------------------------------------------- -// Function: ft1000_read_dpram16 -// -// Parameters: ft1000_device - device structure -// indx - starting address to read -// buffer - data buffer to hold the data read -// hightlow - high or low 16 bit word -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function read 16 bits from DPRAM -// -// Notes: -// -//--------------------------------------------------------------------------- -u16 ft1000_read_dpram16(struct ft1000_device *ft1000dev, u16 indx, u8 *buffer, u8 highlow) +/* send a command to ASIC +* Parameters: ft1000_usb - device structure +* ptempbuffer - command buffer +* size - command buffer size +*/ +void card_send_command(struct ft1000_usb *ft1000dev, void *ptempbuffer, + int size) { - u16 ret = STATUS_SUCCESS; + unsigned short temp; + unsigned char *commandbuf; + + DEBUG("card_send_command: enter card_send_command... size=%d\n", size); - //DEBUG("ft1000_read_dpram16: indx: %d hightlow: %d\n", indx, highlow); + commandbuf = kmalloc(size + 2, GFP_KERNEL); + memcpy((void *)commandbuf + 2, (void *)ptempbuffer, size); - u8 request; + ft1000_read_register(ft1000dev, &temp, FT1000_REG_DOORBELL); - if (highlow == 0 ) - request = HARLEY_READ_DPRAM_LOW; - else - request = HARLEY_READ_DPRAM_HIGH; + if (temp & 0x0100) + usleep_range(900, 1100); - ret = ft1000_control(ft1000dev, - usb_rcvctrlpipe(ft1000dev->dev,0), - request, //request --READ_DPRAM_H/L - HARLEY_READ_OPERATION, //requestType - 0, //value - indx, //index - buffer, //data - 2, //data size - LARGE_TIMEOUT ); //timeout + /* check for odd word */ + size = size + 2; - //DEBUG("ft1000_read_dpram16: ret is %d \n", ret); + /* Must force to be 32 bit aligned */ + if (size % 4) + size += 4 - (size % 4); + ft1000_write_dpram32(ft1000dev, 0, commandbuf, size); + usleep_range(900, 1100); + ft1000_write_register(ft1000dev, FT1000_DB_DPRAM_TX, + FT1000_REG_DOORBELL); + usleep_range(900, 1100); - //DEBUG("ft1000_read_dpram16: data is %x \n", *buffer); + ft1000_read_register(ft1000dev, &temp, FT1000_REG_DOORBELL); - return ret; +#if 0 + if ((temp & 0x0100) == 0) + DEBUG("card_send_command: Message sent\n"); +#endif } -//--------------------------------------------------------------------------- -// Function: ft1000_write_dpram16 -// -// Parameters: ft1000_device - device structure -// indx - starting address to write the data -// value - 16bits value to write -// hightlow - high or low 16 bit word -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function writes into DPRAM a number of bytes -// -// Notes: -// -//--------------------------------------------------------------------------- -u16 ft1000_write_dpram16(struct ft1000_device *ft1000dev, u16 indx, u16 value, u8 highlow) +/* load or reload the DSP */ +int dsp_reload(struct ft1000_usb *ft1000dev) { - u16 ret = STATUS_SUCCESS; + int status; + u16 tempword; + u32 templong; + struct ft1000_info *pft1000info; + pft1000info = netdev_priv(ft1000dev->net); - //DEBUG("ft1000_write_dpram16: indx: %d value: %d highlow: %d\n", indx, value, highlow); + pft1000info->CardReady = 0; - u8 request; + /* Program Interrupt Mask register */ + status = ft1000_write_register(ft1000dev, 0xffff, FT1000_REG_SUP_IMASK); + status = ft1000_read_register(ft1000dev, &tempword, FT1000_REG_RESET); + tempword |= ASIC_RESET_BIT; + status = ft1000_write_register(ft1000dev, tempword, FT1000_REG_RESET); + msleep(1000); + status = ft1000_read_register(ft1000dev, &tempword, FT1000_REG_RESET); + DEBUG("Reset Register = 0x%x\n", tempword); - if ( highlow == 0 ) - request = HARLEY_WRITE_DPRAM_LOW; - else - request = HARLEY_WRITE_DPRAM_HIGH; + /* Toggle DSP reset */ + card_reset_dsp(ft1000dev, 1); + msleep(1000); + card_reset_dsp(ft1000dev, 0); + msleep(1000); - ret = ft1000_control(ft1000dev, - usb_sndctrlpipe(ft1000dev->dev, 0), - request, //request -- WRITE_DPRAM_H/L - HARLEY_WRITE_OPERATION, //requestType - value, //value - indx, //index - NULL, //buffer - 0, //buffer size - LARGE_TIMEOUT ); + status = + ft1000_write_register(ft1000dev, HOST_INTF_BE, FT1000_REG_SUP_CTRL); - return ret; -} + /* Let's check for FEFE */ + status = + ft1000_read_dpram32(ft1000dev, FT1000_MAG_DPRAM_FEFE_INDX, + (u8 *) &templong, 4); + DEBUG("templong (fefe) = 0x%8x\n", templong); -//--------------------------------------------------------------------------- -// Function: fix_ft1000_read_dpram32 -// -// Parameters: ft1000_device - device structure -// indx - starting address to read -// buffer - data buffer to hold the data read -// -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function read DPRAM 4 words at a time -// -// Notes: -// -//--------------------------------------------------------------------------- -u16 fix_ft1000_read_dpram32(struct ft1000_device *ft1000dev, u16 indx, u8 *buffer) -{ - u8 buf[16]; - u16 pos; - u16 ret = STATUS_SUCCESS; - - //DEBUG("fix_ft1000_read_dpram32: indx: %d \n", indx); - pos = (indx / 4)*4; - ret = ft1000_read_dpram32(ft1000dev, pos, buf, 16); - if (ret == STATUS_SUCCESS) - { - pos = (indx % 4)*4; - *buffer++ = buf[pos++]; - *buffer++ = buf[pos++]; - *buffer++ = buf[pos++]; - *buffer++ = buf[pos++]; - } - else - { - DEBUG("fix_ft1000_read_dpram32: DPRAM32 Read failed\n"); - *buffer++ = 0; - *buffer++ = 0; - *buffer++ = 0; - *buffer++ = 0; - - } - - //DEBUG("fix_ft1000_read_dpram32: data is %x \n", *buffer); - return ret; + /* call codeloader */ + status = scram_dnldr(ft1000dev, pFileStart, FileLength); -} + if (status != 0) + return -EIO; + msleep(1000); -//--------------------------------------------------------------------------- -// Function: fix_ft1000_write_dpram32 -// -// Parameters: ft1000_device - device structure -// indx - starting address to write -// buffer - data buffer to write -// -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function write to DPRAM 4 words at a time -// -// Notes: -// -//--------------------------------------------------------------------------- -u16 fix_ft1000_write_dpram32(struct ft1000_device *ft1000dev, u16 indx, u8 *buffer) -{ - u16 pos1; - u16 pos2; - u16 i; - u8 buf[32]; - u8 resultbuffer[32]; - u8 *pdata; - u16 ret = STATUS_SUCCESS; - - //DEBUG("fix_ft1000_write_dpram32: Entered:\n"); - - pos1 = (indx / 4)*4; - pdata = buffer; - ret = ft1000_read_dpram32(ft1000dev, pos1, buf, 16); - if (ret == STATUS_SUCCESS) - { - pos2 = (indx % 4)*4; - buf[pos2++] = *buffer++; - buf[pos2++] = *buffer++; - buf[pos2++] = *buffer++; - buf[pos2++] = *buffer++; - ret = ft1000_write_dpram32(ft1000dev, pos1, buf, 16); - } - else - { - DEBUG("fix_ft1000_write_dpram32: DPRAM32 Read failed\n"); - - return ret; - } - - ret = ft1000_read_dpram32(ft1000dev, pos1, (u8 *)&resultbuffer[0], 16); - if (ret == STATUS_SUCCESS) - { - buffer = pdata; - for (i=0; i<16; i++) - { - if (buf[i] != resultbuffer[i]){ - - ret = STATUS_FAILURE; - } - } - } - - if (ret == STATUS_FAILURE) - { - ret = ft1000_write_dpram32(ft1000dev, pos1, (u8 *)&tempbuffer[0], 16); - ret = ft1000_read_dpram32(ft1000dev, pos1, (u8 *)&resultbuffer[0], 16); - if (ret == STATUS_SUCCESS) - { - buffer = pdata; - for (i=0; i<16; i++) - { - if (tempbuffer[i] != resultbuffer[i]) - { - ret = STATUS_FAILURE; - DEBUG("fix_ft1000_write_dpram32 Failed to write\n"); - } - } - } - } - - return ret; + DEBUG("dsp_reload returned\n"); + return 0; } - -//------------------------------------------------------------------------ -// -// Function: card_reset_dsp -// -// Synopsis: This function is called to reset or activate the DSP -// -// Arguments: value - reset or activate -// -// Returns: None -//----------------------------------------------------------------------- -static void card_reset_dsp (struct ft1000_device *ft1000dev, bool value) +/* call the Card Service function to reset the ASIC. */ +static void ft1000_reset_asic(struct net_device *dev) { - u16 status = STATUS_SUCCESS; - u16 tempword; - - status = ft1000_write_register (ft1000dev, HOST_INTF_BE, FT1000_REG_SUP_CTRL); - status = ft1000_read_register(ft1000dev, &tempword, FT1000_REG_SUP_CTRL); - if (value) - { - DEBUG("Reset DSP\n"); - status = ft1000_read_register(ft1000dev, &tempword, FT1000_REG_RESET); - tempword |= DSP_RESET_BIT; - status = ft1000_write_register(ft1000dev, tempword, FT1000_REG_RESET); - } - else - { - DEBUG("Activate DSP\n"); - status = ft1000_read_register(ft1000dev, &tempword, FT1000_REG_RESET); - tempword |= DSP_ENCRYPTED; - tempword &= ~DSP_UNENCRYPTED; - status = ft1000_write_register(ft1000dev, tempword, FT1000_REG_RESET); - status = ft1000_read_register(ft1000dev, &tempword, FT1000_REG_RESET); - tempword &= ~EFUSE_MEM_DISABLE; - tempword &= ~DSP_RESET_BIT; - status = ft1000_write_register(ft1000dev, tempword, FT1000_REG_RESET); - status = ft1000_read_register(ft1000dev, &tempword, FT1000_REG_RESET); - } -} + struct ft1000_info *info = netdev_priv(dev); + struct ft1000_usb *ft1000dev = info->priv; + u16 tempword; -//--------------------------------------------------------------------------- -// Function: CardSendCommand -// -// Parameters: ft1000_device - device structure -// ptempbuffer - command buffer -// size - command buffer size -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function sends a command to ASIC -// -// Notes: -// -//--------------------------------------------------------------------------- -void CardSendCommand(struct ft1000_device *ft1000dev, void *ptempbuffer, int size) -{ - unsigned short temp; - unsigned char *commandbuf; + DEBUG("ft1000_hw:ft1000_reset_asic called\n"); - DEBUG("CardSendCommand: enter CardSendCommand... size=%d\n", size); + /* Let's use the register provided by the Magnemite ASIC to reset the + * ASIC and DSP. + */ + ft1000_write_register(ft1000dev, (DSP_RESET_BIT | ASIC_RESET_BIT), + FT1000_REG_RESET); - commandbuf =(unsigned char*) kmalloc(size+2, GFP_KERNEL); - memcpy((void*)commandbuf+2, (void*)ptempbuffer, size); + mdelay(1); - //DEBUG("CardSendCommand: Command Send\n"); + /* set watermark to -1 in order to not generate an interrupt */ + ft1000_write_register(ft1000dev, 0xffff, FT1000_REG_MAG_WATERMARK); - ft1000_read_register(ft1000dev, &temp, FT1000_REG_DOORBELL); + /* clear interrupts */ + ft1000_read_register(ft1000dev, &tempword, FT1000_REG_SUP_ISR); + DEBUG("ft1000_hw: interrupt status register = 0x%x\n", tempword); + ft1000_write_register(ft1000dev, tempword, FT1000_REG_SUP_ISR); + ft1000_read_register(ft1000dev, &tempword, FT1000_REG_SUP_ISR); + DEBUG("ft1000_hw: interrupt status register = 0x%x\n", tempword); +} - if (temp & 0x0100) - { - msleep(10); - } +static int ft1000_reset_card(struct net_device *dev) +{ + struct ft1000_info *info = netdev_priv(dev); + struct ft1000_usb *ft1000dev = info->priv; + u16 tempword; + struct prov_record *ptr; - // check for odd word - size = size + 2; - if (size % 4) - { - // Must force to be 32 bit aligned - size += 4 - (size % 4); - } + DEBUG("ft1000_hw:ft1000_reset_card called.....\n"); + ft1000dev->fCondResetPend = true; + info->CardReady = 0; + ft1000dev->fProvComplete = false; - //DEBUG("CardSendCommand: write dpram ... size=%d\n", size); - ft1000_write_dpram32(ft1000dev, 0,commandbuf, size); - msleep(1); - //DEBUG("CardSendCommand: write into doorbell ...\n"); - ft1000_write_register(ft1000dev, FT1000_DB_DPRAM_TX ,FT1000_REG_DOORBELL) ; - msleep(1); + /* Make sure we free any memory reserve for provisioning */ + while (list_empty(&info->prov_list) == 0) { + DEBUG("ft1000_reset_card:deleting provisioning record\n"); + ptr = + list_entry(info->prov_list.next, struct prov_record, list); + list_del(&ptr->list); + kfree(ptr->pprov_data); + kfree(ptr); + } - ft1000_read_register(ft1000dev, &temp, FT1000_REG_DOORBELL); - //DEBUG("CardSendCommand: read doorbell ...temp=%x\n", temp); - if ( (temp & 0x0100) == 0) - { - //DEBUG("CardSendCommand: Message sent\n"); - } + DEBUG("ft1000_hw:ft1000_reset_card: reset asic\n"); + ft1000_reset_asic(dev); -} + DEBUG("ft1000_hw:ft1000_reset_card: call dsp_reload\n"); + dsp_reload(ft1000dev); + DEBUG("dsp reload successful\n"); -//-------------------------------------------------------------------------- -// -// Function: dsp_reload -// -// Synopsis: This function is called to load or reload the DSP -// -// Arguments: ft1000dev - device structure -// -// Returns: None -//----------------------------------------------------------------------- -int dsp_reload(struct ft1000_device *ft1000dev) -{ - u16 status; - u16 tempword; - u32 templong; + mdelay(10); - struct ft1000_info *pft1000info; + /* Initialize DSP heartbeat area */ + ft1000_write_dpram16(ft1000dev, FT1000_MAG_HI_HO, ho_mag, + FT1000_MAG_HI_HO_INDX); + ft1000_read_dpram16(ft1000dev, FT1000_MAG_HI_HO, (u8 *) &tempword, + FT1000_MAG_HI_HO_INDX); + DEBUG("ft1000_hw:ft1000_reset_card:hi_ho value = 0x%x\n", tempword); - pft1000info = netdev_priv(ft1000dev->net); + info->CardReady = 1; - pft1000info->CardReady = 0; + ft1000dev->fCondResetPend = false; - // Program Interrupt Mask register - status = ft1000_write_register (ft1000dev, 0xffff, FT1000_REG_SUP_IMASK); + return TRUE; +} - status = ft1000_read_register (ft1000dev, &tempword, FT1000_REG_RESET); - tempword |= ASIC_RESET_BIT; - status = ft1000_write_register (ft1000dev, tempword, FT1000_REG_RESET); - msleep(1000); - status = ft1000_read_register (ft1000dev, &tempword, FT1000_REG_RESET); - DEBUG("Reset Register = 0x%x\n", tempword); +/* callback function when a urb is transmitted */ +static void ft1000_usb_transmit_complete(struct urb *urb) +{ - // Toggle DSP reset - card_reset_dsp (ft1000dev, 1); - msleep(1000); - card_reset_dsp (ft1000dev, 0); - msleep(1000); + struct ft1000_usb *ft1000dev = urb->context; - status = ft1000_write_register (ft1000dev, HOST_INTF_BE, FT1000_REG_SUP_CTRL); + if (urb->status) + pr_err("%s: TX status %d\n", ft1000dev->net->name, urb->status); - // Let's check for FEFE - status = ft1000_read_dpram32 (ft1000dev, FT1000_MAG_DPRAM_FEFE_INDX, (u8 *)&templong, 4); - DEBUG("templong (fefe) = 0x%8x\n", templong); + netif_wake_queue(ft1000dev->net); +} - // call codeloader - status = scram_dnldr(ft1000dev, pFileStart, FileLength); +/* take an ethernet packet and convert it to a Flarion +* packet prior to sending it to the ASIC Downlink FIFO. +*/ +static int ft1000_copy_down_pkt(struct net_device *netdev, u8 *packet, u16 len) +{ + struct ft1000_info *pInfo = netdev_priv(netdev); + struct ft1000_usb *pFt1000Dev = pInfo->priv; - if (status != STATUS_SUCCESS) - return -EIO; + int count, ret; + u8 *t; + struct pseudo_hdr hdr; - msleep(1000); + if (!pInfo->CardReady) { + DEBUG("ft1000_copy_down_pkt::Card Not Ready\n"); + return -ENODEV; + } - DEBUG("dsp_reload returned\n"); - return 0; + count = sizeof(struct pseudo_hdr) + len; + if (count > MAX_BUF_SIZE) { + DEBUG("Error:ft1000_copy_down_pkt:Message Size Overflow!\n"); + DEBUG("size = %d\n", count); + return -EINVAL; + } -} + if (count % 4) + count = count + (4 - (count % 4)); -//--------------------------------------------------------------------------- -// -// Function: ft1000_reset_asic -// Descripton: This function will call the Card Service function to reset the -// ASIC. -// Input: -// dev - device structure -// Output: -// none -// -//--------------------------------------------------------------------------- -static void ft1000_reset_asic (struct net_device *dev) -{ - struct ft1000_info *info = netdev_priv(dev); - struct ft1000_device *ft1000dev = info->pFt1000Dev; - u16 tempword; + memset(&hdr, 0, sizeof(struct pseudo_hdr)); - DEBUG("ft1000_hw:ft1000_reset_asic called\n"); + hdr.length = ntohs(count); + hdr.source = 0x10; + hdr.destination = 0x20; + hdr.portdest = 0x20; + hdr.portsrc = 0x10; + hdr.sh_str_id = 0x91; + hdr.control = 0x00; - info->ASICResetNum++; + hdr.checksum = hdr.length ^ hdr.source ^ hdr.destination ^ + hdr.portdest ^ hdr.portsrc ^ hdr.sh_str_id ^ hdr.control; - // Let's use the register provided by the Magnemite ASIC to reset the - // ASIC and DSP. - ft1000_write_register(ft1000dev, (DSP_RESET_BIT | ASIC_RESET_BIT), FT1000_REG_RESET ); + memcpy(&pFt1000Dev->tx_buf[0], &hdr, sizeof(hdr)); + memcpy(&(pFt1000Dev->tx_buf[sizeof(struct pseudo_hdr)]), packet, len); - mdelay(1); + netif_stop_queue(netdev); - // set watermark to -1 in order to not generate an interrrupt - ft1000_write_register(ft1000dev, 0xffff, FT1000_REG_MAG_WATERMARK); + usb_fill_bulk_urb(pFt1000Dev->tx_urb, + pFt1000Dev->dev, + usb_sndbulkpipe(pFt1000Dev->dev, + pFt1000Dev->bulk_out_endpointAddr), + pFt1000Dev->tx_buf, count, + ft1000_usb_transmit_complete, (void *)pFt1000Dev); - // clear interrupts - ft1000_read_register (ft1000dev, &tempword, FT1000_REG_SUP_ISR); - DEBUG("ft1000_hw: interrupt status register = 0x%x\n",tempword); - ft1000_write_register (ft1000dev, tempword, FT1000_REG_SUP_ISR); - ft1000_read_register (ft1000dev, &tempword, FT1000_REG_SUP_ISR); - DEBUG("ft1000_hw: interrupt status register = 0x%x\n",tempword); + t = (u8 *) pFt1000Dev->tx_urb->transfer_buffer; -} + ret = usb_submit_urb(pFt1000Dev->tx_urb, GFP_ATOMIC); + + if (ret) { + DEBUG("ft1000 failed tx_urb %d\n", ret); + return ret; + } else { + pInfo->stats.tx_packets++; + pInfo->stats.tx_bytes += (len + 14); + } + return 0; +} -//--------------------------------------------------------------------------- -// -// Function: ft1000_reset_card -// Descripton: This function will reset the card -// Input: -// dev - device structure -// Output: -// status - FALSE (card reset fail) -// TRUE (card reset successful) -// -//--------------------------------------------------------------------------- -static int ft1000_reset_card (struct net_device *dev) +/* transmit an ethernet packet +* Parameters: skb - socket buffer to be sent +* dev - network device +*/ +static int ft1000_start_xmit(struct sk_buff *skb, struct net_device *dev) { - struct ft1000_info *info = netdev_priv(dev); - struct ft1000_device *ft1000dev = info->pFt1000Dev; - u16 tempword; - struct prov_record *ptr; + struct ft1000_info *pInfo = netdev_priv(dev); + struct ft1000_usb *pFt1000Dev = pInfo->priv; + u8 *pdata; + int maxlen, pipe; - DEBUG("ft1000_hw:ft1000_reset_card called.....\n"); + if (skb == NULL) { + DEBUG("ft1000_hw: ft1000_start_xmit:skb == NULL!!!\n"); + return NETDEV_TX_OK; + } - info->fCondResetPend = 1; - info->CardReady = 0; - info->fProvComplete = 0; + if (pFt1000Dev->status & FT1000_STATUS_CLOSING) { + DEBUG("network driver is closed, return\n"); + goto err; + } - // Make sure we free any memory reserve for provisioning - while (list_empty(&info->prov_list) == 0) { - DEBUG("ft1000_hw:ft1000_reset_card:deleting provisioning record\n"); - ptr = list_entry(info->prov_list.next, struct prov_record, list); - list_del(&ptr->list); - kfree(ptr->pprov_data); - kfree(ptr); - } + pipe = + usb_sndbulkpipe(pFt1000Dev->dev, pFt1000Dev->bulk_out_endpointAddr); + maxlen = usb_maxpacket(pFt1000Dev->dev, pipe, usb_pipeout(pipe)); - DEBUG("ft1000_hw:ft1000_reset_card: reset asic\n"); - //reset ASIC - ft1000_reset_asic(dev); + pdata = (u8 *) skb->data; - info->DSPResetNum++; + if (pInfo->mediastate == 0) { + /* Drop packet is mediastate is down */ + DEBUG("ft1000_hw:ft1000_start_xmit:mediastate is down\n"); + goto err; + } - DEBUG("ft1000_hw:ft1000_reset_card: call dsp_reload\n"); - dsp_reload(ft1000dev); + if ((skb->len < ENET_HEADER_SIZE) || (skb->len > ENET_MAX_SIZE)) { + /* Drop packet which has invalid size */ + DEBUG("ft1000_hw:ft1000_start_xmit:invalid ethernet length\n"); + goto err; + } - DEBUG("dsp reload successful\n"); + ft1000_copy_down_pkt(dev, (pdata + ENET_HEADER_SIZE - 2), + skb->len - ENET_HEADER_SIZE + 2); +err: + dev_kfree_skb(skb); - mdelay(10); + return NETDEV_TX_OK; +} - // Initialize DSP heartbeat area to ho - ft1000_write_dpram16(ft1000dev, FT1000_MAG_HI_HO, ho_mag, FT1000_MAG_HI_HO_INDX); - ft1000_read_dpram16(ft1000dev, FT1000_MAG_HI_HO, (u8 *)&tempword, FT1000_MAG_HI_HO_INDX); - DEBUG("ft1000_hw:ft1000_reset_card:hi_ho value = 0x%x\n", tempword); +/* open the network driver */ +static int ft1000_open(struct net_device *dev) +{ + struct ft1000_info *pInfo = netdev_priv(dev); + struct ft1000_usb *pFt1000Dev = pInfo->priv; + struct timeval tv; + DEBUG("ft1000_open is called for card %d\n", pFt1000Dev->CardNumber); + pInfo->stats.rx_bytes = 0; + pInfo->stats.tx_bytes = 0; + pInfo->stats.rx_packets = 0; + pInfo->stats.tx_packets = 0; + do_gettimeofday(&tv); + pInfo->ConTm = tv.tv_sec; + pInfo->ProgConStat = 0; - info->CardReady = 1; + netif_start_queue(dev); - info->fCondResetPend = 0; - return TRUE; + netif_carrier_on(dev); + return ft1000_submit_rx_urb(pInfo); } - -//mbelian -#ifdef HAVE_NET_DEVICE_OPS -static const struct net_device_ops ftnet_ops = +static struct net_device_stats *ft1000_netdev_stats(struct net_device *dev) { -.ndo_open = &ft1000_open, -.ndo_stop = &ft1000_close, -.ndo_start_xmit = &ft1000_start_xmit, -.ndo_get_stats = &ft1000_netdev_stats, + struct ft1000_info *info = netdev_priv(dev); + + return &(info->stats); +} + +static const struct net_device_ops ftnet_ops = { + .ndo_open = &ft1000_open, + .ndo_stop = &ft1000_close, + .ndo_start_xmit = &ft1000_start_xmit, + .ndo_get_stats = &ft1000_netdev_stats, }; -#endif +/* initialize the network device */ +static int ft1000_reset(void *dev) +{ + ft1000_reset_card(dev); + return 0; +} -//--------------------------------------------------------------------------- -// Function: init_ft1000_netdev -// -// Parameters: ft1000dev - device structure -// -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function initialize the network device -// -// Notes: -// -//--------------------------------------------------------------------------- -u16 init_ft1000_netdev(struct ft1000_device *ft1000dev) +int init_ft1000_netdev(struct ft1000_usb *ft1000dev) { - struct net_device *netdev; + struct net_device *netdev; struct ft1000_info *pInfo = NULL; struct dpram_blk *pdpram_blk; int i, ret_val; struct list_head *cur, *tmp; char card_nr[2]; - unsigned long gCardIndex = 0; - - DEBUG("Enter init_ft1000_netdev...\n"); + u8 gCardIndex = 0; + DEBUG("Enter init_ft1000_netdev...\n"); netdev = alloc_etherdev(sizeof(struct ft1000_info)); - if (!netdev ) - { - DEBUG("init_ft1000_netdev: can not allocate network device\n"); - return -ENOMEM; - } + if (!netdev) { + DEBUG("init_ft1000_netdev: can not allocate network device\n"); + return -ENOMEM; + } pInfo = netdev_priv(netdev); - //DEBUG("init_ft1000_netdev: gFt1000Info=%x, netdev=%x, ft1000dev=%x\n", gFt1000Info, netdev, ft1000dev); - memset(pInfo, 0, sizeof(struct ft1000_info)); - dev_alloc_name(netdev, netdev->name); + dev_alloc_name(netdev, netdev->name); - DEBUG("init_ft1000_netdev: network device name is %s\n", netdev->name); + DEBUG("init_ft1000_netdev: network device name is %s\n", netdev->name); - if ( strncmp(netdev->name,"eth", 3) == 0) { + if (strncmp(netdev->name, "eth", 3) == 0) { card_nr[0] = netdev->name[3]; card_nr[1] = '\0'; - ret_val = strict_strtoul(card_nr, 10, &gCardIndex); + ret_val = kstrtou8(card_nr, 10, &gCardIndex); if (ret_val) { - printk(KERN_ERR "Can't parse netdev\n"); + netdev_err(ft1000dev->net, "Can't parse netdev\n"); goto err_net; } - pInfo->CardNumber = gCardIndex; - DEBUG("card number = %d\n", pInfo->CardNumber); - } - else { - printk(KERN_ERR "ft1000: Invalid device name\n"); + ft1000dev->CardNumber = gCardIndex; + DEBUG("card number = %d\n", ft1000dev->CardNumber); + } else { + netdev_err(ft1000dev->net, "ft1000: Invalid device name\n"); ret_val = -ENXIO; goto err_net; - } - - memset(&pInfo->stats, 0, sizeof(struct net_device_stats) ); - - spin_lock_init(&pInfo->dpram_lock); - pInfo->pFt1000Dev = ft1000dev; - pInfo->DrvErrNum = 0; - pInfo->ASICResetNum = 0; - pInfo->registered = 1; - pInfo->ft1000_reset = ft1000_reset; - pInfo->mediastate = 0; - pInfo->fifo_cnt = 0; - pInfo->DeviceCreated = FALSE; - pInfo->CurrentInterruptEnableMask = ISR_DEFAULT_MASK; - pInfo->InterruptsEnabled = FALSE; - pInfo->CardReady = 0; - pInfo->DSP_TIME[0] = 0; - pInfo->DSP_TIME[1] = 0; - pInfo->DSP_TIME[2] = 0; - pInfo->DSP_TIME[3] = 0; - pInfo->fAppMsgPend = 0; - pInfo->fCondResetPend = 0; - pInfo->usbboot = 0; - pInfo->dspalive = 0; - memset(&pInfo->tempbuf[0], 0, sizeof(pInfo->tempbuf)); - - INIT_LIST_HEAD(&pInfo->prov_list); - - INIT_LIST_HEAD(&pInfo->nodes.list); -//mbelian -#ifdef HAVE_NET_DEVICE_OPS - netdev->netdev_ops = &ftnet_ops; -#else - netdev->hard_start_xmit = &ft1000_start_xmit; - netdev->get_stats = &ft1000_netdev_stats; - netdev->open = &ft1000_open; - netdev->stop = &ft1000_close; -#endif + } - ft1000dev->net = netdev; + memset(&pInfo->stats, 0, sizeof(struct net_device_stats)); + + spin_lock_init(&pInfo->dpram_lock); + pInfo->priv = ft1000dev; + pInfo->DrvErrNum = 0; + pInfo->registered = 1; + pInfo->ft1000_reset = ft1000_reset; + pInfo->mediastate = 0; + pInfo->fifo_cnt = 0; + ft1000dev->DeviceCreated = FALSE; + pInfo->CardReady = 0; + pInfo->DSP_TIME[0] = 0; + pInfo->DSP_TIME[1] = 0; + pInfo->DSP_TIME[2] = 0; + pInfo->DSP_TIME[3] = 0; + ft1000dev->fAppMsgPend = false; + ft1000dev->fCondResetPend = false; + ft1000dev->usbboot = 0; + ft1000dev->dspalive = 0; + memset(&ft1000dev->tempbuf[0], 0, sizeof(ft1000dev->tempbuf)); + + INIT_LIST_HEAD(&pInfo->prov_list); + + INIT_LIST_HEAD(&ft1000dev->nodes.list); + netdev->netdev_ops = &ftnet_ops; + ft1000dev->net = netdev; -//init free_buff_lock, freercvpool, numofmsgbuf, pdpram_blk -//only init once per card -//Jim - DEBUG("Initialize free_buff_lock and freercvpool\n"); - spin_lock_init(&free_buff_lock); + DEBUG("Initialize free_buff_lock and freercvpool\n"); + spin_lock_init(&free_buff_lock); - // initialize a list of buffers to be use for queuing up receive command data - INIT_LIST_HEAD (&freercvpool); + /* initialize a list of buffers to be use for queuing + * up receive command data + */ + INIT_LIST_HEAD(&freercvpool); - // create list of free buffers - for (i=0; i<NUM_OF_FREE_BUFFERS; i++) { - // Get memory for DPRAM_DATA link list + /* create list of free buffers */ + for (i = 0; i < NUM_OF_FREE_BUFFERS; i++) { + /* Get memory for DPRAM_DATA link list */ pdpram_blk = kmalloc(sizeof(struct dpram_blk), GFP_KERNEL); if (pdpram_blk == NULL) { ret_val = -ENOMEM; goto err_free; } - // Get a block of memory to store command data - pdpram_blk->pbuffer = kmalloc ( MAX_CMD_SQSIZE, GFP_KERNEL ); + /* Get a block of memory to store command data */ + pdpram_blk->pbuffer = kmalloc(MAX_CMD_SQSIZE, GFP_KERNEL); if (pdpram_blk->pbuffer == NULL) { ret_val = -ENOMEM; kfree(pdpram_blk); goto err_free; } - // link provisioning data - list_add_tail (&pdpram_blk->list, &freercvpool); - } - numofmsgbuf = NUM_OF_FREE_BUFFERS; - + /* link provisioning data */ + list_add_tail(&pdpram_blk->list, &freercvpool); + } + numofmsgbuf = NUM_OF_FREE_BUFFERS; return 0; - err_free: list_for_each_safe(cur, tmp, &freercvpool) { pdpram_blk = list_entry(cur, struct dpram_blk, list); @@ -898,1204 +772,833 @@ err_net: return ret_val; } - - -//--------------------------------------------------------------------------- -// Function: reg_ft1000_netdev -// -// Parameters: ft1000dev - device structure -// -// -// Returns: STATUS_SUCCESS - success -// STATUS_FAILURE - failure -// -// Description: This function register the network driver -// -// Notes: -// -//--------------------------------------------------------------------------- -int reg_ft1000_netdev(struct ft1000_device *ft1000dev, struct usb_interface *intf) +/* register the network driver */ +int reg_ft1000_netdev(struct ft1000_usb *ft1000dev, + struct usb_interface *intf) { - struct net_device *netdev; + struct net_device *netdev; struct ft1000_info *pInfo; int rc; - netdev = ft1000dev->net; - pInfo = netdev_priv(ft1000dev->net); - DEBUG("Enter reg_ft1000_netdev...\n"); - - - ft1000_read_register(ft1000dev, &pInfo->AsicID, FT1000_REG_ASIC_ID); + netdev = ft1000dev->net; + pInfo = netdev_priv(ft1000dev->net); + DEBUG("Enter reg_ft1000_netdev...\n"); - usb_set_intfdata(intf, pInfo); - SET_NETDEV_DEV(netdev, &intf->dev); + ft1000_read_register(ft1000dev, &pInfo->AsicID, FT1000_REG_ASIC_ID); - rc = register_netdev(netdev); - if (rc) - { - DEBUG("reg_ft1000_netdev: could not register network device\n"); - free_netdev(netdev); - return rc; - } + usb_set_intfdata(intf, pInfo); + SET_NETDEV_DEV(netdev, &intf->dev); + rc = register_netdev(netdev); + if (rc) { + DEBUG("reg_ft1000_netdev: could not register network device\n"); + free_netdev(netdev); + return rc; + } - //Create character device, implemented by Jim - ft1000_create_dev(ft1000dev); - - DEBUG ("reg_ft1000_netdev returned\n"); + ft1000_create_dev(ft1000dev); - pInfo->CardReady = 1; + DEBUG("reg_ft1000_netdev returned\n"); + pInfo->CardReady = 1; return 0; } -static int ft1000_reset(struct net_device *dev) -{ - ft1000_reset_card(dev); - return 0; -} - -//--------------------------------------------------------------------------- -// Function: ft1000_usb_transmit_complete -// -// Parameters: urb - transmitted usb urb -// -// -// Returns: none -// -// Description: This is the callback function when a urb is transmitted -// -// Notes: -// -//--------------------------------------------------------------------------- -static void ft1000_usb_transmit_complete(struct urb *urb) -{ - - struct ft1000_device *ft1000dev = urb->context; - - //DEBUG("ft1000_usb_transmit_complete entered\n"); - - if (urb->status) - printk("%s: TX status %d\n", ft1000dev->net->name, urb->status); - - netif_wake_queue(ft1000dev->net); - - //DEBUG("Return from ft1000_usb_transmit_complete\n"); -} - -//--------------------------------------------------------------------------- -// -// Function: ft1000_copy_down_pkt -// Descripton: This function will take an ethernet packet and convert it to -// a Flarion packet prior to sending it to the ASIC Downlink -// FIFO. -// Input: -// dev - device structure -// packet - address of ethernet packet -// len - length of IP packet -// Output: -// status - FAILURE -// SUCCESS -// -//--------------------------------------------------------------------------- -static int ft1000_copy_down_pkt (struct net_device *netdev, u8 *packet, u16 len) +/* take a packet from the FIFO up link and +* convert it into an ethernet packet and deliver it to the IP stack +*/ +static int ft1000_copy_up_pkt(struct urb *urb) { - struct ft1000_info *pInfo = netdev_priv(netdev); - struct ft1000_device *pFt1000Dev = pInfo->pFt1000Dev; - - - int count, ret; - u8 *t; - struct pseudo_hdr hdr; - - if (!pInfo->CardReady) - { - - DEBUG("ft1000_copy_down_pkt::Card Not Ready\n"); - return -ENODEV; - - } - + struct ft1000_info *info = urb->context; + struct ft1000_usb *ft1000dev = info->priv; + struct net_device *net = ft1000dev->net; + + u16 tempword; + u16 len; + u16 lena; + struct sk_buff *skb; + u16 i; + u8 *pbuffer = NULL; + u8 *ptemp = NULL; + u16 *chksum; + + if (ft1000dev->status & FT1000_STATUS_CLOSING) { + DEBUG("network driver is closed, return\n"); + return 0; + } + /* Read length */ + len = urb->transfer_buffer_length; + lena = urb->actual_length; - //DEBUG("ft1000_copy_down_pkt() entered, len = %d\n", len); + chksum = (u16 *) ft1000dev->rx_buf; - count = sizeof(struct pseudo_hdr) + len; - if(count > MAX_BUF_SIZE) - { - DEBUG("Error:ft1000_copy_down_pkt:Message Size Overflow!\n"); - DEBUG("size = %d\n", count); - return -EINVAL; - } + tempword = *chksum++; + for (i = 1; i < 7; i++) + tempword ^= *chksum++; - if ( count % 4) - count = count + (4- (count %4) ); + if (tempword != *chksum) { + info->stats.rx_errors++; + ft1000_submit_rx_urb(info); + return -1; + } - memset(&hdr, 0, sizeof(struct pseudo_hdr)); + skb = dev_alloc_skb(len + 12 + 2); - hdr.length = ntohs(count); - hdr.source = 0x10; - hdr.destination = 0x20; - hdr.portdest = 0x20; - hdr.portsrc = 0x10; - hdr.sh_str_id = 0x91; - hdr.control = 0x00; - - hdr.checksum = hdr.length ^ hdr.source ^ hdr.destination ^ - hdr.portdest ^ hdr.portsrc ^ hdr.sh_str_id ^ - hdr.control; + if (skb == NULL) { + DEBUG("ft1000_copy_up_pkt: No Network buffers available\n"); + info->stats.rx_errors++; + ft1000_submit_rx_urb(info); + return -1; + } - memcpy(&pFt1000Dev->tx_buf[0], &hdr, sizeof(hdr)); - memcpy(&(pFt1000Dev->tx_buf[sizeof(struct pseudo_hdr)]), packet, len); + pbuffer = (u8 *) skb_put(skb, len + 12); - netif_stop_queue(netdev); + /* subtract the number of bytes read already */ + ptemp = pbuffer; - //DEBUG ("ft1000_copy_down_pkt: count = %d\n", count); + /* fake MAC address */ + *pbuffer++ = net->dev_addr[0]; + *pbuffer++ = net->dev_addr[1]; + *pbuffer++ = net->dev_addr[2]; + *pbuffer++ = net->dev_addr[3]; + *pbuffer++ = net->dev_addr[4]; + *pbuffer++ = net->dev_addr[5]; + *pbuffer++ = 0x00; + *pbuffer++ = 0x07; + *pbuffer++ = 0x35; + *pbuffer++ = 0xff; + *pbuffer++ = 0xff; + *pbuffer++ = 0xfe; - usb_fill_bulk_urb(pFt1000Dev->tx_urb, - pFt1000Dev->dev, - usb_sndbulkpipe(pFt1000Dev->dev, pFt1000Dev->bulk_out_endpointAddr), - pFt1000Dev->tx_buf, - count, - ft1000_usb_transmit_complete, - (void*)pFt1000Dev); + memcpy(pbuffer, ft1000dev->rx_buf + sizeof(struct pseudo_hdr), + len - sizeof(struct pseudo_hdr)); - t = (u8 *)pFt1000Dev->tx_urb->transfer_buffer; - //DEBUG("transfer_length=%d\n", pFt1000Dev->tx_urb->transfer_buffer_length); - /*for (i=0; i<count; i++ ) - { - DEBUG("%x ", *t++ ); - }*/ + skb->dev = net; + skb->protocol = eth_type_trans(skb, net); + skb->ip_summed = CHECKSUM_UNNECESSARY; + netif_rx(skb); - ret = usb_submit_urb(pFt1000Dev->tx_urb, GFP_ATOMIC); - if (ret) { - DEBUG("ft1000 failed tx_urb %d\n", ret); - return ret; - } else { - pInfo->stats.tx_packets++; - pInfo->stats.tx_bytes += (len+14); - } + info->stats.rx_packets++; + /* Add on 12 bytes for MAC address which was removed */ + info->stats.rx_bytes += (lena + 12); - //DEBUG("ft1000_copy_down_pkt() exit\n"); + ft1000_submit_rx_urb(info); return 0; } -//--------------------------------------------------------------------------- -// Function: ft1000_start_xmit -// -// Parameters: skb - socket buffer to be sent -// dev - network device -// -// -// Returns: none -// -// Description: transmit a ethernet packet -// -// Notes: -// -//--------------------------------------------------------------------------- -static int ft1000_start_xmit(struct sk_buff *skb, struct net_device *dev) -{ - struct ft1000_info *pInfo = netdev_priv(dev); - struct ft1000_device *pFt1000Dev= pInfo->pFt1000Dev; - u8 *pdata; - int maxlen, pipe; - - - //DEBUG(" ft1000_start_xmit() entered\n"); - if ( skb == NULL ) - { - DEBUG ("ft1000_hw: ft1000_start_xmit:skb == NULL!!!\n" ); - return NETDEV_TX_OK; - } - - if ( pFt1000Dev->status & FT1000_STATUS_CLOSING) - { - DEBUG("network driver is closed, return\n"); - goto err; - } - - //DEBUG("ft1000_start_xmit 1:length of packet = %d\n", skb->len); - pipe = usb_sndbulkpipe(pFt1000Dev->dev, pFt1000Dev->bulk_out_endpointAddr); - maxlen = usb_maxpacket(pFt1000Dev->dev, pipe, usb_pipeout(pipe)); - //DEBUG("ft1000_start_xmit 2: pipe=%d dev->maxpacket = %d\n", pipe, maxlen); - - pdata = (u8 *)skb->data; - /*for (i=0; i<skb->len; i++) - DEBUG("skb->data[%d]=%x ", i, *(skb->data+i)); - - DEBUG("\n");*/ - - - if (pInfo->mediastate == 0) - { - /* Drop packet is mediastate is down */ - DEBUG("ft1000_hw:ft1000_start_xmit:mediastate is down\n"); - goto err; - } - - if ( (skb->len < ENET_HEADER_SIZE) || (skb->len > ENET_MAX_SIZE) ) - { - /* Drop packet which has invalid size */ - DEBUG("ft1000_hw:ft1000_start_xmit:invalid ethernet length\n"); - goto err; - } -//mbelian - ft1000_copy_down_pkt(dev, (pdata+ENET_HEADER_SIZE-2), - skb->len - ENET_HEADER_SIZE + 2); - -err: - dev_kfree_skb(skb); - //DEBUG(" ft1000_start_xmit() exit\n"); - - return NETDEV_TX_OK; -} - -//--------------------------------------------------------------------------- -// -// Function: ft1000_copy_up_pkt -// Descripton: This function will take a packet from the FIFO up link and -// convert it into an ethernet packet and deliver it to the IP stack -// Input: -// urb - the receving usb urb -// -// Output: -// status - FAILURE -// SUCCESS -// -//--------------------------------------------------------------------------- -static int ft1000_copy_up_pkt (struct urb *urb) +/* the receiving function of the network driver */ +static int ft1000_submit_rx_urb(struct ft1000_info *info) { - struct ft1000_info *info = urb->context; - struct ft1000_device *ft1000dev = info->pFt1000Dev; - struct net_device *net = ft1000dev->net; + int result; + struct ft1000_usb *pFt1000Dev = info->priv; - u16 tempword; - u16 len; - u16 lena; //mbelian - struct sk_buff *skb; - u16 i; - u8 *pbuffer=NULL; - u8 *ptemp=NULL; - u16 *chksum; - - - //DEBUG("ft1000_copy_up_pkt entered\n"); - - if ( ft1000dev->status & FT1000_STATUS_CLOSING) - { - DEBUG("network driver is closed, return\n"); - return STATUS_SUCCESS; - } - - // Read length - len = urb->transfer_buffer_length; - lena = urb->actual_length; //mbelian - //DEBUG("ft1000_copy_up_pkt: transfer_buffer_length=%d, actual_buffer_len=%d\n", - // urb->transfer_buffer_length, urb->actual_length); - - chksum = (u16 *)ft1000dev->rx_buf; - - tempword = *chksum++; - for (i=1; i<7; i++) - { - tempword ^= *chksum++; - } - - if (tempword != *chksum) - { - info->stats.rx_errors ++; - ft1000_submit_rx_urb(info); - return STATUS_FAILURE; - } - - - //DEBUG("ft1000_copy_up_pkt: checksum is correct %x\n", *chksum); - - skb = dev_alloc_skb(len+12+2); - - if (skb == NULL) - { - DEBUG("ft1000_copy_up_pkt: No Network buffers available\n"); - info->stats.rx_errors++; - ft1000_submit_rx_urb(info); - return STATUS_FAILURE; - } - - pbuffer = (u8 *)skb_put(skb, len+12); - - //subtract the number of bytes read already - ptemp = pbuffer; - - // fake MAC address - *pbuffer++ = net->dev_addr[0]; - *pbuffer++ = net->dev_addr[1]; - *pbuffer++ = net->dev_addr[2]; - *pbuffer++ = net->dev_addr[3]; - *pbuffer++ = net->dev_addr[4]; - *pbuffer++ = net->dev_addr[5]; - *pbuffer++ = 0x00; - *pbuffer++ = 0x07; - *pbuffer++ = 0x35; - *pbuffer++ = 0xff; - *pbuffer++ = 0xff; - *pbuffer++ = 0xfe; - - - - - memcpy(pbuffer, ft1000dev->rx_buf+sizeof(struct pseudo_hdr), len-sizeof(struct pseudo_hdr)); - - //DEBUG("ft1000_copy_up_pkt: Data passed to Protocol layer\n"); - /*for (i=0; i<len+12; i++) - { - DEBUG("ft1000_copy_up_pkt: Protocol Data: 0x%x\n ", *ptemp++); - }*/ + if (pFt1000Dev->status & FT1000_STATUS_CLOSING) { + DEBUG("network driver is closed, return\n"); + return -ENODEV; + } - skb->dev = net; + usb_fill_bulk_urb(pFt1000Dev->rx_urb, + pFt1000Dev->dev, + usb_rcvbulkpipe(pFt1000Dev->dev, + pFt1000Dev->bulk_in_endpointAddr), + pFt1000Dev->rx_buf, MAX_BUF_SIZE, + (usb_complete_t) ft1000_copy_up_pkt, info); - skb->protocol = eth_type_trans(skb, net); - skb->ip_summed = CHECKSUM_UNNECESSARY; - netif_rx(skb); + result = usb_submit_urb(pFt1000Dev->rx_urb, GFP_ATOMIC); - info->stats.rx_packets++; - // Add on 12 bytes for MAC address which was removed - info->stats.rx_bytes += (lena+12); //mbelian + if (result) { + pr_err("ft1000_submit_rx_urb: submitting rx_urb %d failed\n", + result); + return result; + } - ft1000_submit_rx_urb(info); - //DEBUG("ft1000_copy_up_pkt exited\n"); - return SUCCESS; + return 0; } -//--------------------------------------------------------------------------- -// -// Function: ft1000_submit_rx_urb -// Descripton: the receiving function of the network driver -// -// Input: -// info - a private structure contains the device information -// -// Output: -// status - FAILURE -// SUCCESS -// -//--------------------------------------------------------------------------- -static int ft1000_submit_rx_urb(struct ft1000_info *info) +/* close the network driver */ +int ft1000_close(struct net_device *net) { - int result; - struct ft1000_device *pFt1000Dev = info->pFt1000Dev; - - - //DEBUG ("ft1000_submit_rx_urb entered: sizeof rx_urb is %d\n", sizeof(*pFt1000Dev->rx_urb)); - if ( pFt1000Dev->status & FT1000_STATUS_CLOSING) - { - DEBUG("network driver is closed, return\n"); - //usb_kill_urb(pFt1000Dev->rx_urb); //mbelian - return -ENODEV; - } - - usb_fill_bulk_urb(pFt1000Dev->rx_urb, - pFt1000Dev->dev, - usb_rcvbulkpipe(pFt1000Dev->dev, pFt1000Dev->bulk_in_endpointAddr), - pFt1000Dev->rx_buf, - MAX_BUF_SIZE, - (usb_complete_t)ft1000_copy_up_pkt, - info); + struct ft1000_info *pInfo = netdev_priv(net); + struct ft1000_usb *ft1000dev = pInfo->priv; + ft1000dev->status |= FT1000_STATUS_CLOSING; - if((result = usb_submit_urb(pFt1000Dev->rx_urb, GFP_ATOMIC))) - { - printk("ft1000_submit_rx_urb: submitting rx_urb %d failed\n", result); - return result; - } + DEBUG("ft1000_close: pInfo=%p, ft1000dev=%p\n", pInfo, ft1000dev); + netif_carrier_off(net); + netif_stop_queue(net); + ft1000dev->status &= ~FT1000_STATUS_CLOSING; - //DEBUG("ft1000_submit_rx_urb exit: result=%d\n", result); + pInfo->ProgConStat = 0xff; return 0; } -//--------------------------------------------------------------------------- -// Function: ft1000_open -// -// Parameters: -// dev - network device -// -// -// Returns: none -// -// Description: open the network driver -// -// Notes: -// -//--------------------------------------------------------------------------- -static int ft1000_open (struct net_device *dev) +/* check if the device is presently available on the system. */ +static int ft1000_chkcard(struct ft1000_usb *dev) { - struct ft1000_info *pInfo = netdev_priv(dev); - struct timeval tv; //mbelian - int ret; + u16 tempword; + int status; - DEBUG("ft1000_open is called for card %d\n", pInfo->CardNumber); - //DEBUG("ft1000_open: dev->addr=%x, dev->addr_len=%d\n", dev->addr, dev->addr_len); - - pInfo->stats.rx_bytes = 0; //mbelian - pInfo->stats.tx_bytes = 0; //mbelian - pInfo->stats.rx_packets = 0; //mbelian - pInfo->stats.tx_packets = 0; //mbelian - do_gettimeofday(&tv); - pInfo->ConTm = tv.tv_sec; - pInfo->ProgConStat = 0; //mbelian - - - netif_start_queue(dev); - - netif_carrier_on(dev); //mbelian - - ret = ft1000_submit_rx_urb(pInfo); - - return ret; + if (dev->fCondResetPend) { + DEBUG("ft1000_hw:ft1000_chkcard:Card is being reset, return FALSE\n"); + return TRUE; + } + /* Mask register is used to check for device presence since it is never + * set to zero. + */ + status = ft1000_read_register(dev, &tempword, FT1000_REG_SUP_IMASK); + if (tempword == 0) { + DEBUG("ft1000_hw:ft1000_chkcard: IMASK = 0 Card not detected\n"); + return FALSE; + } + /* The system will return the value of 0xffff for the version register + * if the device is not present. + */ + status = ft1000_read_register(dev, &tempword, FT1000_REG_ASIC_ID); + if (tempword != 0x1b01) { + dev->status |= FT1000_STATUS_CLOSING; + DEBUG("ft1000_hw:ft1000_chkcard: Version = 0xffff Card not detected\n"); + return FALSE; + } + return TRUE; } -//--------------------------------------------------------------------------- -// Function: ft1000_close -// -// Parameters: -// net - network device -// -// -// Returns: none -// -// Description: close the network driver -// -// Notes: -// -//--------------------------------------------------------------------------- -int ft1000_close(struct net_device *net) +/* read a message from the dpram area. +* Input: +* dev - network device structure +* pbuffer - caller supply address to buffer +*/ +static bool ft1000_receive_cmd(struct ft1000_usb *dev, u16 *pbuffer, + int maxsz) { - struct ft1000_info *pInfo = netdev_priv(net); - struct ft1000_device *ft1000dev = pInfo->pFt1000Dev; - - //DEBUG ("ft1000_close: netdev->refcnt=%d\n", net->refcnt); - - ft1000dev->status |= FT1000_STATUS_CLOSING; - - //DEBUG("ft1000_close: calling usb_kill_urb \n"); - - DEBUG("ft1000_close: pInfo=%p, ft1000dev=%p\n", pInfo, ft1000dev); - netif_carrier_off(net);//mbelian - netif_stop_queue(net); - //DEBUG("ft1000_close: netif_stop_queue called\n"); - ft1000dev->status &= ~FT1000_STATUS_CLOSING; - - pInfo->ProgConStat = 0xff; //mbelian + u16 size; + int ret; + u16 *ppseudohdr; + int i; + u16 tempword; + + ret = + ft1000_read_dpram16(dev, FT1000_MAG_PH_LEN, (u8 *) &size, + FT1000_MAG_PH_LEN_INDX); + size = ntohs(size) + PSEUDOSZ; + if (size > maxsz) { + DEBUG("FT1000:ft1000_receive_cmd:Invalid command length = %d\n", + size); + return FALSE; + } else { + ppseudohdr = (u16 *) pbuffer; + ft1000_write_register(dev, FT1000_DPRAM_MAG_RX_BASE, + FT1000_REG_DPRAM_ADDR); + ret = + ft1000_read_register(dev, pbuffer, FT1000_REG_MAG_DPDATAH); + pbuffer++; + ft1000_write_register(dev, FT1000_DPRAM_MAG_RX_BASE + 1, + FT1000_REG_DPRAM_ADDR); + for (i = 0; i <= (size >> 2); i++) { + ret = + ft1000_read_register(dev, pbuffer, + FT1000_REG_MAG_DPDATAL); + pbuffer++; + ret = + ft1000_read_register(dev, pbuffer, + FT1000_REG_MAG_DPDATAH); + pbuffer++; + } + /* copy odd aligned word */ + ret = + ft1000_read_register(dev, pbuffer, FT1000_REG_MAG_DPDATAL); + + pbuffer++; + ret = + ft1000_read_register(dev, pbuffer, FT1000_REG_MAG_DPDATAH); + + pbuffer++; + if (size & 0x0001) { + /* copy odd byte from fifo */ + ret = + ft1000_read_register(dev, &tempword, + FT1000_REG_DPRAM_DATA); + *pbuffer = ntohs(tempword); + } + /* Check if pseudo header checksum is good + * Calculate pseudo header checksum + */ + tempword = *ppseudohdr++; + for (i = 1; i < 7; i++) + tempword ^= *ppseudohdr++; + if ((tempword != *ppseudohdr)) + return FALSE; - return 0; + return TRUE; + } } -static struct net_device_stats *ft1000_netdev_stats(struct net_device *dev) +static int ft1000_dsp_prov(void *arg) { - struct ft1000_info *info = netdev_priv(dev); - - return &(info->stats); //mbelian -} + struct ft1000_usb *dev = (struct ft1000_usb *)arg; + struct ft1000_info *info = netdev_priv(dev->net); + u16 tempword; + u16 len; + u16 i = 0; + struct prov_record *ptr; + struct pseudo_hdr *ppseudo_hdr; + u16 *pmsg; + int status; + u16 TempShortBuf[256]; + + DEBUG("*** DspProv Entered\n"); + + while (list_empty(&info->prov_list) == 0) { + DEBUG("DSP Provisioning List Entry\n"); + + /* Check if doorbell is available */ + DEBUG("check if doorbell is cleared\n"); + status = + ft1000_read_register(dev, &tempword, FT1000_REG_DOORBELL); + if (status) { + DEBUG("ft1000_dsp_prov::ft1000_read_register error\n"); + break; + } + while (tempword & FT1000_DB_DPRAM_TX) { + mdelay(10); + i++; + if (i == 10) { + DEBUG("FT1000:ft1000_dsp_prov:message drop\n"); + return -1; + } + ft1000_read_register(dev, &tempword, + FT1000_REG_DOORBELL); + } -/********************************************************************************* -Jim -*/ + if (!(tempword & FT1000_DB_DPRAM_TX)) { + DEBUG("*** Provision Data Sent to DSP\n"); + /* Send provisioning data */ + ptr = + list_entry(info->prov_list.next, struct prov_record, + list); + len = *(u16 *) ptr->pprov_data; + len = htons(len); + len += PSEUDOSZ; -//--------------------------------------------------------------------------- -// -// Function: ft1000_chkcard -// Descripton: This function will check if the device is presently available on -// the system. -// Input: -// dev - device structure -// Output: -// status - FALSE (device is not present) -// TRUE (device is present) -// -//--------------------------------------------------------------------------- -static int ft1000_chkcard (struct ft1000_device *dev) { - u16 tempword; - u16 status; - struct ft1000_info *info = netdev_priv(dev->net); + pmsg = (u16 *) ptr->pprov_data; + ppseudo_hdr = (struct pseudo_hdr *)pmsg; + /* Insert slow queue sequence number */ + ppseudo_hdr->seq_num = info->squeseqnum++; + ppseudo_hdr->portsrc = 0; + /* Calculate new checksum */ + ppseudo_hdr->checksum = *pmsg++; + for (i = 1; i < 7; i++) + ppseudo_hdr->checksum ^= *pmsg++; + + TempShortBuf[0] = 0; + TempShortBuf[1] = htons(len); + memcpy(&TempShortBuf[2], ppseudo_hdr, len); + + status = + ft1000_write_dpram32(dev, 0, + (u8 *) &TempShortBuf[0], + (unsigned short)(len + 2)); + status = + ft1000_write_register(dev, FT1000_DB_DPRAM_TX, + FT1000_REG_DOORBELL); + + list_del(&ptr->list); + kfree(ptr->pprov_data); + kfree(ptr); + } + usleep_range(9000, 11000); + } - if (info->fCondResetPend) - { - DEBUG("ft1000_hw:ft1000_chkcard:Card is being reset, return FALSE\n"); - return TRUE; - } - - // Mask register is used to check for device presence since it is never - // set to zero. - status = ft1000_read_register(dev, &tempword, FT1000_REG_SUP_IMASK); - //DEBUG("ft1000_hw:ft1000_chkcard: read FT1000_REG_SUP_IMASK = %x\n", tempword); - if (tempword == 0) { - DEBUG("ft1000_hw:ft1000_chkcard: IMASK = 0 Card not detected\n"); - return FALSE; - } - - // The system will return the value of 0xffff for the version register - // if the device is not present. - status = ft1000_read_register(dev, &tempword, FT1000_REG_ASIC_ID); - //DEBUG("ft1000_hw:ft1000_chkcard: read FT1000_REG_ASIC_ID = %x\n", tempword); - if (tempword != 0x1b01 ){ - dev->status |= FT1000_STATUS_CLOSING; //mbelian - DEBUG("ft1000_hw:ft1000_chkcard: Version = 0xffff Card not detected\n"); - return FALSE; - } - return TRUE; -} + DEBUG("DSP Provisioning List Entry finished\n"); + msleep(100); + dev->fProvComplete = true; + info->CardReady = 1; -//--------------------------------------------------------------------------- -// -// Function: ft1000_receive_cmd -// Descripton: This function will read a message from the dpram area. -// Input: -// dev - network device structure -// pbuffer - caller supply address to buffer -// pnxtph - pointer to next pseudo header -// Output: -// Status = 0 (unsuccessful) -// = 1 (successful) -// -//--------------------------------------------------------------------------- -static bool ft1000_receive_cmd (struct ft1000_device *dev, u16 *pbuffer, int maxsz, u16 *pnxtph) { - u16 size, ret; - u16 *ppseudohdr; - int i; - u16 tempword; - - ret = ft1000_read_dpram16(dev, FT1000_MAG_PH_LEN, (u8 *)&size, FT1000_MAG_PH_LEN_INDX); - size = ntohs(size) + PSEUDOSZ; - if (size > maxsz) { - DEBUG("FT1000:ft1000_receive_cmd:Invalid command length = %d\n", size); - return FALSE; - } - else { - ppseudohdr = (u16 *)pbuffer; - ft1000_write_register(dev, FT1000_DPRAM_MAG_RX_BASE, FT1000_REG_DPRAM_ADDR); - ret = ft1000_read_register(dev, pbuffer, FT1000_REG_MAG_DPDATAH); - //DEBUG("ft1000_hw:received data = 0x%x\n", *pbuffer); - pbuffer++; - ft1000_write_register(dev, FT1000_DPRAM_MAG_RX_BASE+1, FT1000_REG_DPRAM_ADDR); - for (i=0; i<=(size>>2); i++) { - ret = ft1000_read_register(dev, pbuffer, FT1000_REG_MAG_DPDATAL); - pbuffer++; - ret = ft1000_read_register(dev, pbuffer, FT1000_REG_MAG_DPDATAH); - pbuffer++; - } - //copy odd aligned word - ret = ft1000_read_register(dev, pbuffer, FT1000_REG_MAG_DPDATAL); - //DEBUG("ft1000_hw:received data = 0x%x\n", *pbuffer); - pbuffer++; - ret = ft1000_read_register(dev, pbuffer, FT1000_REG_MAG_DPDATAH); - //DEBUG("ft1000_hw:received data = 0x%x\n", *pbuffer); - pbuffer++; - if (size & 0x0001) { - //copy odd byte from fifo - ret = ft1000_read_register(dev, &tempword, FT1000_REG_DPRAM_DATA); - *pbuffer = ntohs(tempword); - } - - // Check if pseudo header checksum is good - // Calculate pseudo header checksum - tempword = *ppseudohdr++; - for (i=1; i<7; i++) { - tempword ^= *ppseudohdr++; - } - if ( (tempword != *ppseudohdr) ) { - return FALSE; - } - - return TRUE; - } + return 0; } - -static int ft1000_dsp_prov(void *arg) +static int ft1000_proc_drvmsg(struct ft1000_usb *dev, u16 size) { - struct ft1000_device *dev = (struct ft1000_device *)arg; struct ft1000_info *info = netdev_priv(dev->net); - u16 tempword; - u16 len; - u16 i=0; - struct prov_record *ptr; - struct pseudo_hdr *ppseudo_hdr; - u16 *pmsg; - u16 status; - u16 TempShortBuf [256]; - - DEBUG("*** DspProv Entered\n"); - - while (list_empty(&info->prov_list) == 0) - { - DEBUG("DSP Provisioning List Entry\n"); - - // Check if doorbell is available - DEBUG("check if doorbell is cleared\n"); - status = ft1000_read_register (dev, &tempword, FT1000_REG_DOORBELL); - if (status) - { - DEBUG("ft1000_dsp_prov::ft1000_read_register error\n"); - break; - } - - while (tempword & FT1000_DB_DPRAM_TX) { - mdelay(10); - i++; - if (i==10) { - DEBUG("FT1000:ft1000_dsp_prov:message drop\n"); - return STATUS_FAILURE; - } - ft1000_read_register(dev, &tempword, FT1000_REG_DOORBELL); - } - - if ( !(tempword & FT1000_DB_DPRAM_TX) ) { - DEBUG("*** Provision Data Sent to DSP\n"); - - // Send provisioning data - ptr = list_entry(info->prov_list.next, struct prov_record, list); - len = *(u16 *)ptr->pprov_data; - len = htons(len); - len += PSEUDOSZ; - - pmsg = (u16 *)ptr->pprov_data; - ppseudo_hdr = (struct pseudo_hdr *)pmsg; - // Insert slow queue sequence number - ppseudo_hdr->seq_num = info->squeseqnum++; - ppseudo_hdr->portsrc = 0; - // Calculate new checksum - ppseudo_hdr->checksum = *pmsg++; - //DEBUG("checksum = 0x%x\n", ppseudo_hdr->checksum); - for (i=1; i<7; i++) { - ppseudo_hdr->checksum ^= *pmsg++; - //DEBUG("checksum = 0x%x\n", ppseudo_hdr->checksum); - } - - TempShortBuf[0] = 0; - TempShortBuf[1] = htons (len); - memcpy(&TempShortBuf[2], ppseudo_hdr, len); - - status = ft1000_write_dpram32 (dev, 0, (u8 *)&TempShortBuf[0], (unsigned short)(len+2)); - status = ft1000_write_register (dev, FT1000_DB_DPRAM_TX, FT1000_REG_DOORBELL); - - list_del(&ptr->list); - kfree(ptr->pprov_data); - kfree(ptr); - } - msleep(10); - } - - DEBUG("DSP Provisioning List Entry finished\n"); - - msleep(100); - - info->fProvComplete = 1; - info->CardReady = 1; - return STATUS_SUCCESS; - -} - - -static int ft1000_proc_drvmsg (struct ft1000_device *dev, u16 size) { - struct ft1000_info *info = netdev_priv(dev->net); - u16 msgtype; - u16 tempword; + u16 msgtype; + u16 tempword; struct media_msg *pmediamsg; struct dsp_init_msg *pdspinitmsg; struct drv_msg *pdrvmsg; - u16 i; + u16 i; struct pseudo_hdr *ppseudo_hdr; - u16 *pmsg; - u16 status; - union { - u8 byte[2]; - u16 wrd; - } convert; - - - char *cmdbuffer = kmalloc(1600, GFP_KERNEL); - if (!cmdbuffer) - return STATUS_FAILURE; - - status = ft1000_read_dpram32(dev, 0x200, cmdbuffer, size); + u16 *pmsg; + int status; + union { + u8 byte[2]; + u16 wrd; + } convert; + char *cmdbuffer = kmalloc(1600, GFP_KERNEL); + if (!cmdbuffer) + return -ENOMEM; + status = ft1000_read_dpram32(dev, 0x200, cmdbuffer, size); #ifdef JDEBUG - DEBUG("ft1000_proc_drvmsg:cmdbuffer\n"); - for(i = 0; i < size; i+=5) - { - if( (i + 5) < size ) - DEBUG("0x%x, 0x%x, 0x%x, 0x%x, 0x%x\n", cmdbuffer[i], cmdbuffer[i+1], cmdbuffer[i+2], cmdbuffer[i+3], cmdbuffer[i+4]); - else - { - for (j = i; j < size; j++) - DEBUG("0x%x ", cmdbuffer[j]); - DEBUG("\n"); - break; - } - } + DEBUG("ft1000_proc_drvmsg:cmdbuffer\n"); + for (i = 0; i < size; i += 5) { + if ((i + 5) < size) + DEBUG("0x%x, 0x%x, 0x%x, 0x%x, 0x%x\n", cmdbuffer[i], + cmdbuffer[i + 1], cmdbuffer[i + 2], + cmdbuffer[i + 3], cmdbuffer[i + 4]); + else { + for (j = i; j < size; j++) + DEBUG("0x%x ", cmdbuffer[j]); + DEBUG("\n"); + break; + } + } #endif pdrvmsg = (struct drv_msg *)&cmdbuffer[2]; - msgtype = ntohs(pdrvmsg->type); - DEBUG("ft1000_proc_drvmsg:Command message type = 0x%x\n", msgtype); - switch (msgtype) { - case MEDIA_STATE: { - DEBUG("ft1000_proc_drvmsg:Command message type = MEDIA_STATE"); - + msgtype = ntohs(pdrvmsg->type); + DEBUG("ft1000_proc_drvmsg:Command message type = 0x%x\n", msgtype); + switch (msgtype) { + case MEDIA_STATE:{ + DEBUG("ft1000_proc_drvmsg:Command message type = MEDIA_STATE"); pmediamsg = (struct media_msg *)&cmdbuffer[0]; - if (info->ProgConStat != 0xFF) { - if (pmediamsg->state) { - DEBUG("Media is up\n"); - if (info->mediastate == 0) { - if ( info->NetDevRegDone ) - { - //netif_carrier_on(dev->net);//mbelian - netif_wake_queue(dev->net); - } - info->mediastate = 1; - /*do_gettimeofday(&tv); - info->ConTm = tv.tv_sec;*/ //mbelian - } - } - else { - DEBUG("Media is down\n"); - if (info->mediastate == 1) { - info->mediastate = 0; - if ( info->NetDevRegDone ) - { - //netif_carrier_off(dev->net); mbelian - //netif_stop_queue(dev->net); - } - info->ConTm = 0; - } - } - } - else { - DEBUG("Media is down\n"); - if (info->mediastate == 1) { - info->mediastate = 0; - if ( info->NetDevRegDone) - { - //netif_carrier_off(dev->net); //mbelian - //netif_stop_queue(dev->net); - } - info->ConTm = 0; - } - } - break; - } - case DSP_INIT_MSG: { - DEBUG("ft1000_proc_drvmsg:Command message type = DSP_INIT_MSG"); - + if (info->ProgConStat != 0xFF) { + if (pmediamsg->state) { + DEBUG("Media is up\n"); + if (info->mediastate == 0) { + if (dev->NetDevRegDone) + netif_wake_queue(dev->net); + info->mediastate = 1; + } + } else { + DEBUG("Media is down\n"); + if (info->mediastate == 1) { + info->mediastate = 0; + if (dev->NetDevRegDone) + info->ConTm = 0; + } + } + } else { + DEBUG("Media is down\n"); + if (info->mediastate == 1) { + info->mediastate = 0; + info->ConTm = 0; + } + } + break; + } + case DSP_INIT_MSG:{ + DEBUG("ft1000_proc_drvmsg:Command message type = DSP_INIT_MSG"); pdspinitmsg = (struct dsp_init_msg *)&cmdbuffer[2]; - memcpy(info->DspVer, pdspinitmsg->DspVer, DSPVERSZ); - DEBUG("DSPVER = 0x%2x 0x%2x 0x%2x 0x%2x\n", info->DspVer[0], info->DspVer[1], info->DspVer[2], info->DspVer[3]); - memcpy(info->HwSerNum, pdspinitmsg->HwSerNum, HWSERNUMSZ); - memcpy(info->Sku, pdspinitmsg->Sku, SKUSZ); - memcpy(info->eui64, pdspinitmsg->eui64, EUISZ); - DEBUG("EUI64=%2x.%2x.%2x.%2x.%2x.%2x.%2x.%2x\n", info->eui64[0],info->eui64[1], info->eui64[2], info->eui64[3], info->eui64[4], info->eui64[5],info->eui64[6], info->eui64[7]); - dev->net->dev_addr[0] = info->eui64[0]; - dev->net->dev_addr[1] = info->eui64[1]; - dev->net->dev_addr[2] = info->eui64[2]; - dev->net->dev_addr[3] = info->eui64[5]; - dev->net->dev_addr[4] = info->eui64[6]; - dev->net->dev_addr[5] = info->eui64[7]; - - if (ntohs(pdspinitmsg->length) == (sizeof(struct dsp_init_msg) - 20)) { - memcpy(info->ProductMode, pdspinitmsg->ProductMode, MODESZ); - memcpy(info->RfCalVer, pdspinitmsg->RfCalVer, CALVERSZ); - memcpy(info->RfCalDate, pdspinitmsg->RfCalDate, CALDATESZ); - DEBUG("RFCalVer = 0x%2x 0x%2x\n", info->RfCalVer[0], info->RfCalVer[1]); - } - break; - } - case DSP_PROVISION: { - DEBUG("ft1000_proc_drvmsg:Command message type = DSP_PROVISION\n"); - - // kick off dspprov routine to start provisioning - // Send provisioning data to DSP - if (list_empty(&info->prov_list) == 0) - { - info->fProvComplete = 0; - status = ft1000_dsp_prov(dev); - if (status != STATUS_SUCCESS) - goto out; - } - else { - info->fProvComplete = 1; - status = ft1000_write_register (dev, FT1000_DB_HB, FT1000_REG_DOORBELL); - DEBUG("FT1000:drivermsg:No more DSP provisioning data in dsp image\n"); - } - DEBUG("ft1000_proc_drvmsg:DSP PROVISION is done\n"); - break; - } - case DSP_STORE_INFO: { - DEBUG("ft1000_proc_drvmsg:Command message type = DSP_STORE_INFO"); - - DEBUG("FT1000:drivermsg:Got DSP_STORE_INFO\n"); - tempword = ntohs(pdrvmsg->length); - info->DSPInfoBlklen = tempword; - if (tempword < (MAX_DSP_SESS_REC-4) ) { - pmsg = (u16 *)&pdrvmsg->data[0]; - for (i=0; i<((tempword+1)/2); i++) { - DEBUG("FT1000:drivermsg:dsp info data = 0x%x\n", *pmsg); - info->DSPInfoBlk[i+10] = *pmsg++; - } - } - else { - info->DSPInfoBlklen = 0; - } - break; - } - case DSP_GET_INFO: { - DEBUG("FT1000:drivermsg:Got DSP_GET_INFO\n"); - // copy dsp info block to dsp - info->DrvMsgPend = 1; - // allow any outstanding ioctl to finish - mdelay(10); - status = ft1000_read_register(dev, &tempword, FT1000_REG_DOORBELL); - if (tempword & FT1000_DB_DPRAM_TX) { - mdelay(10); - status = ft1000_read_register(dev, &tempword, FT1000_REG_DOORBELL); - if (tempword & FT1000_DB_DPRAM_TX) { - mdelay(10); - status = ft1000_read_register(dev, &tempword, FT1000_REG_DOORBELL); - if (tempword & FT1000_DB_DPRAM_TX) { - break; - } - } - } - - // Put message into Slow Queue - // Form Pseudo header - pmsg = (u16 *)info->DSPInfoBlk; - *pmsg++ = 0; - *pmsg++ = htons(info->DSPInfoBlklen+20+info->DSPInfoBlklen); - ppseudo_hdr = (struct pseudo_hdr *)(u16 *)&info->DSPInfoBlk[2]; - ppseudo_hdr->length = htons(info->DSPInfoBlklen+4+info->DSPInfoBlklen); - ppseudo_hdr->source = 0x10; - ppseudo_hdr->destination = 0x20; - ppseudo_hdr->portdest = 0; - ppseudo_hdr->portsrc = 0; - ppseudo_hdr->sh_str_id = 0; - ppseudo_hdr->control = 0; - ppseudo_hdr->rsvd1 = 0; - ppseudo_hdr->rsvd2 = 0; - ppseudo_hdr->qos_class = 0; - // Insert slow queue sequence number - ppseudo_hdr->seq_num = info->squeseqnum++; - // Insert application id - ppseudo_hdr->portsrc = 0; - // Calculate new checksum - ppseudo_hdr->checksum = *pmsg++; - for (i=1; i<7; i++) { - ppseudo_hdr->checksum ^= *pmsg++; - } - info->DSPInfoBlk[10] = 0x7200; - info->DSPInfoBlk[11] = htons(info->DSPInfoBlklen); - status = ft1000_write_dpram32 (dev, 0, (u8 *)&info->DSPInfoBlk[0], (unsigned short)(info->DSPInfoBlklen+22)); - status = ft1000_write_register (dev, FT1000_DB_DPRAM_TX, FT1000_REG_DOORBELL); - info->DrvMsgPend = 0; - - break; - } - - case GET_DRV_ERR_RPT_MSG: { - DEBUG("FT1000:drivermsg:Got GET_DRV_ERR_RPT_MSG\n"); - // copy driver error message to dsp - info->DrvMsgPend = 1; - // allow any outstanding ioctl to finish - mdelay(10); - status = ft1000_read_register(dev, &tempword, FT1000_REG_DOORBELL); - if (tempword & FT1000_DB_DPRAM_TX) { - mdelay(10); - status = ft1000_read_register(dev, &tempword, FT1000_REG_DOORBELL); - if (tempword & FT1000_DB_DPRAM_TX) { - mdelay(10); - } - } - - if ( (tempword & FT1000_DB_DPRAM_TX) == 0) { - // Put message into Slow Queue - // Form Pseudo header - pmsg = (u16 *)&tempbuffer[0]; + memcpy(info->DspVer, pdspinitmsg->DspVer, DSPVERSZ); + DEBUG("DSPVER = 0x%2x 0x%2x 0x%2x 0x%2x\n", + info->DspVer[0], info->DspVer[1], info->DspVer[2], + info->DspVer[3]); + memcpy(info->HwSerNum, pdspinitmsg->HwSerNum, + HWSERNUMSZ); + memcpy(info->Sku, pdspinitmsg->Sku, SKUSZ); + memcpy(info->eui64, pdspinitmsg->eui64, EUISZ); + DEBUG("EUI64=%2x.%2x.%2x.%2x.%2x.%2x.%2x.%2x\n", + info->eui64[0], info->eui64[1], info->eui64[2], + info->eui64[3], info->eui64[4], info->eui64[5], + info->eui64[6], info->eui64[7]); + dev->net->dev_addr[0] = info->eui64[0]; + dev->net->dev_addr[1] = info->eui64[1]; + dev->net->dev_addr[2] = info->eui64[2]; + dev->net->dev_addr[3] = info->eui64[5]; + dev->net->dev_addr[4] = info->eui64[6]; + dev->net->dev_addr[5] = info->eui64[7]; + + if (ntohs(pdspinitmsg->length) == + (sizeof(struct dsp_init_msg) - 20)) { + memcpy(info->ProductMode, pdspinitmsg->ProductMode, + MODESZ); + memcpy(info->RfCalVer, pdspinitmsg->RfCalVer, CALVERSZ); + memcpy(info->RfCalDate, pdspinitmsg->RfCalDate, + CALDATESZ); + DEBUG("RFCalVer = 0x%2x 0x%2x\n", info->RfCalVer[0], + info->RfCalVer[1]); + } + break; + } + case DSP_PROVISION:{ + DEBUG("ft1000_proc_drvmsg:Command message type = DSP_PROVISION\n"); + + /* kick off dspprov routine to start provisioning + * Send provisioning data to DSP + */ + if (list_empty(&info->prov_list) == 0) { + dev->fProvComplete = false; + status = ft1000_dsp_prov(dev); + if (status != 0) + goto out; + } else { + dev->fProvComplete = true; + status = ft1000_write_register(dev, FT1000_DB_HB, + FT1000_REG_DOORBELL); + DEBUG("FT1000:drivermsg:No more DSP provisioning data in dsp image\n"); + } + DEBUG("ft1000_proc_drvmsg:DSP PROVISION is done\n"); + break; + } + case DSP_STORE_INFO:{ + DEBUG("ft1000_proc_drvmsg:Command message type = DSP_STORE_INFO"); + DEBUG("FT1000:drivermsg:Got DSP_STORE_INFO\n"); + tempword = ntohs(pdrvmsg->length); + info->DSPInfoBlklen = tempword; + if (tempword < (MAX_DSP_SESS_REC - 4)) { + pmsg = (u16 *) &pdrvmsg->data[0]; + for (i = 0; i < ((tempword + 1) / 2); i++) { + DEBUG("FT1000:drivermsg:dsp info data = 0x%x\n", *pmsg); + info->DSPInfoBlk[i + 10] = *pmsg++; + } + } else { + info->DSPInfoBlklen = 0; + } + break; + } + case DSP_GET_INFO:{ + DEBUG("FT1000:drivermsg:Got DSP_GET_INFO\n"); + /* copy dsp info block to dsp */ + dev->DrvMsgPend = 1; + /* allow any outstanding ioctl to finish */ + mdelay(10); + status = ft1000_read_register(dev, &tempword, + FT1000_REG_DOORBELL); + if (tempword & FT1000_DB_DPRAM_TX) { + mdelay(10); + status = ft1000_read_register(dev, &tempword, + FT1000_REG_DOORBELL); + if (tempword & FT1000_DB_DPRAM_TX) { + mdelay(10); + status = ft1000_read_register(dev, &tempword, + FT1000_REG_DOORBELL); + if (tempword & FT1000_DB_DPRAM_TX) + break; + } + } + /* Put message into Slow Queue Form Pseudo header */ + pmsg = (u16 *) info->DSPInfoBlk; + *pmsg++ = 0; + *pmsg++ = htons(info->DSPInfoBlklen + 20 + info->DSPInfoBlklen); + ppseudo_hdr = + (struct pseudo_hdr *)(u16 *) &info->DSPInfoBlk[2]; + ppseudo_hdr->length = htons(info->DSPInfoBlklen + 4 + + info->DSPInfoBlklen); + ppseudo_hdr->source = 0x10; + ppseudo_hdr->destination = 0x20; + ppseudo_hdr->portdest = 0; + ppseudo_hdr->portsrc = 0; + ppseudo_hdr->sh_str_id = 0; + ppseudo_hdr->control = 0; + ppseudo_hdr->rsvd1 = 0; + ppseudo_hdr->rsvd2 = 0; + ppseudo_hdr->qos_class = 0; + /* Insert slow queue sequence number */ + ppseudo_hdr->seq_num = info->squeseqnum++; + /* Insert application id */ + ppseudo_hdr->portsrc = 0; + /* Calculate new checksum */ + ppseudo_hdr->checksum = *pmsg++; + for (i = 1; i < 7; i++) + ppseudo_hdr->checksum ^= *pmsg++; + + info->DSPInfoBlk[10] = 0x7200; + info->DSPInfoBlk[11] = htons(info->DSPInfoBlklen); + status = ft1000_write_dpram32(dev, 0, + (u8 *)&info->DSPInfoBlk[0], + (unsigned short)(info->DSPInfoBlklen + 22)); + status = ft1000_write_register(dev, FT1000_DB_DPRAM_TX, + FT1000_REG_DOORBELL); + dev->DrvMsgPend = 0; + break; + } + case GET_DRV_ERR_RPT_MSG:{ + DEBUG("FT1000:drivermsg:Got GET_DRV_ERR_RPT_MSG\n"); + /* copy driver error message to dsp */ + dev->DrvMsgPend = 1; + /* allow any outstanding ioctl to finish */ + mdelay(10); + status = ft1000_read_register(dev, &tempword, + FT1000_REG_DOORBELL); + if (tempword & FT1000_DB_DPRAM_TX) { + mdelay(10); + status = ft1000_read_register(dev, &tempword, + FT1000_REG_DOORBELL); + if (tempword & FT1000_DB_DPRAM_TX) + mdelay(10); + } + if ((tempword & FT1000_DB_DPRAM_TX) == 0) { + /* Put message into Slow Queue Form Pseudo header */ + pmsg = (u16 *) &tempbuffer[0]; ppseudo_hdr = (struct pseudo_hdr *)pmsg; - ppseudo_hdr->length = htons(0x0012); - ppseudo_hdr->source = 0x10; - ppseudo_hdr->destination = 0x20; - ppseudo_hdr->portdest = 0; - ppseudo_hdr->portsrc = 0; - ppseudo_hdr->sh_str_id = 0; - ppseudo_hdr->control = 0; - ppseudo_hdr->rsvd1 = 0; - ppseudo_hdr->rsvd2 = 0; - ppseudo_hdr->qos_class = 0; - // Insert slow queue sequence number - ppseudo_hdr->seq_num = info->squeseqnum++; - // Insert application id - ppseudo_hdr->portsrc = 0; - // Calculate new checksum - ppseudo_hdr->checksum = *pmsg++; - for (i=1; i<7; i++) { - ppseudo_hdr->checksum ^= *pmsg++; - } - pmsg = (u16 *)&tempbuffer[16]; - *pmsg++ = htons(RSP_DRV_ERR_RPT_MSG); - *pmsg++ = htons(0x000e); - *pmsg++ = htons(info->DSP_TIME[0]); - *pmsg++ = htons(info->DSP_TIME[1]); - *pmsg++ = htons(info->DSP_TIME[2]); - *pmsg++ = htons(info->DSP_TIME[3]); - convert.byte[0] = info->DspVer[0]; - convert.byte[1] = info->DspVer[1]; - *pmsg++ = convert.wrd; - convert.byte[0] = info->DspVer[2]; - convert.byte[1] = info->DspVer[3]; - *pmsg++ = convert.wrd; - *pmsg++ = htons(info->DrvErrNum); - - CardSendCommand (dev, (unsigned char*)&tempbuffer[0], (u16)(0x0012 + PSEUDOSZ)); - info->DrvErrNum = 0; - } - info->DrvMsgPend = 0; - - break; - } - - default: - break; - } - - - status = STATUS_SUCCESS; + ppseudo_hdr->length = htons(0x0012); + ppseudo_hdr->source = 0x10; + ppseudo_hdr->destination = 0x20; + ppseudo_hdr->portdest = 0; + ppseudo_hdr->portsrc = 0; + ppseudo_hdr->sh_str_id = 0; + ppseudo_hdr->control = 0; + ppseudo_hdr->rsvd1 = 0; + ppseudo_hdr->rsvd2 = 0; + ppseudo_hdr->qos_class = 0; + /* Insert slow queue sequence number */ + ppseudo_hdr->seq_num = info->squeseqnum++; + /* Insert application id */ + ppseudo_hdr->portsrc = 0; + /* Calculate new checksum */ + ppseudo_hdr->checksum = *pmsg++; + for (i = 1; i < 7; i++) + ppseudo_hdr->checksum ^= *pmsg++; + + pmsg = (u16 *) &tempbuffer[16]; + *pmsg++ = htons(RSP_DRV_ERR_RPT_MSG); + *pmsg++ = htons(0x000e); + *pmsg++ = htons(info->DSP_TIME[0]); + *pmsg++ = htons(info->DSP_TIME[1]); + *pmsg++ = htons(info->DSP_TIME[2]); + *pmsg++ = htons(info->DSP_TIME[3]); + convert.byte[0] = info->DspVer[0]; + convert.byte[1] = info->DspVer[1]; + *pmsg++ = convert.wrd; + convert.byte[0] = info->DspVer[2]; + convert.byte[1] = info->DspVer[3]; + *pmsg++ = convert.wrd; + *pmsg++ = htons(info->DrvErrNum); + + card_send_command(dev, (unsigned char *)&tempbuffer[0], + (u16)(0x0012 + PSEUDOSZ)); + info->DrvErrNum = 0; + } + dev->DrvMsgPend = 0; + break; + } + default: + break; + } + + status = 0; out: - kfree(cmdbuffer); - DEBUG("return from ft1000_proc_drvmsg\n"); - return status; + kfree(cmdbuffer); + DEBUG("return from ft1000_proc_drvmsg\n"); + return status; } +/* Check which application has registered for dsp broadcast messages */ +static int dsp_broadcast_msg_id(struct ft1000_usb *dev) +{ + struct dpram_blk *pdpram_blk; + unsigned long flags; + int i; + + for (i = 0; i < MAX_NUM_APP; i++) { + if ((dev->app_info[i].DspBCMsgFlag) + && (dev->app_info[i].fileobject) + && (dev->app_info[i].NumOfMsg + < MAX_MSG_LIMIT)) { + pdpram_blk = ft1000_get_buffer(&freercvpool); + if (pdpram_blk == NULL) { + DEBUG("Out of memory in free receive command pool\n"); + dev->app_info[i].nRxMsgMiss++; + return -1; + } + if (ft1000_receive_cmd(dev, pdpram_blk->pbuffer, + MAX_CMD_SQSIZE)) { + /* Put message into the + * appropriate application block + */ + dev->app_info[i].nRxMsg++; + spin_lock_irqsave(&free_buff_lock, flags); + list_add_tail(&pdpram_blk->list, + &dev->app_info[i] .app_sqlist); + dev->app_info[i].NumOfMsg++; + spin_unlock_irqrestore(&free_buff_lock, flags); + wake_up_interruptible(&dev->app_info[i] + .wait_dpram_msg); + } else { + dev->app_info[i].nRxMsgMiss++; + ft1000_free_buffer(pdpram_blk, &freercvpool); + DEBUG("pdpram_blk::ft1000_get_buffer NULL\n"); + return -1; + } + } + } + return 0; +} - -int ft1000_poll(void* dev_id) { - - struct ft1000_device *dev = (struct ft1000_device *)dev_id; - struct ft1000_info *info = netdev_priv(dev->net); - - u16 tempword; - u16 status; - u16 size; - int i; - u16 data; - u16 modulo; - u16 portid; - u16 nxtph; +static int handle_misc_portid(struct ft1000_usb *dev) +{ struct dpram_blk *pdpram_blk; - struct pseudo_hdr *ppseudo_hdr; - unsigned long flags; - - //DEBUG("Enter ft1000_poll...\n"); - if (ft1000_chkcard(dev) == FALSE) { - DEBUG("ft1000_poll::ft1000_chkcard: failed\n"); - return STATUS_FAILURE; - } - - status = ft1000_read_register (dev, &tempword, FT1000_REG_DOORBELL); - // DEBUG("ft1000_poll: read FT1000_REG_DOORBELL message 0x%x\n", tempword); - - if ( !status ) - { - - if (tempword & FT1000_DB_DPRAM_RX) { - //DEBUG("ft1000_poll: FT1000_REG_DOORBELL message type: FT1000_DB_DPRAM_RX\n"); - - status = ft1000_read_dpram16(dev, 0x200, (u8 *)&data, 0); - //DEBUG("ft1000_poll:FT1000_DB_DPRAM_RX:ft1000_read_dpram16:size = 0x%x\n", data); - size = ntohs(data) + 16 + 2; //wai - if (size % 4) { - modulo = 4 - (size % 4); - size = size + modulo; - } - status = ft1000_read_dpram16(dev, 0x201, (u8 *)&portid, 1); - portid &= 0xff; - //DEBUG("ft1000_poll: FT1000_REG_DOORBELL message type: FT1000_DB_DPRAM_RX : portid 0x%x\n", portid); - - if (size < MAX_CMD_SQSIZE) { - switch (portid) - { - case DRIVERID: - DEBUG("ft1000_poll: FT1000_REG_DOORBELL message type: FT1000_DB_DPRAM_RX : portid DRIVERID\n"); - - status = ft1000_proc_drvmsg (dev, size); - if (status != STATUS_SUCCESS ) - return status; - break; - case DSPBCMSGID: - // This is a dsp broadcast message - // Check which application has registered for dsp broadcast messages - //DEBUG("ft1000_poll: FT1000_REG_DOORBELL message type: FT1000_DB_DPRAM_RX : portid DSPBCMSGID\n"); - - for (i=0; i<MAX_NUM_APP; i++) { - if ( (info->app_info[i].DspBCMsgFlag) && (info->app_info[i].fileobject) && - (info->app_info[i].NumOfMsg < MAX_MSG_LIMIT) ) - { - //DEBUG("Dsp broadcast message detected for app id %d\n", i); - nxtph = FT1000_DPRAM_RX_BASE + 2; - pdpram_blk = ft1000_get_buffer (&freercvpool); - if (pdpram_blk != NULL) { - if ( ft1000_receive_cmd(dev, pdpram_blk->pbuffer, MAX_CMD_SQSIZE, &nxtph) ) { - ppseudo_hdr = (struct pseudo_hdr *)pdpram_blk->pbuffer; - // Put message into the appropriate application block - info->app_info[i].nRxMsg++; - spin_lock_irqsave(&free_buff_lock, flags); - list_add_tail(&pdpram_blk->list, &info->app_info[i].app_sqlist); - info->app_info[i].NumOfMsg++; - spin_unlock_irqrestore(&free_buff_lock, flags); - wake_up_interruptible(&info->app_info[i].wait_dpram_msg); - } - else { - info->app_info[i].nRxMsgMiss++; - // Put memory back to free pool - ft1000_free_buffer(pdpram_blk, &freercvpool); - DEBUG("pdpram_blk::ft1000_get_buffer NULL\n"); - } - } - else { - DEBUG("Out of memory in free receive command pool\n"); - info->app_info[i].nRxMsgMiss++; - }//endof if (pdpram_blk != NULL) - }//endof if - //else - // DEBUG("app_info mismatch\n"); - }// endof for - break; - default: - pdpram_blk = ft1000_get_buffer (&freercvpool); - //DEBUG("Memory allocated = 0x%8x\n", (u32)pdpram_blk); - if (pdpram_blk != NULL) { - if ( ft1000_receive_cmd(dev, pdpram_blk->pbuffer, MAX_CMD_SQSIZE, &nxtph) ) { - ppseudo_hdr = (struct pseudo_hdr *)pdpram_blk->pbuffer; - // Search for correct application block - for (i=0; i<MAX_NUM_APP; i++) { - if (info->app_info[i].app_id == ppseudo_hdr->portdest) { - break; - } - } - - if (i == MAX_NUM_APP) { - DEBUG("FT1000:ft1000_parse_dpram_msg: No application matching id = %d\n", ppseudo_hdr->portdest); - // Put memory back to free pool - ft1000_free_buffer(pdpram_blk, &freercvpool); - } - else { - if (info->app_info[i].NumOfMsg > MAX_MSG_LIMIT) { - // Put memory back to free pool - ft1000_free_buffer(pdpram_blk, &freercvpool); - } - else { - info->app_info[i].nRxMsg++; - // Put message into the appropriate application block - //pxu spin_lock_irqsave(&free_buff_lock, flags); - list_add_tail(&pdpram_blk->list, &info->app_info[i].app_sqlist); - info->app_info[i].NumOfMsg++; - //pxu spin_unlock_irqrestore(&free_buff_lock, flags); - //pxu wake_up_interruptible(&info->app_info[i].wait_dpram_msg); - } - } - } - else { - // Put memory back to free pool - ft1000_free_buffer(pdpram_blk, &freercvpool); - } - } - else { - DEBUG("Out of memory in free receive command pool\n"); - } - break; - } //end of switch - } //endof if (size < MAX_CMD_SQSIZE) - else { - DEBUG("FT1000:dpc:Invalid total length for SlowQ = %d\n", size); - } - status = ft1000_write_register (dev, FT1000_DB_DPRAM_RX, FT1000_REG_DOORBELL); - } - else if (tempword & FT1000_DSP_ASIC_RESET) { - //DEBUG("ft1000_poll: FT1000_REG_DOORBELL message type: FT1000_DSP_ASIC_RESET\n"); - - // Let's reset the ASIC from the Host side as well - status = ft1000_write_register (dev, ASIC_RESET_BIT, FT1000_REG_RESET); - status = ft1000_read_register (dev, &tempword, FT1000_REG_RESET); - i = 0; - while (tempword & ASIC_RESET_BIT) { - status = ft1000_read_register (dev, &tempword, FT1000_REG_RESET); - msleep(10); - i++; - if (i==100) - break; - } - if (i==100) { - DEBUG("Unable to reset ASIC\n"); - return STATUS_SUCCESS; - } - msleep(10); - // Program WMARK register - status = ft1000_write_register (dev, 0x600, FT1000_REG_MAG_WATERMARK); - // clear ASIC reset doorbell - status = ft1000_write_register (dev, FT1000_DSP_ASIC_RESET, FT1000_REG_DOORBELL); - msleep(10); - } - else if (tempword & FT1000_ASIC_RESET_REQ) { - DEBUG("ft1000_poll: FT1000_REG_DOORBELL message type: FT1000_ASIC_RESET_REQ\n"); - - // clear ASIC reset request from DSP - status = ft1000_write_register (dev, FT1000_ASIC_RESET_REQ, FT1000_REG_DOORBELL); - status = ft1000_write_register (dev, HOST_INTF_BE, FT1000_REG_SUP_CTRL); - // copy dsp session record from Adapter block - status = ft1000_write_dpram32 (dev, 0, (u8 *)&info->DSPSess.Rec[0], 1024); - // Program WMARK register - status = ft1000_write_register (dev, 0x600, FT1000_REG_MAG_WATERMARK); - // ring doorbell to tell DSP that ASIC is out of reset - status = ft1000_write_register (dev, FT1000_ASIC_RESET_DSP, FT1000_REG_DOORBELL); - } - else if (tempword & FT1000_DB_COND_RESET) { - DEBUG("ft1000_poll: FT1000_REG_DOORBELL message type: FT1000_DB_COND_RESET\n"); -//By Jim -// Reset ASIC and DSP -//MAG - if (info->fAppMsgPend == 0) { - // Reset ASIC and DSP - - status = ft1000_read_dpram16(dev, FT1000_MAG_DSP_TIMER0, (u8 *)&(info->DSP_TIME[0]), FT1000_MAG_DSP_TIMER0_INDX); - status = ft1000_read_dpram16(dev, FT1000_MAG_DSP_TIMER1, (u8 *)&(info->DSP_TIME[1]), FT1000_MAG_DSP_TIMER1_INDX); - status = ft1000_read_dpram16(dev, FT1000_MAG_DSP_TIMER2, (u8 *)&(info->DSP_TIME[2]), FT1000_MAG_DSP_TIMER2_INDX); - status = ft1000_read_dpram16(dev, FT1000_MAG_DSP_TIMER3, (u8 *)&(info->DSP_TIME[3]), FT1000_MAG_DSP_TIMER3_INDX); - info->CardReady = 0; - info->DrvErrNum = DSP_CONDRESET_INFO; - DEBUG("ft1000_hw:DSP conditional reset requested\n"); - info->ft1000_reset(dev->net); - } - else { - info->fProvComplete = 0; - info->fCondResetPend = 1; - } - - ft1000_write_register(dev, FT1000_DB_COND_RESET, FT1000_REG_DOORBELL); - } - - }//endof if ( !status ) - - //DEBUG("return from ft1000_poll.\n"); - return STATUS_SUCCESS; + int i; + pdpram_blk = ft1000_get_buffer(&freercvpool); + if (pdpram_blk == NULL) { + DEBUG("Out of memory in free receive command pool\n"); + return -1; + } + if (!ft1000_receive_cmd(dev, pdpram_blk->pbuffer, MAX_CMD_SQSIZE)) + goto exit_failure; + + /* Search for correct application block */ + for (i = 0; i < MAX_NUM_APP; i++) { + if (dev->app_info[i].app_id == ((struct pseudo_hdr *) + pdpram_blk->pbuffer)->portdest) + break; + } + if (i == MAX_NUM_APP) { + DEBUG("FT1000:ft1000_parse_dpram_msg: No application matching id = %d\n", ((struct pseudo_hdr *)pdpram_blk->pbuffer)->portdest); + goto exit_failure; + } else if (dev->app_info[i].NumOfMsg > MAX_MSG_LIMIT) { + goto exit_failure; + } else { + dev->app_info[i].nRxMsg++; + /* Put message into the appropriate application block */ + list_add_tail(&pdpram_blk->list, &dev->app_info[i].app_sqlist); + dev->app_info[i].NumOfMsg++; + } + return 0; + +exit_failure: + ft1000_free_buffer(pdpram_blk, &freercvpool); + return -1; } -/*end of Jim*/ +int ft1000_poll(void *dev_id) +{ + struct ft1000_usb *dev = (struct ft1000_usb *)dev_id; + struct ft1000_info *info = netdev_priv(dev->net); + u16 tempword; + int status; + u16 size; + int i; + u16 data; + u16 modulo; + u16 portid; + + if (ft1000_chkcard(dev) == FALSE) { + DEBUG("ft1000_poll::ft1000_chkcard: failed\n"); + return -1; + } + status = ft1000_read_register(dev, &tempword, FT1000_REG_DOORBELL); + if (!status) { + if (tempword & FT1000_DB_DPRAM_RX) { + status = ft1000_read_dpram16(dev, + 0x200, (u8 *)&data, 0); + size = ntohs(data) + 16 + 2; + if (size % 4) { + modulo = 4 - (size % 4); + size = size + modulo; + } + status = ft1000_read_dpram16(dev, 0x201, + (u8 *)&portid, 1); + portid &= 0xff; + if (size < MAX_CMD_SQSIZE) { + switch (portid) { + case DRIVERID: + DEBUG("ft1000_poll: FT1000_REG_DOORBELL message type: FT1000_DB_DPRAM_RX : portid DRIVERID\n"); + status = ft1000_proc_drvmsg(dev, size); + if (status != 0) + return status; + break; + case DSPBCMSGID: + status = dsp_broadcast_msg_id(dev); + break; + default: + status = handle_misc_portid(dev); + break; + } + } else + DEBUG("FT1000:dpc:Invalid total length for SlowQ = %d\n", size); + status = ft1000_write_register(dev, + FT1000_DB_DPRAM_RX, + FT1000_REG_DOORBELL); + } else if (tempword & FT1000_DSP_ASIC_RESET) { + /* Let's reset the ASIC from the Host side as well */ + status = ft1000_write_register(dev, ASIC_RESET_BIT, + FT1000_REG_RESET); + status = ft1000_read_register(dev, &tempword, + FT1000_REG_RESET); + i = 0; + while (tempword & ASIC_RESET_BIT) { + status = ft1000_read_register(dev, &tempword, + FT1000_REG_RESET); + usleep_range(9000, 11000); + i++; + if (i == 100) + break; + } + if (i == 100) { + DEBUG("Unable to reset ASIC\n"); + return 0; + } + usleep_range(9000, 11000); + /* Program WMARK register */ + status = ft1000_write_register(dev, 0x600, + FT1000_REG_MAG_WATERMARK); + /* clear ASIC reset doorbell */ + status = ft1000_write_register(dev, + FT1000_DSP_ASIC_RESET, + FT1000_REG_DOORBELL); + usleep_range(9000, 11000); + } else if (tempword & FT1000_ASIC_RESET_REQ) { + DEBUG("ft1000_poll: FT1000_REG_DOORBELL message type: FT1000_ASIC_RESET_REQ\n"); + /* clear ASIC reset request from DSP */ + status = ft1000_write_register(dev, + FT1000_ASIC_RESET_REQ, + FT1000_REG_DOORBELL); + status = ft1000_write_register(dev, HOST_INTF_BE, + FT1000_REG_SUP_CTRL); + /* copy dsp session record from Adapter block */ + status = ft1000_write_dpram32(dev, 0, + (u8 *)&info->DSPSess.Rec[0], 1024); + status = ft1000_write_register(dev, 0x600, + FT1000_REG_MAG_WATERMARK); + /* ring doorbell to tell DSP that + * ASIC is out of reset + * */ + status = ft1000_write_register(dev, + FT1000_ASIC_RESET_DSP, + FT1000_REG_DOORBELL); + } else if (tempword & FT1000_DB_COND_RESET) { + DEBUG("ft1000_poll: FT1000_REG_DOORBELL message type: FT1000_DB_COND_RESET\n"); + if (!dev->fAppMsgPend) { + /* Reset ASIC and DSP */ + status = ft1000_read_dpram16(dev, + FT1000_MAG_DSP_TIMER0, + (u8 *)&(info->DSP_TIME[0]), + FT1000_MAG_DSP_TIMER0_INDX); + status = ft1000_read_dpram16(dev, + FT1000_MAG_DSP_TIMER1, + (u8 *)&(info->DSP_TIME[1]), + FT1000_MAG_DSP_TIMER1_INDX); + status = ft1000_read_dpram16(dev, + FT1000_MAG_DSP_TIMER2, + (u8 *)&(info->DSP_TIME[2]), + FT1000_MAG_DSP_TIMER2_INDX); + status = ft1000_read_dpram16(dev, + FT1000_MAG_DSP_TIMER3, + (u8 *)&(info->DSP_TIME[3]), + FT1000_MAG_DSP_TIMER3_INDX); + info->CardReady = 0; + info->DrvErrNum = DSP_CONDRESET_INFO; + DEBUG("ft1000_hw:DSP conditional reset requested\n"); + info->ft1000_reset(dev->net); + } else { + dev->fProvComplete = false; + dev->fCondResetPend = true; + } + ft1000_write_register(dev, FT1000_DB_COND_RESET, + FT1000_REG_DOORBELL); + } + } + return 0; +} diff --git a/drivers/staging/ft1000/ft1000-usb/ft1000_hw.h b/drivers/staging/ft1000/ft1000-usb/ft1000_hw.h deleted file mode 100644 index ab9312f9f32..00000000000 --- a/drivers/staging/ft1000/ft1000-usb/ft1000_hw.h +++ /dev/null @@ -1,10 +0,0 @@ - -#ifndef _FT1000_HW_H_ -#define _FT1000_HW_H_ - -#include "ft1000_usb.h" - -extern u16 ft1000_read_register(struct usb_device *dev, u16 *Data, u8 nRegIndx); -extern u16 ft1000_write_register(struct usb_device *dev, u16 value, u8 nRegIndx); - -#endif diff --git a/drivers/staging/ft1000/ft1000-usb/ft1000_ioctl.h b/drivers/staging/ft1000/ft1000-usb/ft1000_ioctl.h index 3f72d5bb3f9..cb644a58d9f 100644 --- a/drivers/staging/ft1000/ft1000-usb/ft1000_ioctl.h +++ b/drivers/staging/ft1000/ft1000-usb/ft1000_ioctl.h @@ -1,139 +1,123 @@ -//--------------------------------------------------------------------------- -// FT1000 driver for Flarion Flash OFDM NIC Device -// -// Copyright (C) 2002 Flarion Technologies, All rights reserved. -// -// This program is free software; you can redistribute it and/or modify it -// under the terms of the GNU General Public License as published by the Free -// Software Foundation; either version 2 of the License, or (at your option) any -// later version. This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY -// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for -// more details. You should have received a copy of the GNU General Public -// License along with this program; if not, write to the -// Free Software Foundation, Inc., 59 Temple Place - -// Suite 330, Boston, MA 02111-1307, USA. -//--------------------------------------------------------------------------- -// -// File: ft1000_ioctl.h -// -// Description: Common structures and defines relating to IOCTL -// -// History: -// 11/5/02 Whc Created. -// -//---------------------------------------------------------------------------//--------------------------------------------------------------------------- +/* +*--------------------------------------------------------------------------- +* FT1000 driver for Flarion Flash OFDM NIC Device +* +* Copyright (C) 2002 Flarion Technologies, All rights reserved. +* +* This program is free software; you can redistribute it and/or modify it +* under the terms of the GNU General Public License as published by the Free +* Software Foundation; either version 2 of the License, or (at your option) any +* later version. This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY +* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for +* more details. You should have received a copy of the GNU General Public +* License along with this program; if not, write to the +* Free Software Foundation, Inc., 59 Temple Place - +* Suite 330, Boston, MA 02111-1307, USA. +*--------------------------------------------------------------------------- +* +* File: ft1000_ioctl.h +* +* Description: Common structures and defines relating to IOCTL +* +* History: +* 11/5/02 Whc Created. +* +*--------------------------------------------------------------------------- +*/ #ifndef _FT1000IOCTLH_ #define _FT1000IOCTLH_ -#define DSPVERSZ 4 -#define HWSERNUMSZ 16 -#define SKUSZ 20 -#define EUISZ 8 -#define CALVERSZ 2 -#define CALDATESZ 6 +struct IOCTL_GET_VER { + unsigned long drv_ver; +} __packed; -#define MAX_DNLD_BLKSZ 1024 +/* Data structure for Dsp statistics */ +struct IOCTL_GET_DSP_STAT { + unsigned char DspVer[DSPVERSZ]; /* DSP version number */ + unsigned char HwSerNum[HWSERNUMSZ]; /* Hardware Serial Number */ + unsigned char Sku[SKUSZ]; /* SKU */ + unsigned char eui64[EUISZ]; /* EUI64 */ + unsigned short ConStat; /* Connection Status */ + /* Bits 0-3 = Connection Status Field */ + /* 0000=Idle (Disconnect) */ + /* 0001=Searching */ + /* 0010=Active (Connected) */ + /* 0011=Waiting for L2 down */ + /* 0100=Sleep */ + unsigned short LedStat; /* Led Status */ + /* Bits 0-3 = Signal Strength Field */ + /* 0000 = -105dBm to -92dBm */ + /* 0001 = -92dBm to -85dBm */ + /* 0011 = -85dBm to -75dBm */ + /* 0111 = -75dBm to -50dBm */ + /* 1111 = -50dBm to 0dBm */ + /* Bits 4-7 = Reserved */ + /* Bits 8-11 = SNR Field */ + /* 0000 = <2dB */ + /* 0001 = 2dB to 8dB */ + /* 0011 = 8dB to 15dB */ + /* 0111 = 15dB to 22dB */ + /* 1111 = >22dB */ + /* Bits 12-15 = Reserved */ + unsigned long nTxPkts; /* Number of packets transmitted + * from host to dsp + */ + unsigned long nRxPkts; /* Number of packets received from + * dsp to host + */ + unsigned long nTxBytes; /* Number of bytes transmitted + * from host to dsp + */ + unsigned long nRxBytes; /* Number of bytes received from + * dsp to host + */ + unsigned long ConTm; /* Current session connection time + * in seconds + */ + unsigned char CalVer[CALVERSZ]; /* Proprietary Calibration + * Version + */ + unsigned char CalDate[CALDATESZ]; /* Proprietary Calibration Date */ +} __packed; -// Standard Flarion Pseudo header -struct pseudo_hdr { - unsigned short length; //length of msg body - unsigned char source; //source address (0x10=Host 0x20=DSP) - unsigned char destination; //destination address (refer to source address) - unsigned char portdest; //destination port id - // 0x00=Driver - // 0x10=Application Broadcast - // 0x20=Network Stack - // 0x80=Dsp OAM - // 0x90=Dsp Airlink - // 0xa0=Dsp Loader - // 0xb0=Dsp MIP - unsigned char portsrc; //source port id (refer to portdest) - unsigned short sh_str_id; //stream id (Not applicable on Mobile) - unsigned char control; //stream id (Not applicable on Mobile) - unsigned char rsvd1; //reserved - unsigned char seq_num; //sequence number - unsigned char rsvd2; //reserved - unsigned short qos_class; //Quality of Service class (Not applicable on Mobile) - unsigned short checksum; //Psuedo header checksum -} __attribute__ ((packed)); - -typedef struct _IOCTL_GET_VER -{ - unsigned long drv_ver; -} __attribute__ ((packed)) IOCTL_GET_VER, *PIOCTL_GET_VER; - -//Data structure for Dsp statistics -typedef struct _IOCTL_GET_DSP_STAT -{ - unsigned char DspVer[DSPVERSZ]; // DSP version number - unsigned char HwSerNum[HWSERNUMSZ]; // Hardware Serial Number - unsigned char Sku[SKUSZ]; // SKU - unsigned char eui64[EUISZ]; // EUI64 - unsigned short ConStat; // Connection Status - // Bits 0-3 = Connection Status Field - // 0000=Idle (Disconnect) - // 0001=Searching - // 0010=Active (Connected) - // 0011=Waiting for L2 down - // 0100=Sleep - unsigned short LedStat; // Led Status - // Bits 0-3 = Signal Strength Field - // 0000 = -105dBm to -92dBm - // 0001 = -92dBm to -85dBm - // 0011 = -85dBm to -75dBm - // 0111 = -75dBm to -50dBm - // 1111 = -50dBm to 0dBm - // Bits 4-7 = Reserved - // Bits 8-11 = SNR Field - // 0000 = <2dB - // 0001 = 2dB to 8dB - // 0011 = 8dB to 15dB - // 0111 = 15dB to 22dB - // 1111 = >22dB - // Bits 12-15 = Reserved - unsigned long nTxPkts; // Number of packets transmitted from host to dsp - unsigned long nRxPkts; // Number of packets received from dsp to host - unsigned long nTxBytes; // Number of bytes transmitted from host to dsp - unsigned long nRxBytes; // Number of bytes received from dsp to host - unsigned long ConTm; // Current session connection time in seconds - unsigned char CalVer[CALVERSZ]; // Proprietary Calibration Version - unsigned char CalDate[CALDATESZ]; // Proprietary Calibration Date -} __attribute__ ((packed)) IOCTL_GET_DSP_STAT, *PIOCTL_GET_DSP_STAT; - -//Data structure for Dual Ported RAM messaging between Host and Dsp -typedef struct _IOCTL_DPRAM_BLK -{ - unsigned short total_len; +/* Data structure for Dual Ported RAM messaging between Host and Dsp */ +struct IOCTL_DPRAM_BLK { + unsigned short total_len; struct pseudo_hdr pseudohdr; - unsigned char buffer[1780]; -} __attribute__ ((packed)) IOCTL_DPRAM_BLK, *PIOCTL_DPRAM_BLK; + unsigned char buffer[1780]; +} __packed; -typedef struct _IOCTL_DPRAM_COMMAND -{ - unsigned short extra; - IOCTL_DPRAM_BLK dpram_blk; -} __attribute__ ((packed)) IOCTL_DPRAM_COMMAND, *PIOCTL_DPRAM_COMMAND; +struct IOCTL_DPRAM_COMMAND { + unsigned short extra; + struct IOCTL_DPRAM_BLK dpram_blk; +} __packed; -// -// Custom IOCTL command codes -// +/* +* Custom IOCTL command codes +*/ #define FT1000_MAGIC_CODE 'F' -#define IOCTL_REGISTER_CMD 0 -#define IOCTL_SET_DPRAM_CMD 3 -#define IOCTL_GET_DPRAM_CMD 4 -#define IOCTL_GET_DSP_STAT_CMD 6 -#define IOCTL_GET_VER_CMD 7 -#define IOCTL_CONNECT 10 -#define IOCTL_DISCONNECT 11 +#define IOCTL_REGISTER_CMD 0 +#define IOCTL_SET_DPRAM_CMD 3 +#define IOCTL_GET_DPRAM_CMD 4 +#define IOCTL_GET_DSP_STAT_CMD 6 +#define IOCTL_GET_VER_CMD 7 +#define IOCTL_CONNECT 10 +#define IOCTL_DISCONNECT 11 -#define IOCTL_FT1000_GET_DSP_STAT _IOR (FT1000_MAGIC_CODE, IOCTL_GET_DSP_STAT_CMD, sizeof(IOCTL_GET_DSP_STAT) ) -#define IOCTL_FT1000_GET_VER _IOR (FT1000_MAGIC_CODE, IOCTL_GET_VER_CMD, sizeof(IOCTL_GET_VER) ) -#define IOCTL_FT1000_CONNECT _IOW (FT1000_MAGIC_CODE, IOCTL_CONNECT, 0 ) -#define IOCTL_FT1000_DISCONNECT _IOW (FT1000_MAGIC_CODE, IOCTL_DISCONNECT, 0 ) -#define IOCTL_FT1000_SET_DPRAM _IOW (FT1000_MAGIC_CODE, IOCTL_SET_DPRAM_CMD, sizeof(IOCTL_DPRAM_BLK) ) -#define IOCTL_FT1000_GET_DPRAM _IOR (FT1000_MAGIC_CODE, IOCTL_GET_DPRAM_CMD, sizeof(IOCTL_DPRAM_BLK) ) -#define IOCTL_FT1000_REGISTER _IOW (FT1000_MAGIC_CODE, IOCTL_REGISTER_CMD, sizeof(unsigned short *) ) -#endif // _FT1000IOCTLH_ +#define IOCTL_FT1000_GET_DSP_STAT _IOR(FT1000_MAGIC_CODE, \ + IOCTL_GET_DSP_STAT_CMD, \ + struct IOCTL_GET_DSP_STAT) +#define IOCTL_FT1000_GET_VER _IOR(FT1000_MAGIC_CODE, IOCTL_GET_VER_CMD, \ + struct IOCTL_GET_VER) +#define IOCTL_FT1000_CONNECT _IO(FT1000_MAGIC_CODE, IOCTL_CONNECT) +#define IOCTL_FT1000_DISCONNECT _IO(FT1000_MAGIC_CODE, IOCTL_DISCONNECT) +#define IOCTL_FT1000_SET_DPRAM _IOW(FT1000_MAGIC_CODE, IOCTL_SET_DPRAM_CMD, \ + struct IOCTL_DPRAM_BLK) +#define IOCTL_FT1000_GET_DPRAM _IOR(FT1000_MAGIC_CODE, IOCTL_GET_DPRAM_CMD, \ + struct IOCTL_DPRAM_BLK) +#define IOCTL_FT1000_REGISTER _IOW(FT1000_MAGIC_CODE, IOCTL_REGISTER_CMD, \ + unsigned short *) +#endif /* _FT1000IOCTLH_ */ diff --git a/drivers/staging/ft1000/ft1000-usb/ft1000_proc.c b/drivers/staging/ft1000/ft1000-usb/ft1000_proc.c index b87542abbe8..e89b5d2c8e6 100644 --- a/drivers/staging/ft1000/ft1000-usb/ft1000_proc.c +++ b/drivers/staging/ft1000/ft1000-usb/ft1000_proc.c @@ -22,6 +22,7 @@ #include <linux/module.h> #include <linux/kernel.h> #include <linux/proc_fs.h> +#include <linux/seq_file.h> #include <linux/netdevice.h> @@ -30,45 +31,33 @@ #define FT1000_PROC_DIR "ft1000" -#define PUTM_TO_PAGE(len,page,args...) \ - len += snprintf(page+len, PAGE_SIZE - len, args) - -#define PUTX_TO_PAGE(len,page,message,size,var) \ - len += snprintf(page+len, PAGE_SIZE - len, message); \ - for (i = 0; i < (size - 1); i++) {\ - len += snprintf(page+len, PAGE_SIZE - len, "%02x:", var[i]); \ - } \ - len += snprintf(page+len, PAGE_SIZE - len, "%02x\n", var[i]) - -#define PUTD_TO_PAGE(len,page,message,size,var) \ - len += snprintf(page+len, PAGE_SIZE - len, message); \ - for (i = 0; i < (size - 1); i++) {\ - len += snprintf(page+len, PAGE_SIZE - len, "%d.", var[i]); \ - } \ - len += snprintf(page+len, PAGE_SIZE - len, "%d\n", var[i]) +#define seq_putx(m, message, size, var) \ + do { \ + seq_printf(m, message); \ + for (i = 0; i < (size - 1); i++) \ + seq_printf(m, "%02x:", var[i]); \ + seq_printf(m, "%02x\n", var[i]); \ + } while (0) +#define seq_putd(m, message, size, var) \ + do { \ + seq_printf(m, message); \ + for (i = 0; i < (size - 1); i++) \ + seq_printf(m, "%d.", var[i]); \ + seq_printf(m, "%d\n", var[i]); \ + } while (0) #define FTNET_PROC init_net.proc_net -u16 ft1000_read_dpram16 (struct ft1000_device *ft1000dev, u16 indx, +int ft1000_read_dpram16(struct ft1000_usb *ft1000dev, u16 indx, u8 *buffer, u8 highlow); -static int -ft1000ReadProc(char *page, char **start, off_t off, int count, int *eof, - void *data) +static int ft1000ReadProc(struct seq_file *m, void *v) { - struct net_device *dev; - int len; - int i; - unsigned short ledStat; - unsigned short conStat; - - struct ft1000_info *info; - - char *status[] = { - "Idle (Disconnect)", + static const char *status[] = { + "Idle (Disconnect)", "Searching", "Active (Connected)", "Waiting for L2", @@ -77,28 +66,24 @@ ft1000ReadProc(char *page, char **start, off_t off, int count, int *eof, "", "", }; + static const char *signal[] = { "", "*", "**", "***", "****" }; - char *signal[] = { "", "*", "**", "***", "****" }; + struct net_device *dev = m->private; + struct ft1000_info *info = netdev_priv(dev); + int i; + unsigned short ledStat; + unsigned short conStat; int strength; int quality; struct timeval tv; time_t delta; - dev = (struct net_device *) data; - info = netdev_priv(dev); - - if (off > 0) { - *eof = 1; - return 0; - } - - if (info->ProgConStat != 0xFF) { - ft1000_read_dpram16(info->pFt1000Dev, FT1000_MAG_DSP_LED, + ft1000_read_dpram16(info->priv, FT1000_MAG_DSP_LED, (u8 *)&ledStat, FT1000_MAG_DSP_LED_INDX); info->LedStat = ntohs(ledStat); - ft1000_read_dpram16(info->pFt1000Dev, FT1000_MAG_DSP_CON_STATE, + ft1000_read_dpram16(info->priv, FT1000_MAG_DSP_CON_STATE, (u8 *)&conStat, FT1000_MAG_DSP_CON_STATE_INDX); info->ConStat = ntohs(conStat); do_gettimeofday(&tv); @@ -144,40 +129,47 @@ ft1000ReadProc(char *page, char **start, off_t off, int count, int *eof, quality = 0; } - len = 0; - PUTM_TO_PAGE(len, page, "Connection Time: %02ld:%02ld:%02ld\n", - ((delta / 3600) % 24), ((delta / 60) % 60), (delta % 60)); - PUTM_TO_PAGE(len, page, "Connection Time[s]: %ld\n", delta); - PUTM_TO_PAGE(len, page, "Asic ID: %s\n", - (info->AsicID) == - ELECTRABUZZ_ID ? "ELECTRABUZZ ASIC" : "MAGNEMITE ASIC"); - PUTX_TO_PAGE(len, page, "SKU: ", SKUSZ, info->Sku); - PUTX_TO_PAGE(len, page, "EUI64: ", EUISZ, info->eui64); - PUTD_TO_PAGE(len, page, "DSP version number: ", DSPVERSZ, info->DspVer); - PUTX_TO_PAGE(len, page, "Hardware Serial Number: ", HWSERNUMSZ, - info->HwSerNum); - PUTX_TO_PAGE(len, page, "Caliberation Version: ", CALVERSZ, - info->RfCalVer); - PUTD_TO_PAGE(len, page, "Caliberation Date: ", CALDATESZ, - info->RfCalDate); - PUTM_TO_PAGE(len, page, "Media State: %s\n", - (info->mediastate) ? "link" : "no link"); - PUTM_TO_PAGE(len, page, "Connection Status: %s\n", - status[((info->ConStat) & 0x7)]); - PUTM_TO_PAGE(len, page, "RX packets: %ld\n", info->stats.rx_packets); - PUTM_TO_PAGE(len, page, "TX packets: %ld\n", info->stats.tx_packets); - PUTM_TO_PAGE(len, page, "RX bytes: %ld\n", info->stats.rx_bytes); - PUTM_TO_PAGE(len, page, "TX bytes: %ld\n", info->stats.tx_bytes); - PUTM_TO_PAGE(len, page, "Signal Strength: %s\n", signal[strength]); - PUTM_TO_PAGE(len, page, "Signal Quality: %s\n", signal[quality]); - - return len; + seq_printf(m, "Connection Time: %02ld:%02ld:%02ld\n", + ((delta / 3600) % 24), ((delta / 60) % 60), (delta % 60)); + seq_printf(m, "Connection Time[s]: %ld\n", delta); + seq_printf(m, "Asic ID: %s\n", + (info->AsicID) == ELECTRABUZZ_ID ? "ELECTRABUZZ ASIC" : "MAGNEMITE ASIC"); + seq_putx(m, "SKU: ", SKUSZ, info->Sku); + seq_putx(m, "EUI64: ", EUISZ, info->eui64); + seq_putd(m, "DSP version number: ", DSPVERSZ, info->DspVer); + seq_putx(m, "Hardware Serial Number: ", HWSERNUMSZ, info->HwSerNum); + seq_putx(m, "Caliberation Version: ", CALVERSZ, info->RfCalVer); + seq_putd(m, "Caliberation Date: ", CALDATESZ, info->RfCalDate); + seq_printf(m, "Media State: %s\n", (info->mediastate) ? "link" : "no link"); + seq_printf(m, "Connection Status: %s\n", status[info->ConStat & 0x7]); + seq_printf(m, "RX packets: %ld\n", info->stats.rx_packets); + seq_printf(m, "TX packets: %ld\n", info->stats.tx_packets); + seq_printf(m, "RX bytes: %ld\n", info->stats.rx_bytes); + seq_printf(m, "TX bytes: %ld\n", info->stats.tx_bytes); + seq_printf(m, "Signal Strength: %s\n", signal[strength]); + seq_printf(m, "Signal Quality: %s\n", signal[quality]); + return 0; +} + +/* + * seq_file wrappers for procfile show routines. + */ +static int ft1000_proc_open(struct inode *inode, struct file *file) +{ + return single_open(file, ft1000ReadProc, PDE_DATA(inode)); } +static const struct file_operations ft1000_proc_fops = { + .open = ft1000_proc_open, + .read = seq_read, + .llseek = seq_lseek, + .release = single_release, +}; + static int ft1000NotifyProc(struct notifier_block *this, unsigned long event, void *ptr) { - struct net_device *dev = ptr; + struct net_device *dev = netdev_notifier_info_to_dev(ptr); struct ft1000_info *info; struct proc_dir_entry *ft1000_proc_file; @@ -186,9 +178,9 @@ ft1000NotifyProc(struct notifier_block *this, unsigned long event, void *ptr) switch (event) { case NETDEV_CHANGENAME: remove_proc_entry(info->netdevname, info->ft1000_proc_dir); - ft1000_proc_file = create_proc_read_entry(dev->name, 0644, - info->ft1000_proc_dir, - ft1000ReadProc, dev); + ft1000_proc_file = + proc_create_data(dev->name, 0644, info->ft1000_proc_dir, + &ft1000_proc_fops, dev); snprintf(info->netdevname, IFNAMSIZ, "%s", dev->name); break; } @@ -205,25 +197,23 @@ int ft1000_init_proc(struct net_device *dev) { struct ft1000_info *info; struct proc_dir_entry *ft1000_proc_file; - int ret = 0; + int ret = -EINVAL; info = netdev_priv(dev); info->ft1000_proc_dir = proc_mkdir(FT1000_PROC_DIR, FTNET_PROC); if (info->ft1000_proc_dir == NULL) { - printk(KERN_WARNING "Unable to create %s dir.\n", + netdev_warn(dev, "Unable to create %s dir.\n", FT1000_PROC_DIR); - ret = -EINVAL; goto fail; } ft1000_proc_file = - create_proc_read_entry(dev->name, 0644, - info->ft1000_proc_dir, ft1000ReadProc, dev); + proc_create_data(dev->name, 0644, info->ft1000_proc_dir, + &ft1000_proc_fops, dev); - if (ft1000_proc_file == NULL) { - printk(KERN_WARNING "Unable to create /proc entry.\n"); - ret = -EINVAL; + if (!ft1000_proc_file) { + netdev_warn(dev, "Unable to create /proc entry.\n"); goto fail_entry; } diff --git a/drivers/staging/ft1000/ft1000-usb/ft1000_usb.c b/drivers/staging/ft1000/ft1000-usb/ft1000_usb.c index 79482ac1c48..0a2544c7829 100644 --- a/drivers/staging/ft1000/ft1000-usb/ft1000_usb.c +++ b/drivers/staging/ft1000/ft1000-usb/ft1000_usb.c @@ -7,7 +7,6 @@ * $Id: *==================================================== */ -#include <linux/init.h> #include <linux/kernel.h> #include <linux/module.h> #include <linux/usb.h> @@ -36,22 +35,22 @@ static struct usb_device_id id_table[] = { MODULE_DEVICE_TABLE(usb, id_table); -static bool gPollingfailed = FALSE; -int ft1000_poll_thread(void *arg) +static bool gPollingfailed; +static int ft1000_poll_thread(void *arg) { - int ret = STATUS_SUCCESS; + int ret; while (!kthread_should_stop()) { msleep(10); if (!gPollingfailed) { ret = ft1000_poll(arg); - if (ret != STATUS_SUCCESS) { + if (ret != 0) { DEBUG("ft1000_poll_thread: polling failed\n"); - gPollingfailed = TRUE; + gPollingfailed = true; } } } - return STATUS_SUCCESS; + return 0; } static int ft1000_probe(struct usb_interface *interface, @@ -63,18 +62,13 @@ static int ft1000_probe(struct usb_interface *interface, unsigned numaltsetting; int i, ret = 0, size; - struct ft1000_device *ft1000dev; + struct ft1000_usb *ft1000dev; struct ft1000_info *pft1000info = NULL; const struct firmware *dsp_fw; - ft1000dev = kmalloc(sizeof(struct ft1000_device), GFP_KERNEL); - - if (!ft1000dev) { - printk(KERN_ERR "out of memory allocating device structure\n"); - return 0; - } - - memset(ft1000dev, 0, sizeof(*ft1000dev)); + ft1000dev = kzalloc(sizeof(struct ft1000_usb), GFP_KERNEL); + if (!ft1000dev) + return -ENOMEM; dev = interface_to_usbdev(interface); DEBUG("ft1000_probe: usb device descriptor info:\n"); @@ -84,8 +78,12 @@ static int ft1000_probe(struct usb_interface *interface, ft1000dev->dev = dev; ft1000dev->status = 0; ft1000dev->net = NULL; - ft1000dev->tx_urb = usb_alloc_urb(0, GFP_ATOMIC); - ft1000dev->rx_urb = usb_alloc_urb(0, GFP_ATOMIC); + ft1000dev->tx_urb = usb_alloc_urb(0, GFP_KERNEL); + ft1000dev->rx_urb = usb_alloc_urb(0, GFP_KERNEL); + if (!ft1000dev->tx_urb || !ft1000dev->rx_urb) { + ret = -ENOMEM; + goto err_fw; + } DEBUG("ft1000_probe is called\n"); numaltsetting = interface->num_altsetting; @@ -140,7 +138,7 @@ static int ft1000_probe(struct usb_interface *interface, ret = request_firmware(&dsp_fw, "ft3000.img", &dev->dev); if (ret < 0) { - printk(KERN_ERR "Error request_firmware().\n"); + pr_err("Error request_firmware().\n"); goto err_fw; } @@ -168,16 +166,16 @@ static int ft1000_probe(struct usb_interface *interface, DEBUG("In probe: pft1000info=%p\n", pft1000info); ret = dsp_reload(ft1000dev); if (ret) { - printk(KERN_ERR "Problem with DSP image loading\n"); + pr_err("Problem with DSP image loading\n"); goto err_load; } - gPollingfailed = FALSE; - pft1000info->pPollThread = + gPollingfailed = false; + ft1000dev->pPollThread = kthread_run(ft1000_poll_thread, ft1000dev, "ft1000_poll"); - if (IS_ERR(pft1000info->pPollThread)) { - ret = PTR_ERR(pft1000info->pPollThread); + if (IS_ERR(ft1000dev->pPollThread)) { + ret = PTR_ERR(ft1000dev->pPollThread); goto err_load; } @@ -202,7 +200,7 @@ static int ft1000_probe(struct usb_interface *interface, if (ret) goto err_proc; - pft1000info->NetDevRegDone = 1; + ft1000dev->NetDevRegDone = 1; return 0; @@ -210,10 +208,12 @@ err_proc: unregister_netdev(ft1000dev->net); free_netdev(ft1000dev->net); err_thread: - kthread_stop(pft1000info->pPollThread); + kthread_stop(ft1000dev->pPollThread); err_load: kfree(pFileStart); err_fw: + usb_free_urb(ft1000dev->rx_urb); + usb_free_urb(ft1000dev->tx_urb); kfree(ft1000dev); return ret; } @@ -221,6 +221,7 @@ err_fw: static void ft1000_disconnect(struct usb_interface *interface) { struct ft1000_info *pft1000info; + struct ft1000_usb *ft1000dev; DEBUG("ft1000_disconnect is called\n"); @@ -228,28 +229,29 @@ static void ft1000_disconnect(struct usb_interface *interface) DEBUG("In disconnect pft1000info=%p\n", pft1000info); if (pft1000info) { + ft1000dev = pft1000info->priv; ft1000_cleanup_proc(pft1000info); - if (pft1000info->pPollThread) - kthread_stop(pft1000info->pPollThread); + if (ft1000dev->pPollThread) + kthread_stop(ft1000dev->pPollThread); DEBUG("ft1000_disconnect: threads are terminated\n"); - if (pft1000info->pFt1000Dev->net) { + if (ft1000dev->net) { DEBUG("ft1000_disconnect: destroy char driver\n"); - ft1000_destroy_dev(pft1000info->pFt1000Dev->net); - unregister_netdev(pft1000info->pFt1000Dev->net); + ft1000_destroy_dev(ft1000dev->net); + unregister_netdev(ft1000dev->net); DEBUG - ("ft1000_disconnect: network device unregisterd\n"); - free_netdev(pft1000info->pFt1000Dev->net); + ("ft1000_disconnect: network device unregistered\n"); + free_netdev(ft1000dev->net); } - usb_free_urb(pft1000info->pFt1000Dev->rx_urb); - usb_free_urb(pft1000info->pFt1000Dev->tx_urb); + usb_free_urb(ft1000dev->rx_urb); + usb_free_urb(ft1000dev->tx_urb); DEBUG("ft1000_disconnect: urb freed\n"); - kfree(pft1000info->pFt1000Dev); + kfree(ft1000dev); } kfree(pFileStart); @@ -263,24 +265,4 @@ static struct usb_driver ft1000_usb_driver = { .id_table = id_table, }; -static int __init usb_ft1000_init(void) -{ - int ret = 0; - - DEBUG("Initialize and register the driver\n"); - - ret = usb_register(&ft1000_usb_driver); - if (ret) - err("usb_register failed. Error number %d", ret); - - return ret; -} - -static void __exit usb_ft1000_exit(void) -{ - DEBUG("Deregister the driver\n"); - usb_deregister(&ft1000_usb_driver); -} - -module_init(usb_ft1000_init); -module_exit(usb_ft1000_exit); +module_usb_driver(ft1000_usb_driver); diff --git a/drivers/staging/ft1000/ft1000-usb/ft1000_usb.h b/drivers/staging/ft1000/ft1000-usb/ft1000_usb.h index a143e9ca4f0..2d4b02e2382 100644 --- a/drivers/staging/ft1000/ft1000-usb/ft1000_usb.h +++ b/drivers/staging/ft1000/ft1000-usb/ft1000_usb.h @@ -1,459 +1,69 @@ #ifndef _FT1000_USB_H_ #define _FT1000_USB_H_ -/*Jim*/ +#include "../ft1000.h" #include "ft1000_ioctl.h" #define FT1000_DRV_VER 0x01010403 -#define MODESZ 2 #define MAX_NUM_APP 6 #define MAX_MSG_LIMIT 200 #define NUM_OF_FREE_BUFFERS 1500 -// Driver message types -#define MEDIA_STATE 0x0010 -#define DSP_PROVISION 0x0030 -#define DSP_INIT_MSG 0x0050 -#define DSP_STORE_INFO 0x0070 -#define DSP_GET_INFO 0x0071 -#define GET_DRV_ERR_RPT_MSG 0x0073 -#define RSP_DRV_ERR_RPT_MSG 0x0074 - - -// Size of DPRAM Command -#define MAX_CMD_SQSIZE 1780 -#define SLOWQ_TYPE 0 #define PSEUDOSZ 16 -#define DSP_QID_OFFSET 4 - - -// MEMORY MAP FOR ELECTRABUZZ ASIC -#define FT1000_REG_DFIFO_STAT 0x0008 // Downlink FIFO status register -#define FT1000_REG_DPRAM_DATA 0x000C // DPRAM VALUE in DPRAM ADDR - -#define FT1000_DSP_LED 0xFFA // dsp led status for PAD device - -#define FT1000_MAG_DSP_LED 0x3FE // dsp led status for PAD device -#define FT1000_MAG_DSP_LED_INDX 0x1 // dsp led status for PAD device - -#define SUCCESS 0x00 - - -#define DRIVERID 0x00 - -// Driver Error Messages for DSP -#define DSP_CONDRESET_INFO 0x7ef2 -#define DSP_HB_INFO 0x7ef0 - -// Magnemite specific defines -#define hi_mag 0x6968 // Byte swap hi to avoid additional system call -#define ho_mag 0x6f68 // Byte swap ho to avoid additional system call - - - -struct media_msg { - struct pseudo_hdr pseudo; - u16 type; - u16 length; - u16 state; - u32 ip_addr; - u32 net_mask; - u32 gateway; - u32 dns_1; - u32 dns_2; -} __attribute__ ((packed)); - -struct dsp_init_msg { - struct pseudo_hdr pseudo; - u16 type; - u16 length; - u8 DspVer[DSPVERSZ]; // DSP version number - u8 HwSerNum[HWSERNUMSZ]; // Hardware Serial Number - u8 Sku[SKUSZ]; // SKU - u8 eui64[EUISZ]; // EUI64 - u8 ProductMode[MODESZ]; // Product Mode (Market/Production) - u8 RfCalVer[CALVERSZ]; // Rf Calibration version - u8 RfCalDate[CALDATESZ]; // Rf Calibration date -} __attribute__ ((packed)); - struct app_info_block { - u32 nTxMsg; // DPRAM msg sent to DSP with app_id - u32 nRxMsg; // DPRAM msg rcv from dsp with app_id - u32 nTxMsgReject; // DPRAM msg rejected due to DSP doorbell set - u32 nRxMsgMiss; // DPRAM msg dropped due to overflow - struct fown_struct *fileobject;// Application's file object - u16 app_id; // Application id + u32 nTxMsg; /* DPRAM msg sent to DSP with app_id */ + u32 nRxMsg; /* DPRAM msg rcv from dsp with app_id */ + u32 nTxMsgReject; /* DPRAM msg rejected due to DSP doorbell + * set + */ + u32 nRxMsgMiss; /* DPRAM msg dropped due to overflow */ + struct fown_struct *fileobject;/* Application's file object */ + u16 app_id; /* Application id */ int DspBCMsgFlag; - int NumOfMsg; // number of messages queued up + int NumOfMsg; /* number of messages queued up */ wait_queue_head_t wait_dpram_msg; - struct list_head app_sqlist; // link list of msgs for applicaton on slow queue -} __attribute__((packed)); - -struct prov_record { - struct list_head list; - u8 *pprov_data; -}; + struct list_head app_sqlist; /* link list of msgs for applicaton on + * slow queue + */ +} __packed; -/*end of Jim*/ -#define DEBUG(args...) printk(KERN_INFO args) +#define DEBUG(args...) pr_info(args) #define FALSE 0 #define TRUE 1 -#define STATUS_SUCCESS 0 -#define STATUS_FAILURE 0x1001 - #define FT1000_STATUS_CLOSING 0x01 -#define LARGE_TIMEOUT 5000 - -#define MAX_DSP_SESS_REC 1024 - -#define MAX_NUM_CARDS 32 - -#define DSPVERSZ 4 -#define HWSERNUMSZ 16 -#define SKUSZ 20 -#define EUISZ 8 -#define CALVERSZ 2 -#define CALDATESZ 6 -#define MODESZ 2 - -#define DSPID 0x20 -#define HOSTID 0x10 - -#define DSPOAM 0x80 -#define DSPAIRID 0x90 - -#define DRIVERID 0x00 -#define FMM 0x10 -#define NETWORKID 0x20 -#define AUTOLNCHID 0x30 -#define DSPLPBKID 0x40 - #define DSPBCMSGID 0x10 -#define ENET_MAX_SIZE 1514 -#define ENET_HEADER_SIZE 14 - - -#define CIS_NET_ADDR_OFFSET 0xff0 - -// MAGNEMITE specific - -#define FT1000_REG_MAG_UFDR 0x0000 // Uplink FIFO Data Register. - -#define FT1000_REG_MAG_UFDRL 0x0000 // Uplink FIFO Data Register low-word. - -#define FT1000_REG_MAG_UFDRH 0x0002 // Uplink FIFO Data Register high-word. - -#define FT1000_REG_MAG_UFER 0x0004 // Uplink FIFO End Register - -#define FT1000_REG_MAG_UFSR 0x0006 // Uplink FIFO Status Register - -#define FT1000_REG_MAG_DFR 0x0008 // Downlink FIFO Register - -#define FT1000_REG_MAG_DFRL 0x0008 // Downlink FIFO Register low-word - -#define FT1000_REG_MAG_DFRH 0x000a // Downlink FIFO Register high-word - -#define FT1000_REG_MAG_DFSR 0x000c // Downlink FIFO Status Register - -#define FT1000_REG_MAG_DPDATA 0x0010 // Dual Port RAM Indirect Data Register - -#define FT1000_REG_MAG_DPDATAL 0x0010 // Dual Port RAM Indirect Data Register low-word - -#define FT1000_REG_MAG_DPDATAH 0x0012 // Dual Port RAM Indirect Data Register high-word - -#define FT1000_REG_MAG_WATERMARK 0x002c // Supv. Control Reg. LLC register - -#define FT1000_REG_MAG_VERSION 0x0030 // LLC Version LLC register - - - -// Common - -#define FT1000_REG_DPRAM_ADDR 0x000E // DPRAM ADDRESS when card in IO mode - -#define FT1000_REG_SUP_CTRL 0x0020 // Supv. Control Reg. LLC register - -#define FT1000_REG_SUP_STAT 0x0022 // Supv. Status Reg LLC register - -#define FT1000_REG_RESET 0x0024 // Reset Reg LLC register - -#define FT1000_REG_SUP_ISR 0x0026 // Supv ISR LLC register - -#define FT1000_REG_SUP_IMASK 0x0028 // Supervisor Interrupt Mask LLC register - -#define FT1000_REG_DOORBELL 0x002a // Door Bell Reg LLC register - -#define FT1000_REG_ASIC_ID 0x002e // ASIC Identification Number - - // (Electrabuzz=0 Magnemite=TBD) - - - -// DSP doorbells - -#define FT1000_DB_DPRAM_RX 0x0001 // this value indicates that DSP has - - // data for host in DPRAM SlowQ - -#define FT1000_DB_DNLD_RX 0x0002 // Downloader handshake doorbell - -#define FT1000_ASIC_RESET_REQ 0x0004 - -#define FT1000_DSP_ASIC_RESET 0x0008 - - - -#define FT1000_DB_COND_RESET 0x0010 - - - -// Host doorbells - -#define FT1000_DB_DPRAM_TX 0x0100 // this value indicates that host has - - // data for DSP in DPRAM. - -#define FT1000_DB_DNLD_TX 0x0200 // Downloader handshake doorbell - -#define FT1000_ASIC_RESET_DSP 0x0400 - -#define FT1000_DB_HB 0x1000 // this value indicates that supervisor - - - -// Electrabuzz specific DPRAM mapping // has a heartbeat message for DSP. - -#define FT1000_DPRAM_BASE 0x1000 // 0x0000 to 0x07FF DPRAM 2Kx16 - R/W from PCMCIA or DSP - -#define FT1000_DPRAM_TX_BASE 0x1002 // TX AREA (SlowQ) - -#define FT1000_DPRAM_RX_BASE 0x1800 // RX AREA (SlowQ) - -#define FT1000_DPRAM_SIZE 0x1000 // 4K bytes - - - -#define FT1000_DRV_DEBUG 0x17E0 // Debug area for driver - -#define FT1000_FIFO_LEN 0x17FC // total length for DSP FIFO tracking - -#define FT1000_HI_HO 0x17FE // heartbeat with HI/HO - -#define FT1000_DSP_STATUS 0x1FFE // dsp status - non-zero is a request to reset dsp - - - -#define FT1000_DSP_CON_STATE 0x1FF8 // DSP Connection Status Info - -#define FT1000_DSP_LEDS 0x1FFA // DSP LEDS for rcv pwr strength, Rx data, Tx data - -#define DSP_TIMESTAMP 0x1FFC // dsp timestamp - -#define DSP_TIMESTAMP_DIFF 0x1FFA // difference of dsp timestamp in DPRAM and Pseudo header. - - - -#define FT1000_DPRAM_FEFE 0x1002 // Dsp Downloader handshake location - - - -#define FT1000_DSP_TIMER0 0x1FF0 - -#define FT1000_DSP_TIMER1 0x1FF2 - -#define FT1000_DSP_TIMER2 0x1FF4 - -#define FT1000_DSP_TIMER3 0x1FF6 - - - -// MEMORY MAP FOR MAGNEMITE - -#define FT1000_DPRAM_MAG_TX_BASE 0x0000 // TX AREA (SlowQ) - -#define FT1000_DPRAM_MAG_RX_BASE 0x0200 // RX AREA (SlowQ) - - - -#define FT1000_MAG_FIFO_LEN 0x1FF // total length for DSP FIFO tracking - -#define FT1000_MAG_FIFO_LEN_INDX 0x1 // low-word index - -#define FT1000_MAG_HI_HO 0x1FF // heartbeat with HI/HO - -#define FT1000_MAG_HI_HO_INDX 0x0 // high-word index - -#define FT1000_MAG_DSP_LEDS 0x3FE // dsp led status for PAD device - -#define FT1000_MAG_DSP_LEDS_INDX 0x1 // dsp led status for PAD device - - - -#define FT1000_MAG_DSP_CON_STATE 0x3FE // DSP Connection Status Info - -#define FT1000_MAG_DSP_CON_STATE_INDX 0x0 // DSP Connection Status Info - - - -#define FT1000_MAG_DPRAM_FEFE 0x000 // location for dsp ready indicator - -#define FT1000_MAG_DPRAM_FEFE_INDX 0x0 // location for dsp ready indicator - - - -#define FT1000_MAG_DSP_TIMER0 0x3FC - -#define FT1000_MAG_DSP_TIMER0_INDX 0x1 - - - -#define FT1000_MAG_DSP_TIMER1 0x3FC - -#define FT1000_MAG_DSP_TIMER1_INDX 0x0 - - - -#define FT1000_MAG_DSP_TIMER2 0x3FD - -#define FT1000_MAG_DSP_TIMER2_INDX 0x1 - - - -#define FT1000_MAG_DSP_TIMER3 0x3FD - -#define FT1000_MAG_DSP_TIMER3_INDX 0x0 - - - -#define FT1000_MAG_TOTAL_LEN 0x200 - -#define FT1000_MAG_TOTAL_LEN_INDX 0x1 - - - -#define FT1000_MAG_PH_LEN 0x200 - -#define FT1000_MAG_PH_LEN_INDX 0x0 - - - -#define FT1000_MAG_PORT_ID 0x201 - -#define FT1000_MAG_PORT_ID_INDX 0x0 - - - -// - -// Constants for the FT1000_REG_SUP_ISR - -// - -// Indicate the cause of an interrupt. - -// - -// SUPERVISOR ISR BIT MAPS - - - -#define ISR_EMPTY (u8)0x00 // no bits set in ISR - -#define ISR_DOORBELL_ACK (u8)0x01 // the doorbell i sent has been recieved. - -#define ISR_DOORBELL_PEND (u8)0x02 // doorbell for me - -#define ISR_RCV (u8)0x04 // packet received with no errors - -#define ISR_WATERMARK (u8)0x08 // - - - -// Interrupt mask register defines - -// note these are different from the ISR BIT MAPS. - -#define ISR_MASK_NONE 0x0000 - -#define ISR_MASK_DOORBELL_ACK 0x0001 - -#define ISR_MASK_DOORBELL_PEND 0x0002 - -#define ISR_MASK_RCV 0x0004 - -#define ISR_MASK_WATERMARK 0x0008 // Normally we will only mask the watermark interrupt when we want to enable interrupts. - -#define ISR_MASK_ALL 0xffff - - - -#define HOST_INTF_LE 0x0000 // Host interface little endian - -#define HOST_INTF_BE 0x0001 // Host interface big endian - - - -#define ISR_DEFAULT_MASK 0x7ff9 - - - -#define hi 0x6869 - -#define ho 0x686f - - - -#define FT1000_ASIC_RESET 0x80 // COR value for soft reset to PCMCIA core - -#define FT1000_ASIC_BITS 0x51 // Bits set in COR register under normal operation - -#define FT1000_ASIC_MAG_BITS 0x55 // Bits set in COR register under normal operation - - - -#define FT1000_COR_OFFSET 0x100 - - - -#define ELECTRABUZZ_ID 0 // ASIC ID for ELECTRABUZZ - -#define MAGNEMITE_ID 0x1a01 // ASIC ID for MAGNEMITE - - - -// Maximum times trying to get ASIC out of reset - +/* Electrabuzz specific DPRAM mapping */ +/* this is used by ft1000_usb driver - isn't that a bug? */ +#undef FT1000_DPRAM_RX_BASE +#define FT1000_DPRAM_RX_BASE 0x1800 /* RX AREA (SlowQ) */ + +/* MEMORY MAP FOR MAGNEMITE */ +/* the indexes are swapped comparing to PCMCIA - is it OK or a bug? */ +#undef FT1000_MAG_DSP_LED_INDX +#define FT1000_MAG_DSP_LED_INDX 0x1 /* dsp led status for PAD + * device + */ +#undef FT1000_MAG_DSP_CON_STATE_INDX +#define FT1000_MAG_DSP_CON_STATE_INDX 0x0 /* DSP Connection Status Info */ + +/* Maximum times trying to get ASIC out of reset */ #define MAX_ASIC_RESET_CNT 20 - - -#define DSP_RESET_BIT 0x1 - -#define ASIC_RESET_BIT 0x2 - -#define DSP_UNENCRYPTED 0x4 - -#define DSP_ENCRYPTED 0x8 - -#define EFUSE_MEM_DISABLE 0x0040 - - #define MAX_BUF_SIZE 4096 -struct drv_msg { - struct pseudo_hdr pseudo; - u16 type; - u16 length; - u8 data[0]; -} __attribute__ ((packed)); +struct ft1000_debug_dirs { + struct list_head list; + struct dentry *dent; + struct dentry *file; + int int_number; +}; -struct ft1000_device -{ +struct ft1000_usb { struct usb_device *dev; struct net_device *net; @@ -468,135 +78,78 @@ struct ft1000_device u8 bulk_in_endpointAddr; u8 bulk_out_endpointAddr; - //struct ft1000_ethernet_configuration configuration; - -// struct net_device_stats stats; //mbelian -} __attribute__ ((packed)); - -struct ft1000_debug_dirs { - struct list_head list; - struct dentry *dent; - struct dentry *file; - int int_number; -}; - -struct ft1000_info { - struct ft1000_device *pFt1000Dev; - struct net_device_stats stats; - - struct task_struct *pPollThread; - - unsigned char fcodeldr; - unsigned char bootmode; + struct task_struct *pPollThread; + unsigned char fcodeldr; + unsigned char bootmode; unsigned char usbboot; - unsigned short dspalive; - u16 ASIC_ID; - bool fProvComplete; - bool fCondResetPend; - bool fAppMsgPend; - char *pfwimg; - int fwimgsz; - u16 DrvErrNum; - u8 *pTestImage; - u16 AsicID; - unsigned long TestImageIndx; - unsigned long TestImageSz; - u8 TestImageEnable; - u8 TestImageReady; - int ASICResetNum; - int DspAsicReset; - int PktIntfErr; - int DSPResetNum; - int NumIOCTLBufs; - int IOCTLBufLvl; - int DeviceCreated; - int CardReady; - int NetDevRegDone; - u8 CardNumber; - u8 DeviceName[15]; - struct ft1000_debug_dirs nodes; - int registered; - int mediastate; - int dhcpflg; - u16 packetseqnum; - u8 squeseqnum; // sequence number on slow queue - spinlock_t dpram_lock; - spinlock_t fifo_lock; - u16 CurrentInterruptEnableMask; - int InterruptsEnabled; - u16 fifo_cnt; - u8 DspVer[DSPVERSZ]; // DSP version number - u8 HwSerNum[HWSERNUMSZ]; // Hardware Serial Number - u8 Sku[SKUSZ]; // SKU - u8 eui64[EUISZ]; // EUI64 - time_t ConTm; // Connection Time - u8 ProductMode[MODESZ]; - u8 RfCalVer[CALVERSZ]; - u8 RfCalDate[CALDATESZ]; - u16 DSP_TIME[4]; - u16 ProgSnr; - u16 LedStat; //mbelian - u16 ConStat; //mbelian - u16 ProgConStat; - struct list_head prov_list; - int appcnt; + unsigned short dspalive; + bool fProvComplete; + bool fCondResetPend; + bool fAppMsgPend; + int DeviceCreated; + int NetDevRegDone; + u8 CardNumber; + u8 DeviceName[15]; + struct ft1000_debug_dirs nodes; + spinlock_t fifo_lock; + int appcnt; struct app_info_block app_info[MAX_NUM_APP]; - u16 DSPInfoBlklen; - u16 DrvMsgPend; - int (*ft1000_reset)(struct net_device *dev); - u16 DSPInfoBlk[MAX_DSP_SESS_REC]; - union { - u16 Rec[MAX_DSP_SESS_REC]; - u32 MagRec[MAX_DSP_SESS_REC/2]; - } DSPSess; + u16 DrvMsgPend; unsigned short tempbuf[32]; - char netdevname[IFNAMSIZ]; - struct proc_dir_entry *ft1000_proc_dir; //mbelian -}; +} __packed; struct dpram_blk { - struct list_head list; - u16 *pbuffer; -} __attribute__ ((packed)); - -u16 ft1000_read_register(struct ft1000_device *ft1000dev, u16* Data, u16 nRegIndx); -u16 ft1000_write_register(struct ft1000_device *ft1000dev, u16 value, u16 nRegIndx); -u16 ft1000_read_dpram32(struct ft1000_device *ft1000dev, u16 indx, u8 *buffer, u16 cnt); -u16 ft1000_write_dpram32(struct ft1000_device *ft1000dev, u16 indx, u8 *buffer, u16 cnt); -u16 ft1000_read_dpram16(struct ft1000_device *ft1000dev, u16 indx, u8 *buffer, u8 highlow); -u16 ft1000_write_dpram16(struct ft1000_device *ft1000dev, u16 indx, u16 value, u8 highlow); -u16 fix_ft1000_read_dpram32(struct ft1000_device *ft1000dev, u16 indx, u8 *buffer); -u16 fix_ft1000_write_dpram32(struct ft1000_device *ft1000dev, u16 indx, u8 *buffer); + struct list_head list; + u16 *pbuffer; +} __packed; + +int ft1000_read_register(struct ft1000_usb *ft1000dev, + u16 *Data, u16 nRegIndx); +int ft1000_write_register(struct ft1000_usb *ft1000dev, + u16 value, u16 nRegIndx); +int ft1000_read_dpram32(struct ft1000_usb *ft1000dev, + u16 indx, u8 *buffer, u16 cnt); +int ft1000_write_dpram32(struct ft1000_usb *ft1000dev, + u16 indx, u8 *buffer, u16 cnt); +int ft1000_read_dpram16(struct ft1000_usb *ft1000dev, + u16 indx, u8 *buffer, u8 highlow); +int ft1000_write_dpram16(struct ft1000_usb *ft1000dev, + u16 indx, u16 value, u8 highlow); +int fix_ft1000_read_dpram32(struct ft1000_usb *ft1000dev, + u16 indx, u8 *buffer); +int fix_ft1000_write_dpram32(struct ft1000_usb *ft1000dev, + u16 indx, u8 *buffer); extern void *pFileStart; extern size_t FileLength; extern int numofmsgbuf; -int ft1000_close (struct net_device *dev); -u16 scram_dnldr(struct ft1000_device *ft1000dev, void *pFileStart, u32 FileLength); +int ft1000_close(struct net_device *dev); +int scram_dnldr(struct ft1000_usb *ft1000dev, void *pFileStart, + u32 FileLength); extern struct list_head freercvpool; -extern spinlock_t free_buff_lock; // lock to arbitrate free buffer list for receive command data -int ft1000_create_dev(struct ft1000_device *dev); +/* lock to arbitrate free buffer list for receive command data */ +extern spinlock_t free_buff_lock; + +int ft1000_create_dev(struct ft1000_usb *dev); void ft1000_destroy_dev(struct net_device *dev); -extern void CardSendCommand(struct ft1000_device *ft1000dev, void *ptempbuffer, int size); +extern void card_send_command(struct ft1000_usb *ft1000dev, + void *ptempbuffer, int size); struct dpram_blk *ft1000_get_buffer(struct list_head *bufflist); void ft1000_free_buffer(struct dpram_blk *pdpram_blk, struct list_head *plist); -char *getfw (char *fn, size_t *pimgsz); - -int dsp_reload(struct ft1000_device *ft1000dev); -u16 init_ft1000_netdev(struct ft1000_device *ft1000dev); +int dsp_reload(struct ft1000_usb *ft1000dev); +int init_ft1000_netdev(struct ft1000_usb *ft1000dev); struct usb_interface; -int reg_ft1000_netdev(struct ft1000_device *ft1000dev, struct usb_interface *intf); -int ft1000_poll(void* dev_id); +int reg_ft1000_netdev(struct ft1000_usb *ft1000dev, + struct usb_interface *intf); +int ft1000_poll(void *dev_id); int ft1000_init_proc(struct net_device *dev); void ft1000_cleanup_proc(struct ft1000_info *info); - - -#endif +#endif /* _FT1000_USB_H_ */ diff --git a/drivers/staging/ft1000/ft1000.h b/drivers/staging/ft1000/ft1000.h new file mode 100644 index 00000000000..db57430f3b9 --- /dev/null +++ b/drivers/staging/ft1000/ft1000.h @@ -0,0 +1,368 @@ +/* + * Common structures and definitions for FT1000 Flarion Flash OFDM PCMCIA and + * USB devices. + * + * Originally copyright (c) 2002 Flarion Technologies + * + */ + +#define DSPVERSZ 4 +#define HWSERNUMSZ 16 +#define SKUSZ 20 +#define EUISZ 8 +#define MODESZ 2 +#define CALVERSZ 2 +#define CALDATESZ 6 + +#define ELECTRABUZZ_ID 0 /* ASIC ID for Electrabuzz */ +#define MAGNEMITE_ID 0x1a01 /* ASIC ID for Magnemite */ + +/* MEMORY MAP common to both ELECTRABUZZ and MAGNEMITE */ +#define FT1000_REG_DPRAM_ADDR 0x000E /* DPADR - Dual Port Ram Indirect + * Address Register + */ +#define FT1000_REG_SUP_CTRL 0x0020 /* HCTR - Host Control Register */ +#define FT1000_REG_SUP_STAT 0x0022 /* HSTAT - Host Status Register */ +#define FT1000_REG_RESET 0x0024 /* HCTR - Host Control Register */ +#define FT1000_REG_SUP_ISR 0x0026 /* HISR - Host Interrupt Status + * Register + */ +#define FT1000_REG_SUP_IMASK 0x0028 /* HIMASK - Host Interrupt Mask */ +#define FT1000_REG_DOORBELL 0x002a /* DBELL - Door Bell Register */ +#define FT1000_REG_ASIC_ID 0x002e /* ASICID - ASIC Identification + * Number + */ + +/* MEMORY MAP FOR ELECTRABUZZ ASIC */ +#define FT1000_REG_UFIFO_STAT 0x0000 /* UFSR - Uplink FIFO status register */ +#define FT1000_REG_UFIFO_BEG 0x0002 /* UFBR - Uplink FIFO beginning + * register + */ +#define FT1000_REG_UFIFO_MID 0x0004 /* UFMR - Uplink FIFO middle register */ +#define FT1000_REG_UFIFO_END 0x0006 /* UFER - Uplink FIFO end register */ +#define FT1000_REG_DFIFO_STAT 0x0008 /* DFSR - Downlink FIFO status + * register + */ +#define FT1000_REG_DFIFO 0x000A /* DFR - Downlink FIFO Register */ +#define FT1000_REG_DPRAM_DATA 0x000C /* DPRAM - Dual Port Indirect + * Data Register + */ +#define FT1000_REG_WATERMARK 0x0010 /* WMARK - Watermark Register */ + +/* MEMORY MAP FOR MAGNEMITE */ +#define FT1000_REG_MAG_UFDR 0x0000 /* UFDR - Uplink FIFO Data + * Register (32-bits) + */ +#define FT1000_REG_MAG_UFDRL 0x0000 /* UFDRL - Uplink FIFO Data + * Register low-word (16-bits) + */ +#define FT1000_REG_MAG_UFDRH 0x0002 /* UFDRH - Uplink FIFO Data Register + * high-word (16-bits) + */ +#define FT1000_REG_MAG_UFER 0x0004 /* UFER - Uplink FIFO End Register */ +#define FT1000_REG_MAG_UFSR 0x0006 /* UFSR - Uplink FIFO Status Register */ +#define FT1000_REG_MAG_DFR 0x0008 /* DFR - Downlink FIFO Register + * (32-bits) + */ +#define FT1000_REG_MAG_DFRL 0x0008 /* DFRL - Downlink FIFO Register + * low-word (16-bits) + */ +#define FT1000_REG_MAG_DFRH 0x000a /* DFRH - Downlink FIFO Register + * high-word (16-bits) + */ +#define FT1000_REG_MAG_DFSR 0x000c /* DFSR - Downlink FIFO Status + * Register + */ +#define FT1000_REG_MAG_DPDATA 0x0010 /* DPDATA - Dual Port RAM Indirect + * Data Register (32-bits) + */ +#define FT1000_REG_MAG_DPDATAL 0x0010 /* DPDATAL - Dual Port RAM Indirect + * Data Register low-word (16-bits) + */ +#define FT1000_REG_MAG_DPDATAH 0x0012 /* DPDATAH - Dual Port RAM Indirect Data + * Register high-word (16-bits) + */ +#define FT1000_REG_MAG_WATERMARK 0x002c /* WMARK - Watermark Register */ +#define FT1000_REG_MAG_VERSION 0x0030 /* LLC Version */ + +/* Reserved Dual Port RAM offsets for Electrabuzz */ +#define FT1000_DPRAM_TX_BASE 0x0002 /* Host to PC Card Messaging Area */ +#define FT1000_DPRAM_RX_BASE 0x0800 /* PC Card to Host Messaging Area */ +#define FT1000_FIFO_LEN 0x07FC /* total length for DSP FIFO tracking */ +#define FT1000_HI_HO 0x07FE /* heartbeat with HI/HO */ +#define FT1000_DSP_STATUS 0x0FFE /* dsp status - non-zero is a request + * to reset dsp + */ +#define FT1000_DSP_LED 0x0FFA /* dsp led status for PAD device */ +#define FT1000_DSP_CON_STATE 0x0FF8 /* DSP Connection Status Info */ +#define FT1000_DPRAM_FEFE 0x0002 /* location for dsp ready indicator */ +#define FT1000_DSP_TIMER0 0x1FF0 /* Timer Field from Basestation */ +#define FT1000_DSP_TIMER1 0x1FF2 /* Timer Field from Basestation */ +#define FT1000_DSP_TIMER2 0x1FF4 /* Timer Field from Basestation */ +#define FT1000_DSP_TIMER3 0x1FF6 /* Timer Field from Basestation */ + +/* Reserved Dual Port RAM offsets for Magnemite */ +#define FT1000_DPRAM_MAG_TX_BASE 0x0000 /* Host to PC Card + * Messaging Area + */ +#define FT1000_DPRAM_MAG_RX_BASE 0x0200 /* PC Card to Host + * Messaging Area + */ + +#define FT1000_MAG_FIFO_LEN 0x1FF /* total length for DSP + * FIFO tracking + */ +#define FT1000_MAG_FIFO_LEN_INDX 0x1 /* low-word index */ +#define FT1000_MAG_HI_HO 0x1FF /* heartbeat with HI/HO */ +#define FT1000_MAG_HI_HO_INDX 0x0 /* high-word index */ +#define FT1000_MAG_DSP_LED 0x3FE /* dsp led status for + * PAD device + */ +#define FT1000_MAG_DSP_LED_INDX 0x0 /* dsp led status for + * PAD device + */ +#define FT1000_MAG_DSP_CON_STATE 0x3FE /* DSP Connection Status Info */ +#define FT1000_MAG_DSP_CON_STATE_INDX 0x1 /* DSP Connection Status Info */ +#define FT1000_MAG_DPRAM_FEFE 0x000 /* location for dsp ready + * indicator + */ +#define FT1000_MAG_DPRAM_FEFE_INDX 0x0 /* location for dsp ready + * indicator + */ +#define FT1000_MAG_DSP_TIMER0 0x3FC /* Timer Field from + * Basestation + */ +#define FT1000_MAG_DSP_TIMER0_INDX 0x1 +#define FT1000_MAG_DSP_TIMER1 0x3FC /* Timer Field from + * Basestation + */ +#define FT1000_MAG_DSP_TIMER1_INDX 0x0 +#define FT1000_MAG_DSP_TIMER2 0x3FD /* Timer Field from + * Basestation + */ +#define FT1000_MAG_DSP_TIMER2_INDX 0x1 +#define FT1000_MAG_DSP_TIMER3 0x3FD /* Timer Field from + * Basestation + */ +#define FT1000_MAG_DSP_TIMER3_INDX 0x0 +#define FT1000_MAG_TOTAL_LEN 0x200 +#define FT1000_MAG_TOTAL_LEN_INDX 0x1 +#define FT1000_MAG_PH_LEN 0x200 +#define FT1000_MAG_PH_LEN_INDX 0x0 +#define FT1000_MAG_PORT_ID 0x201 +#define FT1000_MAG_PORT_ID_INDX 0x0 + +#define HOST_INTF_LE 0x0 /* Host interface little endian mode */ +#define HOST_INTF_BE 0x1 /* Host interface big endian mode */ + +/* FT1000 to Host Doorbell assignments */ +#define FT1000_DB_DPRAM_RX 0x0001 /* this value indicates that DSP + * has data for host in DPRAM + */ +#define FT1000_DB_DNLD_RX 0x0002 /* Downloader handshake doorbell */ +#define FT1000_ASIC_RESET_REQ 0x0004 /* DSP requesting host to + * reset the ASIC + */ +#define FT1000_DSP_ASIC_RESET 0x0008 /* DSP indicating host that + * it will reset the ASIC + */ +#define FT1000_DB_COND_RESET 0x0010 /* DSP request for a card reset. */ + +/* Host to FT1000 Doorbell assignments */ +#define FT1000_DB_DPRAM_TX 0x0100 /* this value indicates that host + * has data for DSP in DPRAM. + */ +#define FT1000_DB_DNLD_TX 0x0200 /* Downloader handshake doorbell */ +#define FT1000_ASIC_RESET_DSP 0x0400 /* Responds to FT1000_ASIC_RESET_REQ */ +#define FT1000_DB_HB 0x1000 /* Indicates that supervisor has a + * heartbeat message for DSP. + */ + +#define hi 0x6869 /* PC Card heartbeat values */ +#define ho 0x686f /* PC Card heartbeat values */ + +/* Magnemite specific defines */ +#define hi_mag 0x6968 /* Byte swap hi to avoid + * additional system call + */ +#define ho_mag 0x6f68 /* Byte swap ho to avoid + * additional system call + */ + +/* Bit field definitions for Host Interrupt Status Register */ +/* Indicate the cause of an interrupt. */ +#define ISR_EMPTY 0x00 /* no bits set */ +#define ISR_DOORBELL_ACK 0x01 /* Doorbell acknowledge from DSP */ +#define ISR_DOORBELL_PEND 0x02 /* Doorbell pending from DSP */ +#define ISR_RCV 0x04 /* Packet available in Downlink FIFO */ +#define ISR_WATERMARK 0x08 /* Watermark requirements satisfied */ + +/* Bit field definition for Host Interrupt Mask */ +#define ISR_MASK_NONE 0x0000 /* no bits set */ +#define ISR_MASK_DOORBELL_ACK 0x0001 /* Doorbell acknowledge mask */ +#define ISR_MASK_DOORBELL_PEND 0x0002 /* Doorbell pending mask */ +#define ISR_MASK_RCV 0x0004 /* Downlink Packet available mask */ +#define ISR_MASK_WATERMARK 0x0008 /* Watermark interrupt mask */ +#define ISR_MASK_ALL 0xffff /* Mask all interrupts */ +/* Default interrupt mask + * (Enable Doorbell pending and Packet available interrupts) + */ +#define ISR_DEFAULT_MASK 0x7ff9 + +/* Bit field definition for Host Control Register */ +#define DSP_RESET_BIT 0x0001 /* Bit field to control + * dsp reset state + */ + /* (0 = out of reset 1 = reset) */ +#define ASIC_RESET_BIT 0x0002 /* Bit field to control + * ASIC reset state + */ + /* (0 = out of reset 1 = reset) */ +#define DSP_UNENCRYPTED 0x0004 +#define DSP_ENCRYPTED 0x0008 +#define EFUSE_MEM_DISABLE 0x0040 + +/* Application specific IDs */ +#define DSPID 0x20 +#define HOSTID 0x10 +#define DSPAIRID 0x90 +#define DRIVERID 0x00 +#define NETWORKID 0x20 + +/* Size of DPRAM Message */ +#define MAX_CMD_SQSIZE 1780 + +#define ENET_MAX_SIZE 1514 +#define ENET_HEADER_SIZE 14 + +#define SLOWQ_TYPE 0 +#define FASTQ_TYPE 1 + +#define MAX_DSP_SESS_REC 1024 + +#define DSP_QID_OFFSET 4 + +/* Driver message types */ +#define MEDIA_STATE 0x0010 +#define TIME_UPDATE 0x0020 +#define DSP_PROVISION 0x0030 +#define DSP_INIT_MSG 0x0050 +#define DSP_HIBERNATE 0x0060 +#define DSP_STORE_INFO 0x0070 +#define DSP_GET_INFO 0x0071 +#define GET_DRV_ERR_RPT_MSG 0x0073 +#define RSP_DRV_ERR_RPT_MSG 0x0074 + +/* Driver Error Messages for DSP */ +#define DSP_HB_INFO 0x7ef0 +#define DSP_FIFO_INFO 0x7ef1 +#define DSP_CONDRESET_INFO 0x7ef2 +#define DSP_CMDLEN_INFO 0x7ef3 +#define DSP_CMDPHCKSUM_INFO 0x7ef4 +#define DSP_PKTPHCKSUM_INFO 0x7ef5 +#define DSP_PKTLEN_INFO 0x7ef6 +#define DSP_USER_RESET 0x7ef7 +#define FIFO_FLUSH_MAXLIMIT 0x7ef8 +#define FIFO_FLUSH_BADCNT 0x7ef9 +#define FIFO_ZERO_LEN 0x7efa + +/* Pseudo Header structure */ +struct pseudo_hdr { + unsigned short length; /* length of msg body */ + unsigned char source; /* hardware source id */ + /* Host = 0x10 */ + /* Dsp = 0x20 */ + unsigned char destination; /* hardware destination id + * (refer to source) + */ + unsigned char portdest; /* software destination port id */ + /* Host = 0x00 */ + /* Applicaton Broadcast = 0x10 */ + /* Network Stack = 0x20 */ + /* Dsp OAM = 0x80 */ + /* Dsp Airlink = 0x90 */ + /* Dsp Loader = 0xa0 */ + /* Dsp MIP = 0xb0 */ + unsigned char portsrc; /* software source port id + * (refer to portdest) + */ + unsigned short sh_str_id; /* not used */ + unsigned char control; /* not used */ + unsigned char rsvd1; + unsigned char seq_num; /* message sequence number */ + unsigned char rsvd2; + unsigned short qos_class; /* not used */ + unsigned short checksum; /* pseudo header checksum */ +} __packed; + +struct drv_msg { + struct pseudo_hdr pseudo; + u16 type; + u16 length; + u8 data[0]; +} __packed; + +struct media_msg { + struct pseudo_hdr pseudo; + u16 type; + u16 length; + u16 state; + u32 ip_addr; + u32 net_mask; + u32 gateway; + u32 dns_1; + u32 dns_2; +} __packed; + +struct dsp_init_msg { + struct pseudo_hdr pseudo; + u16 type; + u16 length; + u8 DspVer[DSPVERSZ]; /* DSP version number */ + u8 HwSerNum[HWSERNUMSZ]; /* Hardware Serial Number */ + u8 Sku[SKUSZ]; /* SKU */ + u8 eui64[EUISZ]; /* EUI64 */ + u8 ProductMode[MODESZ]; /* Product Mode (Market/Production) */ + u8 RfCalVer[CALVERSZ]; /* Rf Calibration version */ + u8 RfCalDate[CALDATESZ]; /* Rf Calibration date */ +} __packed; + +struct prov_record { + struct list_head list; + u8 *pprov_data; +}; + +struct ft1000_info { + void *priv; + struct net_device_stats stats; + u16 DrvErrNum; + u16 AsicID; + int CardReady; + int registered; + int mediastate; + u8 squeseqnum; /* sequence number on slow queue */ + spinlock_t dpram_lock; + u16 fifo_cnt; + u8 DspVer[DSPVERSZ]; /* DSP version number */ + u8 HwSerNum[HWSERNUMSZ]; /* Hardware Serial Number */ + u8 Sku[SKUSZ]; /* SKU */ + u8 eui64[EUISZ]; /* EUI64 */ + time_t ConTm; /* Connection Time */ + u8 ProductMode[MODESZ]; + u8 RfCalVer[CALVERSZ]; + u8 RfCalDate[CALDATESZ]; + u16 DSP_TIME[4]; + u16 LedStat; + u16 ConStat; + u16 ProgConStat; + struct list_head prov_list; + u16 DSPInfoBlklen; + int (*ft1000_reset)(void *); + u16 DSPInfoBlk[MAX_DSP_SESS_REC]; + union { + u16 Rec[MAX_DSP_SESS_REC]; + u32 MagRec[MAX_DSP_SESS_REC/2]; + } DSPSess; + struct proc_dir_entry *ft1000_proc_dir; + char netdevname[IFNAMSIZ]; +}; |
