~ubuntu-branches/ubuntu/precise/linux-lowlatency/precise

« back to all changes in this revision

Viewing changes to drivers/scsi/aic94xx/aic94xx_sds.c

  • Committer: Package Import Robot
  • Author(s): Alessio Igor Bogani
  • Date: 2011-10-26 11:13:05 UTC
  • Revision ID: package-import@ubuntu.com-20111026111305-tz023xykf0i6eosh
Tags: upstream-3.2.0
ImportĀ upstreamĀ versionĀ 3.2.0

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
 * Aic94xx SAS/SATA driver access to shared data structures and memory
 
3
 * maps.
 
4
 *
 
5
 * Copyright (C) 2005 Adaptec, Inc.  All rights reserved.
 
6
 * Copyright (C) 2005 Luben Tuikov <luben_tuikov@adaptec.com>
 
7
 *
 
8
 * This file is licensed under GPLv2.
 
9
 *
 
10
 * This file is part of the aic94xx driver.
 
11
 *
 
12
 * The aic94xx driver is free software; you can redistribute it and/or
 
13
 * modify it under the terms of the GNU General Public License as
 
14
 * published by the Free Software Foundation; version 2 of the
 
15
 * License.
 
16
 *
 
17
 * The aic94xx driver is distributed in the hope that it will be useful,
 
18
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 
19
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 
20
 * General Public License for more details.
 
21
 *
 
22
 * You should have received a copy of the GNU General Public License
 
23
 * along with the aic94xx driver; if not, write to the Free Software
 
24
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 
25
 *
 
26
 */
 
27
 
 
28
#include <linux/pci.h>
 
29
#include <linux/slab.h>
 
30
#include <linux/delay.h>
 
31
 
 
32
#include "aic94xx.h"
 
33
#include "aic94xx_reg.h"
 
34
#include "aic94xx_sds.h"
 
35
 
 
36
/* ---------- OCM stuff ---------- */
 
37
 
 
38
struct asd_ocm_dir_ent {
 
39
        u8 type;
 
40
        u8 offs[3];
 
41
        u8 _r1;
 
42
        u8 size[3];
 
43
} __attribute__ ((packed));
 
44
 
 
45
struct asd_ocm_dir {
 
46
        char sig[2];
 
47
        u8   _r1[2];
 
48
        u8   major;          /* 0 */
 
49
        u8   minor;          /* 0 */
 
50
        u8   _r2;
 
51
        u8   num_de;
 
52
        struct asd_ocm_dir_ent entry[15];
 
53
} __attribute__ ((packed));
 
54
 
 
55
#define OCM_DE_OCM_DIR                  0x00
 
56
#define OCM_DE_WIN_DRVR                 0x01
 
57
#define OCM_DE_BIOS_CHIM                0x02
 
58
#define OCM_DE_RAID_ENGN                0x03
 
59
#define OCM_DE_BIOS_INTL                0x04
 
60
#define OCM_DE_BIOS_CHIM_OSM            0x05
 
61
#define OCM_DE_BIOS_CHIM_DYNAMIC        0x06
 
62
#define OCM_DE_ADDC2C_RES0              0x07
 
63
#define OCM_DE_ADDC2C_RES1              0x08
 
64
#define OCM_DE_ADDC2C_RES2              0x09
 
65
#define OCM_DE_ADDC2C_RES3              0x0A
 
66
 
 
67
#define OCM_INIT_DIR_ENTRIES    5
 
68
/***************************************************************************
 
69
*  OCM directory default
 
70
***************************************************************************/
 
71
static struct asd_ocm_dir OCMDirInit =
 
72
{
 
73
        .sig = {0x4D, 0x4F},    /* signature */
 
74
        .num_de = OCM_INIT_DIR_ENTRIES, /* no. of directory entries */
 
75
};
 
76
 
 
77
/***************************************************************************
 
78
*  OCM directory Entries default
 
79
***************************************************************************/
 
80
static struct asd_ocm_dir_ent OCMDirEntriesInit[OCM_INIT_DIR_ENTRIES] =
 
81
{
 
82
        {
 
83
                .type = (OCM_DE_ADDC2C_RES0),   /* Entry type  */
 
84
                .offs = {128},                  /* Offset */
 
85
                .size = {0, 4},                 /* size */
 
86
        },
 
87
        {
 
88
                .type = (OCM_DE_ADDC2C_RES1),   /* Entry type  */
 
89
                .offs = {128, 4},               /* Offset */
 
90
                .size = {0, 4},                 /* size */
 
91
        },
 
92
        {
 
93
                .type = (OCM_DE_ADDC2C_RES2),   /* Entry type  */
 
94
                .offs = {128, 8},               /* Offset */
 
95
                .size = {0, 4},                 /* size */
 
96
        },
 
97
        {
 
98
                .type = (OCM_DE_ADDC2C_RES3),   /* Entry type  */
 
99
                .offs = {128, 12},              /* Offset */
 
100
                .size = {0, 4},                 /* size */
 
101
        },
 
102
        {
 
103
                .type = (OCM_DE_WIN_DRVR),      /* Entry type  */
 
104
                .offs = {128, 16},              /* Offset */
 
105
                .size = {128, 235, 1},          /* size */
 
106
        },
 
107
};
 
108
 
 
109
struct asd_bios_chim_struct {
 
110
        char sig[4];
 
111
        u8   major;          /* 1 */
 
112
        u8   minor;          /* 0 */
 
113
        u8   bios_major;
 
114
        u8   bios_minor;
 
115
        __le32  bios_build;
 
116
        u8   flags;
 
117
        u8   pci_slot;
 
118
        __le16  ue_num;
 
119
        __le16  ue_size;
 
120
        u8  _r[14];
 
121
        /* The unit element array is right here.
 
122
         */
 
123
} __attribute__ ((packed));
 
124
 
 
125
/**
 
126
 * asd_read_ocm_seg - read an on chip memory (OCM) segment
 
127
 * @asd_ha: pointer to the host adapter structure
 
128
 * @buffer: where to write the read data
 
129
 * @offs: offset into OCM where to read from
 
130
 * @size: how many bytes to read
 
131
 *
 
132
 * Return the number of bytes not read. Return 0 on success.
 
133
 */
 
134
static int asd_read_ocm_seg(struct asd_ha_struct *asd_ha, void *buffer,
 
135
                            u32 offs, int size)
 
136
{
 
137
        u8 *p = buffer;
 
138
        if (unlikely(asd_ha->iospace))
 
139
                asd_read_reg_string(asd_ha, buffer, offs+OCM_BASE_ADDR, size);
 
140
        else {
 
141
                for ( ; size > 0; size--, offs++, p++)
 
142
                        *p = asd_read_ocm_byte(asd_ha, offs);
 
143
        }
 
144
        return size;
 
145
}
 
146
 
 
147
static int asd_read_ocm_dir(struct asd_ha_struct *asd_ha,
 
148
                            struct asd_ocm_dir *dir, u32 offs)
 
149
{
 
150
        int err = asd_read_ocm_seg(asd_ha, dir, offs, sizeof(*dir));
 
151
        if (err) {
 
152
                ASD_DPRINTK("couldn't read ocm segment\n");
 
153
                return err;
 
154
        }
 
155
 
 
156
        if (dir->sig[0] != 'M' || dir->sig[1] != 'O') {
 
157
                ASD_DPRINTK("no valid dir signature(%c%c) at start of OCM\n",
 
158
                            dir->sig[0], dir->sig[1]);
 
159
                return -ENOENT;
 
160
        }
 
161
        if (dir->major != 0) {
 
162
                asd_printk("unsupported major version of ocm dir:0x%x\n",
 
163
                           dir->major);
 
164
                return -ENOENT;
 
165
        }
 
166
        dir->num_de &= 0xf;
 
167
        return 0;
 
168
}
 
169
 
 
170
/**
 
171
 * asd_write_ocm_seg - write an on chip memory (OCM) segment
 
172
 * @asd_ha: pointer to the host adapter structure
 
173
 * @buffer: where to read the write data
 
174
 * @offs: offset into OCM to write to
 
175
 * @size: how many bytes to write
 
176
 *
 
177
 * Return the number of bytes not written. Return 0 on success.
 
178
 */
 
179
static void asd_write_ocm_seg(struct asd_ha_struct *asd_ha, void *buffer,
 
180
                            u32 offs, int size)
 
181
{
 
182
        u8 *p = buffer;
 
183
        if (unlikely(asd_ha->iospace))
 
184
                asd_write_reg_string(asd_ha, buffer, offs+OCM_BASE_ADDR, size);
 
185
        else {
 
186
                for ( ; size > 0; size--, offs++, p++)
 
187
                        asd_write_ocm_byte(asd_ha, offs, *p);
 
188
        }
 
189
        return;
 
190
}
 
191
 
 
192
#define THREE_TO_NUM(X) ((X)[0] | ((X)[1] << 8) | ((X)[2] << 16))
 
193
 
 
194
static int asd_find_dir_entry(struct asd_ocm_dir *dir, u8 type,
 
195
                              u32 *offs, u32 *size)
 
196
{
 
197
        int i;
 
198
        struct asd_ocm_dir_ent *ent;
 
199
 
 
200
        for (i = 0; i < dir->num_de; i++) {
 
201
                if (dir->entry[i].type == type)
 
202
                        break;
 
203
        }
 
204
        if (i >= dir->num_de)
 
205
                return -ENOENT;
 
206
        ent = &dir->entry[i];
 
207
        *offs = (u32) THREE_TO_NUM(ent->offs);
 
208
        *size = (u32) THREE_TO_NUM(ent->size);
 
209
        return 0;
 
210
}
 
211
 
 
212
#define OCM_BIOS_CHIM_DE  2
 
213
#define BC_BIOS_PRESENT   1
 
214
 
 
215
static int asd_get_bios_chim(struct asd_ha_struct *asd_ha,
 
216
                             struct asd_ocm_dir *dir)
 
217
{
 
218
        int err;
 
219
        struct asd_bios_chim_struct *bc_struct;
 
220
        u32 offs, size;
 
221
 
 
222
        err = asd_find_dir_entry(dir, OCM_BIOS_CHIM_DE, &offs, &size);
 
223
        if (err) {
 
224
                ASD_DPRINTK("couldn't find BIOS_CHIM dir ent\n");
 
225
                goto out;
 
226
        }
 
227
        err = -ENOMEM;
 
228
        bc_struct = kmalloc(sizeof(*bc_struct), GFP_KERNEL);
 
229
        if (!bc_struct) {
 
230
                asd_printk("no memory for bios_chim struct\n");
 
231
                goto out;
 
232
        }
 
233
        err = asd_read_ocm_seg(asd_ha, (void *)bc_struct, offs,
 
234
                               sizeof(*bc_struct));
 
235
        if (err) {
 
236
                ASD_DPRINTK("couldn't read ocm segment\n");
 
237
                goto out2;
 
238
        }
 
239
        if (strncmp(bc_struct->sig, "SOIB", 4)
 
240
            && strncmp(bc_struct->sig, "IPSA", 4)) {
 
241
                ASD_DPRINTK("BIOS_CHIM entry has no valid sig(%c%c%c%c)\n",
 
242
                            bc_struct->sig[0], bc_struct->sig[1],
 
243
                            bc_struct->sig[2], bc_struct->sig[3]);
 
244
                err = -ENOENT;
 
245
                goto out2;
 
246
        }
 
247
        if (bc_struct->major != 1) {
 
248
                asd_printk("BIOS_CHIM unsupported major version:0x%x\n",
 
249
                           bc_struct->major);
 
250
                err = -ENOENT;
 
251
                goto out2;
 
252
        }
 
253
        if (bc_struct->flags & BC_BIOS_PRESENT) {
 
254
                asd_ha->hw_prof.bios.present = 1;
 
255
                asd_ha->hw_prof.bios.maj = bc_struct->bios_major;
 
256
                asd_ha->hw_prof.bios.min = bc_struct->bios_minor;
 
257
                asd_ha->hw_prof.bios.bld = le32_to_cpu(bc_struct->bios_build);
 
258
                ASD_DPRINTK("BIOS present (%d,%d), %d\n",
 
259
                            asd_ha->hw_prof.bios.maj,
 
260
                            asd_ha->hw_prof.bios.min,
 
261
                            asd_ha->hw_prof.bios.bld);
 
262
        }
 
263
        asd_ha->hw_prof.ue.num = le16_to_cpu(bc_struct->ue_num);
 
264
        asd_ha->hw_prof.ue.size= le16_to_cpu(bc_struct->ue_size);
 
265
        ASD_DPRINTK("ue num:%d, ue size:%d\n", asd_ha->hw_prof.ue.num,
 
266
                    asd_ha->hw_prof.ue.size);
 
267
        size = asd_ha->hw_prof.ue.num * asd_ha->hw_prof.ue.size;
 
268
        if (size > 0) {
 
269
                err = -ENOMEM;
 
270
                asd_ha->hw_prof.ue.area = kmalloc(size, GFP_KERNEL);
 
271
                if (!asd_ha->hw_prof.ue.area)
 
272
                        goto out2;
 
273
                err = asd_read_ocm_seg(asd_ha, (void *)asd_ha->hw_prof.ue.area,
 
274
                                       offs + sizeof(*bc_struct), size);
 
275
                if (err) {
 
276
                        kfree(asd_ha->hw_prof.ue.area);
 
277
                        asd_ha->hw_prof.ue.area = NULL;
 
278
                        asd_ha->hw_prof.ue.num  = 0;
 
279
                        asd_ha->hw_prof.ue.size = 0;
 
280
                        ASD_DPRINTK("couldn't read ue entries(%d)\n", err);
 
281
                }
 
282
        }
 
283
out2:
 
284
        kfree(bc_struct);
 
285
out:
 
286
        return err;
 
287
}
 
288
 
 
289
static void
 
290
asd_hwi_initialize_ocm_dir (struct asd_ha_struct *asd_ha)
 
291
{
 
292
        int i;
 
293
 
 
294
        /* Zero OCM */
 
295
        for (i = 0; i < OCM_MAX_SIZE; i += 4)
 
296
                asd_write_ocm_dword(asd_ha, i, 0);
 
297
 
 
298
        /* Write Dir */
 
299
        asd_write_ocm_seg(asd_ha, &OCMDirInit, 0,
 
300
                          sizeof(struct asd_ocm_dir));
 
301
 
 
302
        /* Write Dir Entries */
 
303
        for (i = 0; i < OCM_INIT_DIR_ENTRIES; i++)
 
304
                asd_write_ocm_seg(asd_ha, &OCMDirEntriesInit[i],
 
305
                                  sizeof(struct asd_ocm_dir) +
 
306
                                  (i * sizeof(struct asd_ocm_dir_ent))
 
307
                                  , sizeof(struct asd_ocm_dir_ent));
 
308
 
 
309
}
 
310
 
 
311
static int
 
312
asd_hwi_check_ocm_access (struct asd_ha_struct *asd_ha)
 
313
{
 
314
        struct pci_dev *pcidev = asd_ha->pcidev;
 
315
        u32 reg;
 
316
        int err = 0;
 
317
        u32 v;
 
318
 
 
319
        /* check if OCM has been initialized by BIOS */
 
320
        reg = asd_read_reg_dword(asd_ha, EXSICNFGR);
 
321
 
 
322
        if (!(reg & OCMINITIALIZED)) {
 
323
                err = pci_read_config_dword(pcidev, PCIC_INTRPT_STAT, &v);
 
324
                if (err) {
 
325
                        asd_printk("couldn't access PCIC_INTRPT_STAT of %s\n",
 
326
                                        pci_name(pcidev));
 
327
                        goto out;
 
328
                }
 
329
 
 
330
                printk(KERN_INFO "OCM is not initialized by BIOS,"
 
331
                       "reinitialize it and ignore it, current IntrptStatus"
 
332
                       "is 0x%x\n", v);
 
333
 
 
334
                if (v)
 
335
                        err = pci_write_config_dword(pcidev,
 
336
                                                     PCIC_INTRPT_STAT, v);
 
337
                if (err) {
 
338
                        asd_printk("couldn't write PCIC_INTRPT_STAT of %s\n",
 
339
                                        pci_name(pcidev));
 
340
                        goto out;
 
341
                }
 
342
 
 
343
                asd_hwi_initialize_ocm_dir(asd_ha);
 
344
 
 
345
        }
 
346
out:
 
347
        return err;
 
348
}
 
349
 
 
350
/**
 
351
 * asd_read_ocm - read on chip memory (OCM)
 
352
 * @asd_ha: pointer to the host adapter structure
 
353
 */
 
354
int asd_read_ocm(struct asd_ha_struct *asd_ha)
 
355
{
 
356
        int err;
 
357
        struct asd_ocm_dir *dir;
 
358
 
 
359
        if (asd_hwi_check_ocm_access(asd_ha))
 
360
                return -1;
 
361
 
 
362
        dir = kmalloc(sizeof(*dir), GFP_KERNEL);
 
363
        if (!dir) {
 
364
                asd_printk("no memory for ocm dir\n");
 
365
                return -ENOMEM;
 
366
        }
 
367
 
 
368
        err = asd_read_ocm_dir(asd_ha, dir, 0);
 
369
        if (err)
 
370
                goto out;
 
371
 
 
372
        err = asd_get_bios_chim(asd_ha, dir);
 
373
out:
 
374
        kfree(dir);
 
375
        return err;
 
376
}
 
377
 
 
378
/* ---------- FLASH stuff ---------- */
 
379
 
 
380
#define FLASH_RESET                     0xF0
 
381
 
 
382
#define ASD_FLASH_SIZE                  0x200000
 
383
#define FLASH_DIR_COOKIE                "*** ADAPTEC FLASH DIRECTORY *** "
 
384
#define FLASH_NEXT_ENTRY_OFFS           0x2000
 
385
#define FLASH_MAX_DIR_ENTRIES           32
 
386
 
 
387
#define FLASH_DE_TYPE_MASK              0x3FFFFFFF
 
388
#define FLASH_DE_MS                     0x120
 
389
#define FLASH_DE_CTRL_A_USER            0xE0
 
390
 
 
391
struct asd_flash_de {
 
392
        __le32   type;
 
393
        __le32   offs;
 
394
        __le32   pad_size;
 
395
        __le32   image_size;
 
396
        __le32   chksum;
 
397
        u8       _r[12];
 
398
        u8       version[32];
 
399
} __attribute__ ((packed));
 
400
 
 
401
struct asd_flash_dir {
 
402
        u8    cookie[32];
 
403
        __le32   rev;             /* 2 */
 
404
        __le32   chksum;
 
405
        __le32   chksum_antidote;
 
406
        __le32   bld;
 
407
        u8    bld_id[32];         /* build id data */
 
408
        u8    ver_data[32];       /* date and time of build */
 
409
        __le32   ae_mask;
 
410
        __le32   v_mask;
 
411
        __le32   oc_mask;
 
412
        u8    _r[20];
 
413
        struct asd_flash_de dir_entry[FLASH_MAX_DIR_ENTRIES];
 
414
} __attribute__ ((packed));
 
415
 
 
416
struct asd_manuf_sec {
 
417
        char  sig[2];             /* 'S', 'M' */
 
418
        u16   offs_next;
 
419
        u8    maj;           /* 0 */
 
420
        u8    min;           /* 0 */
 
421
        u16   chksum;
 
422
        u16   size;
 
423
        u8    _r[6];
 
424
        u8    sas_addr[SAS_ADDR_SIZE];
 
425
        u8    pcba_sn[ASD_PCBA_SN_SIZE];
 
426
        /* Here start the other segments */
 
427
        u8    linked_list[0];
 
428
} __attribute__ ((packed));
 
429
 
 
430
struct asd_manuf_phy_desc {
 
431
        u8    state;         /* low 4 bits */
 
432
#define MS_PHY_STATE_ENABLED    0
 
433
#define MS_PHY_STATE_REPORTED   1
 
434
#define MS_PHY_STATE_HIDDEN     2
 
435
        u8    phy_id;
 
436
        u16   _r;
 
437
        u8    phy_control_0; /* mode 5 reg 0x160 */
 
438
        u8    phy_control_1; /* mode 5 reg 0x161 */
 
439
        u8    phy_control_2; /* mode 5 reg 0x162 */
 
440
        u8    phy_control_3; /* mode 5 reg 0x163 */
 
441
} __attribute__ ((packed));
 
442
 
 
443
struct asd_manuf_phy_param {
 
444
        char  sig[2];             /* 'P', 'M' */
 
445
        u16   next;
 
446
        u8    maj;           /* 0 */
 
447
        u8    min;           /* 2 */
 
448
        u8    num_phy_desc;  /* 8 */
 
449
        u8    phy_desc_size; /* 8 */
 
450
        u8    _r[3];
 
451
        u8    usage_model_id;
 
452
        u32   _r2;
 
453
        struct asd_manuf_phy_desc phy_desc[ASD_MAX_PHYS];
 
454
} __attribute__ ((packed));
 
455
 
 
456
#if 0
 
457
static const char *asd_sb_type[] = {
 
458
        "unknown",
 
459
        "SGPIO",
 
460
        [2 ... 0x7F] = "unknown",
 
461
        [0x80] = "ADPT_I2C",
 
462
        [0x81 ... 0xFF] = "VENDOR_UNIQUExx"
 
463
};
 
464
#endif
 
465
 
 
466
struct asd_ms_sb_desc {
 
467
        u8    type;
 
468
        u8    node_desc_index;
 
469
        u8    conn_desc_index;
 
470
        u8    _recvd[0];
 
471
} __attribute__ ((packed));
 
472
 
 
473
#if 0
 
474
static const char *asd_conn_type[] = {
 
475
        [0 ... 7] = "unknown",
 
476
        "SFF8470",
 
477
        "SFF8482",
 
478
        "SFF8484",
 
479
        [0x80] = "PCIX_DAUGHTER0",
 
480
        [0x81] = "SAS_DAUGHTER0",
 
481
        [0x82 ... 0xFF] = "VENDOR_UNIQUExx"
 
482
};
 
483
 
 
484
static const char *asd_conn_location[] = {
 
485
        "unknown",
 
486
        "internal",
 
487
        "external",
 
488
        "board_to_board",
 
489
};
 
490
#endif
 
491
 
 
492
struct asd_ms_conn_desc {
 
493
        u8    type;
 
494
        u8    location;
 
495
        u8    num_sideband_desc;
 
496
        u8    size_sideband_desc;
 
497
        u32   _resvd;
 
498
        u8    name[16];
 
499
        struct asd_ms_sb_desc sb_desc[0];
 
500
} __attribute__ ((packed));
 
501
 
 
502
struct asd_nd_phy_desc {
 
503
        u8    vp_attch_type;
 
504
        u8    attch_specific[0];
 
505
} __attribute__ ((packed));
 
506
 
 
507
#if 0
 
508
static const char *asd_node_type[] = {
 
509
        "IOP",
 
510
        "IO_CONTROLLER",
 
511
        "EXPANDER",
 
512
        "PORT_MULTIPLIER",
 
513
        "PORT_MULTIPLEXER",
 
514
        "MULTI_DROP_I2C_BUS",
 
515
};
 
516
#endif
 
517
 
 
518
struct asd_ms_node_desc {
 
519
        u8    type;
 
520
        u8    num_phy_desc;
 
521
        u8    size_phy_desc;
 
522
        u8    _resvd;
 
523
        u8    name[16];
 
524
        struct asd_nd_phy_desc phy_desc[0];
 
525
} __attribute__ ((packed));
 
526
 
 
527
struct asd_ms_conn_map {
 
528
        char  sig[2];             /* 'M', 'C' */
 
529
        __le16 next;
 
530
        u8    maj;                /* 0 */
 
531
        u8    min;                /* 0 */
 
532
        __le16 cm_size;           /* size of this struct */
 
533
        u8    num_conn;
 
534
        u8    conn_size;
 
535
        u8    num_nodes;
 
536
        u8    usage_model_id;
 
537
        u32   _resvd;
 
538
        struct asd_ms_conn_desc conn_desc[0];
 
539
        struct asd_ms_node_desc node_desc[0];
 
540
} __attribute__ ((packed));
 
541
 
 
542
struct asd_ctrla_phy_entry {
 
543
        u8    sas_addr[SAS_ADDR_SIZE];
 
544
        u8    sas_link_rates;  /* max in hi bits, min in low bits */
 
545
        u8    flags;
 
546
        u8    sata_link_rates;
 
547
        u8    _r[5];
 
548
} __attribute__ ((packed));
 
549
 
 
550
struct asd_ctrla_phy_settings {
 
551
        u8    id0;                /* P'h'y */
 
552
        u8    _r;
 
553
        u16   next;
 
554
        u8    num_phys;       /* number of PHYs in the PCI function */
 
555
        u8    _r2[3];
 
556
        struct asd_ctrla_phy_entry phy_ent[ASD_MAX_PHYS];
 
557
} __attribute__ ((packed));
 
558
 
 
559
struct asd_ll_el {
 
560
        u8   id0;
 
561
        u8   id1;
 
562
        __le16  next;
 
563
        u8   something_here[0];
 
564
} __attribute__ ((packed));
 
565
 
 
566
static int asd_poll_flash(struct asd_ha_struct *asd_ha)
 
567
{
 
568
        int c;
 
569
        u8 d;
 
570
 
 
571
        for (c = 5000; c > 0; c--) {
 
572
                d  = asd_read_reg_byte(asd_ha, asd_ha->hw_prof.flash.bar);
 
573
                d ^= asd_read_reg_byte(asd_ha, asd_ha->hw_prof.flash.bar);
 
574
                if (!d)
 
575
                        return 0;
 
576
                udelay(5);
 
577
        }
 
578
        return -ENOENT;
 
579
}
 
580
 
 
581
static int asd_reset_flash(struct asd_ha_struct *asd_ha)
 
582
{
 
583
        int err;
 
584
 
 
585
        err = asd_poll_flash(asd_ha);
 
586
        if (err)
 
587
                return err;
 
588
        asd_write_reg_byte(asd_ha, asd_ha->hw_prof.flash.bar, FLASH_RESET);
 
589
        err = asd_poll_flash(asd_ha);
 
590
 
 
591
        return err;
 
592
}
 
593
 
 
594
static int asd_read_flash_seg(struct asd_ha_struct *asd_ha,
 
595
                              void *buffer, u32 offs, int size)
 
596
{
 
597
        asd_read_reg_string(asd_ha, buffer, asd_ha->hw_prof.flash.bar+offs,
 
598
                            size);
 
599
        return 0;
 
600
}
 
601
 
 
602
/**
 
603
 * asd_find_flash_dir - finds and reads the flash directory
 
604
 * @asd_ha: pointer to the host adapter structure
 
605
 * @flash_dir: pointer to flash directory structure
 
606
 *
 
607
 * If found, the flash directory segment will be copied to
 
608
 * @flash_dir.  Return 1 if found, 0 if not.
 
609
 */
 
610
static int asd_find_flash_dir(struct asd_ha_struct *asd_ha,
 
611
                              struct asd_flash_dir *flash_dir)
 
612
{
 
613
        u32 v;
 
614
        for (v = 0; v < ASD_FLASH_SIZE; v += FLASH_NEXT_ENTRY_OFFS) {
 
615
                asd_read_flash_seg(asd_ha, flash_dir, v,
 
616
                                   sizeof(FLASH_DIR_COOKIE)-1);
 
617
                if (memcmp(flash_dir->cookie, FLASH_DIR_COOKIE,
 
618
                           sizeof(FLASH_DIR_COOKIE)-1) == 0) {
 
619
                        asd_ha->hw_prof.flash.dir_offs = v;
 
620
                        asd_read_flash_seg(asd_ha, flash_dir, v,
 
621
                                           sizeof(*flash_dir));
 
622
                        return 1;
 
623
                }
 
624
        }
 
625
        return 0;
 
626
}
 
627
 
 
628
static int asd_flash_getid(struct asd_ha_struct *asd_ha)
 
629
{
 
630
        int err = 0;
 
631
        u32 reg;
 
632
 
 
633
        reg = asd_read_reg_dword(asd_ha, EXSICNFGR);
 
634
 
 
635
        if (pci_read_config_dword(asd_ha->pcidev, PCI_CONF_FLSH_BAR,
 
636
                                  &asd_ha->hw_prof.flash.bar)) {
 
637
                asd_printk("couldn't read PCI_CONF_FLSH_BAR of %s\n",
 
638
                           pci_name(asd_ha->pcidev));
 
639
                return -ENOENT;
 
640
        }
 
641
        asd_ha->hw_prof.flash.present = 1;
 
642
        asd_ha->hw_prof.flash.wide = reg & FLASHW ? 1 : 0;
 
643
        err = asd_reset_flash(asd_ha);
 
644
        if (err) {
 
645
                ASD_DPRINTK("couldn't reset flash(%d)\n", err);
 
646
                return err;
 
647
        }
 
648
        return 0;
 
649
}
 
650
 
 
651
static u16 asd_calc_flash_chksum(u16 *p, int size)
 
652
{
 
653
        u16 chksum = 0;
 
654
 
 
655
        while (size-- > 0)
 
656
                chksum += *p++;
 
657
 
 
658
        return chksum;
 
659
}
 
660
 
 
661
 
 
662
static int asd_find_flash_de(struct asd_flash_dir *flash_dir, u32 entry_type,
 
663
                             u32 *offs, u32 *size)
 
664
{
 
665
        int i;
 
666
        struct asd_flash_de *de;
 
667
 
 
668
        for (i = 0; i < FLASH_MAX_DIR_ENTRIES; i++) {
 
669
                u32 type = le32_to_cpu(flash_dir->dir_entry[i].type);
 
670
 
 
671
                type &= FLASH_DE_TYPE_MASK;
 
672
                if (type == entry_type)
 
673
                        break;
 
674
        }
 
675
        if (i >= FLASH_MAX_DIR_ENTRIES)
 
676
                return -ENOENT;
 
677
        de = &flash_dir->dir_entry[i];
 
678
        *offs = le32_to_cpu(de->offs);
 
679
        *size = le32_to_cpu(de->pad_size);
 
680
        return 0;
 
681
}
 
682
 
 
683
static int asd_validate_ms(struct asd_manuf_sec *ms)
 
684
{
 
685
        if (ms->sig[0] != 'S' || ms->sig[1] != 'M') {
 
686
                ASD_DPRINTK("manuf sec: no valid sig(%c%c)\n",
 
687
                            ms->sig[0], ms->sig[1]);
 
688
                return -ENOENT;
 
689
        }
 
690
        if (ms->maj != 0) {
 
691
                asd_printk("unsupported manuf. sector. major version:%x\n",
 
692
                           ms->maj);
 
693
                return -ENOENT;
 
694
        }
 
695
        ms->offs_next = le16_to_cpu((__force __le16) ms->offs_next);
 
696
        ms->chksum = le16_to_cpu((__force __le16) ms->chksum);
 
697
        ms->size = le16_to_cpu((__force __le16) ms->size);
 
698
 
 
699
        if (asd_calc_flash_chksum((u16 *)ms, ms->size/2)) {
 
700
                asd_printk("failed manuf sector checksum\n");
 
701
        }
 
702
 
 
703
        return 0;
 
704
}
 
705
 
 
706
static int asd_ms_get_sas_addr(struct asd_ha_struct *asd_ha,
 
707
                               struct asd_manuf_sec *ms)
 
708
{
 
709
        memcpy(asd_ha->hw_prof.sas_addr, ms->sas_addr, SAS_ADDR_SIZE);
 
710
        return 0;
 
711
}
 
712
 
 
713
static int asd_ms_get_pcba_sn(struct asd_ha_struct *asd_ha,
 
714
                              struct asd_manuf_sec *ms)
 
715
{
 
716
        memcpy(asd_ha->hw_prof.pcba_sn, ms->pcba_sn, ASD_PCBA_SN_SIZE);
 
717
        asd_ha->hw_prof.pcba_sn[ASD_PCBA_SN_SIZE] = '\0';
 
718
        return 0;
 
719
}
 
720
 
 
721
/**
 
722
 * asd_find_ll_by_id - find a linked list entry by its id
 
723
 * @start: void pointer to the first element in the linked list
 
724
 * @id0: the first byte of the id  (offs 0)
 
725
 * @id1: the second byte of the id (offs 1)
 
726
 *
 
727
 * @start has to be the _base_ element start, since the
 
728
 * linked list entries's offset is from this pointer.
 
729
 * Some linked list entries use only the first id, in which case
 
730
 * you can pass 0xFF for the second.
 
731
 */
 
732
static void *asd_find_ll_by_id(void * const start, const u8 id0, const u8 id1)
 
733
{
 
734
        struct asd_ll_el *el = start;
 
735
 
 
736
        do {
 
737
                switch (id1) {
 
738
                default:
 
739
                        if (el->id1 == id1)
 
740
                case 0xFF:
 
741
                                if (el->id0 == id0)
 
742
                                        return el;
 
743
                }
 
744
                el = start + le16_to_cpu(el->next);
 
745
        } while (el != start);
 
746
 
 
747
        return NULL;
 
748
}
 
749
 
 
750
/**
 
751
 * asd_ms_get_phy_params - get phy parameters from the manufacturing sector
 
752
 * @asd_ha: pointer to the host adapter structure
 
753
 * @manuf_sec: pointer to the manufacturing sector
 
754
 *
 
755
 * The manufacturing sector contans also the linked list of sub-segments,
 
756
 * since when it was read, its size was taken from the flash directory,
 
757
 * not from the structure size.
 
758
 *
 
759
 * HIDDEN phys do not count in the total count.  REPORTED phys cannot
 
760
 * be enabled but are reported and counted towards the total.
 
761
 * ENABLED phys are enabled by default and count towards the total.
 
762
 * The absolute total phy number is ASD_MAX_PHYS.  hw_prof->num_phys
 
763
 * merely specifies the number of phys the host adapter decided to
 
764
 * report.  E.g., it is possible for phys 0, 1 and 2 to be HIDDEN,
 
765
 * phys 3, 4 and 5 to be REPORTED and phys 6 and 7 to be ENABLED.
 
766
 * In this case ASD_MAX_PHYS is 8, hw_prof->num_phys is 5, and only 2
 
767
 * are actually enabled (enabled by default, max number of phys
 
768
 * enableable in this case).
 
769
 */
 
770
static int asd_ms_get_phy_params(struct asd_ha_struct *asd_ha,
 
771
                                 struct asd_manuf_sec *manuf_sec)
 
772
{
 
773
        int i;
 
774
        int en_phys = 0;
 
775
        int rep_phys = 0;
 
776
        struct asd_manuf_phy_param *phy_param;
 
777
        struct asd_manuf_phy_param dflt_phy_param;
 
778
 
 
779
        phy_param = asd_find_ll_by_id(manuf_sec, 'P', 'M');
 
780
        if (!phy_param) {
 
781
                ASD_DPRINTK("ms: no phy parameters found\n");
 
782
                ASD_DPRINTK("ms: Creating default phy parameters\n");
 
783
                dflt_phy_param.sig[0] = 'P';
 
784
                dflt_phy_param.sig[1] = 'M';
 
785
                dflt_phy_param.maj = 0;
 
786
                dflt_phy_param.min = 2;
 
787
                dflt_phy_param.num_phy_desc = 8;
 
788
                dflt_phy_param.phy_desc_size = sizeof(struct asd_manuf_phy_desc);
 
789
                for (i =0; i < ASD_MAX_PHYS; i++) {
 
790
                        dflt_phy_param.phy_desc[i].state = 0;
 
791
                        dflt_phy_param.phy_desc[i].phy_id = i;
 
792
                        dflt_phy_param.phy_desc[i].phy_control_0 = 0xf6;
 
793
                        dflt_phy_param.phy_desc[i].phy_control_1 = 0x10;
 
794
                        dflt_phy_param.phy_desc[i].phy_control_2 = 0x43;
 
795
                        dflt_phy_param.phy_desc[i].phy_control_3 = 0xeb;
 
796
                }
 
797
 
 
798
                phy_param = &dflt_phy_param;
 
799
 
 
800
        }
 
801
 
 
802
        if (phy_param->maj != 0) {
 
803
                asd_printk("unsupported manuf. phy param major version:0x%x\n",
 
804
                           phy_param->maj);
 
805
                return -ENOENT;
 
806
        }
 
807
 
 
808
        ASD_DPRINTK("ms: num_phy_desc: %d\n", phy_param->num_phy_desc);
 
809
        asd_ha->hw_prof.enabled_phys = 0;
 
810
        for (i = 0; i < phy_param->num_phy_desc; i++) {
 
811
                struct asd_manuf_phy_desc *pd = &phy_param->phy_desc[i];
 
812
                switch (pd->state & 0xF) {
 
813
                case MS_PHY_STATE_HIDDEN:
 
814
                        ASD_DPRINTK("ms: phy%d: HIDDEN\n", i);
 
815
                        continue;
 
816
                case MS_PHY_STATE_REPORTED:
 
817
                        ASD_DPRINTK("ms: phy%d: REPORTED\n", i);
 
818
                        asd_ha->hw_prof.enabled_phys &= ~(1 << i);
 
819
                        rep_phys++;
 
820
                        continue;
 
821
                case MS_PHY_STATE_ENABLED:
 
822
                        ASD_DPRINTK("ms: phy%d: ENABLED\n", i);
 
823
                        asd_ha->hw_prof.enabled_phys |= (1 << i);
 
824
                        en_phys++;
 
825
                        break;
 
826
                }
 
827
                asd_ha->hw_prof.phy_desc[i].phy_control_0 = pd->phy_control_0;
 
828
                asd_ha->hw_prof.phy_desc[i].phy_control_1 = pd->phy_control_1;
 
829
                asd_ha->hw_prof.phy_desc[i].phy_control_2 = pd->phy_control_2;
 
830
                asd_ha->hw_prof.phy_desc[i].phy_control_3 = pd->phy_control_3;
 
831
        }
 
832
        asd_ha->hw_prof.max_phys = rep_phys + en_phys;
 
833
        asd_ha->hw_prof.num_phys = en_phys;
 
834
        ASD_DPRINTK("ms: max_phys:0x%x, num_phys:0x%x\n",
 
835
                    asd_ha->hw_prof.max_phys, asd_ha->hw_prof.num_phys);
 
836
        ASD_DPRINTK("ms: enabled_phys:0x%x\n", asd_ha->hw_prof.enabled_phys);
 
837
        return 0;
 
838
}
 
839
 
 
840
static int asd_ms_get_connector_map(struct asd_ha_struct *asd_ha,
 
841
                                    struct asd_manuf_sec *manuf_sec)
 
842
{
 
843
        struct asd_ms_conn_map *cm;
 
844
 
 
845
        cm = asd_find_ll_by_id(manuf_sec, 'M', 'C');
 
846
        if (!cm) {
 
847
                ASD_DPRINTK("ms: no connector map found\n");
 
848
                return 0;
 
849
        }
 
850
 
 
851
        if (cm->maj != 0) {
 
852
                ASD_DPRINTK("ms: unsupported: connector map major version 0x%x"
 
853
                            "\n", cm->maj);
 
854
                return -ENOENT;
 
855
        }
 
856
 
 
857
        /* XXX */
 
858
 
 
859
        return 0;
 
860
}
 
861
 
 
862
 
 
863
/**
 
864
 * asd_process_ms - find and extract information from the manufacturing sector
 
865
 * @asd_ha: pointer to the host adapter structure
 
866
 * @flash_dir: pointer to the flash directory
 
867
 */
 
868
static int asd_process_ms(struct asd_ha_struct *asd_ha,
 
869
                          struct asd_flash_dir *flash_dir)
 
870
{
 
871
        int err;
 
872
        struct asd_manuf_sec *manuf_sec;
 
873
        u32 offs, size;
 
874
 
 
875
        err = asd_find_flash_de(flash_dir, FLASH_DE_MS, &offs, &size);
 
876
        if (err) {
 
877
                ASD_DPRINTK("Couldn't find the manuf. sector\n");
 
878
                goto out;
 
879
        }
 
880
 
 
881
        if (size == 0)
 
882
                goto out;
 
883
 
 
884
        err = -ENOMEM;
 
885
        manuf_sec = kmalloc(size, GFP_KERNEL);
 
886
        if (!manuf_sec) {
 
887
                ASD_DPRINTK("no mem for manuf sector\n");
 
888
                goto out;
 
889
        }
 
890
 
 
891
        err = asd_read_flash_seg(asd_ha, (void *)manuf_sec, offs, size);
 
892
        if (err) {
 
893
                ASD_DPRINTK("couldn't read manuf sector at 0x%x, size 0x%x\n",
 
894
                            offs, size);
 
895
                goto out2;
 
896
        }
 
897
 
 
898
        err = asd_validate_ms(manuf_sec);
 
899
        if (err) {
 
900
                ASD_DPRINTK("couldn't validate manuf sector\n");
 
901
                goto out2;
 
902
        }
 
903
 
 
904
        err = asd_ms_get_sas_addr(asd_ha, manuf_sec);
 
905
        if (err) {
 
906
                ASD_DPRINTK("couldn't read the SAS_ADDR\n");
 
907
                goto out2;
 
908
        }
 
909
        ASD_DPRINTK("manuf sect SAS_ADDR %llx\n",
 
910
                    SAS_ADDR(asd_ha->hw_prof.sas_addr));
 
911
 
 
912
        err = asd_ms_get_pcba_sn(asd_ha, manuf_sec);
 
913
        if (err) {
 
914
                ASD_DPRINTK("couldn't read the PCBA SN\n");
 
915
                goto out2;
 
916
        }
 
917
        ASD_DPRINTK("manuf sect PCBA SN %s\n", asd_ha->hw_prof.pcba_sn);
 
918
 
 
919
        err = asd_ms_get_phy_params(asd_ha, manuf_sec);
 
920
        if (err) {
 
921
                ASD_DPRINTK("ms: couldn't get phy parameters\n");
 
922
                goto out2;
 
923
        }
 
924
 
 
925
        err = asd_ms_get_connector_map(asd_ha, manuf_sec);
 
926
        if (err) {
 
927
                ASD_DPRINTK("ms: couldn't get connector map\n");
 
928
                goto out2;
 
929
        }
 
930
 
 
931
out2:
 
932
        kfree(manuf_sec);
 
933
out:
 
934
        return err;
 
935
}
 
936
 
 
937
static int asd_process_ctrla_phy_settings(struct asd_ha_struct *asd_ha,
 
938
                                          struct asd_ctrla_phy_settings *ps)
 
939
{
 
940
        int i;
 
941
        for (i = 0; i < ps->num_phys; i++) {
 
942
                struct asd_ctrla_phy_entry *pe = &ps->phy_ent[i];
 
943
 
 
944
                if (!PHY_ENABLED(asd_ha, i))
 
945
                        continue;
 
946
                if (*(u64 *)pe->sas_addr == 0) {
 
947
                        asd_ha->hw_prof.enabled_phys &= ~(1 << i);
 
948
                        continue;
 
949
                }
 
950
                /* This is the SAS address which should be sent in IDENTIFY. */
 
951
                memcpy(asd_ha->hw_prof.phy_desc[i].sas_addr, pe->sas_addr,
 
952
                       SAS_ADDR_SIZE);
 
953
                asd_ha->hw_prof.phy_desc[i].max_sas_lrate =
 
954
                        (pe->sas_link_rates & 0xF0) >> 4;
 
955
                asd_ha->hw_prof.phy_desc[i].min_sas_lrate =
 
956
                        (pe->sas_link_rates & 0x0F);
 
957
                asd_ha->hw_prof.phy_desc[i].max_sata_lrate =
 
958
                        (pe->sata_link_rates & 0xF0) >> 4;
 
959
                asd_ha->hw_prof.phy_desc[i].min_sata_lrate =
 
960
                        (pe->sata_link_rates & 0x0F);
 
961
                asd_ha->hw_prof.phy_desc[i].flags = pe->flags;
 
962
                ASD_DPRINTK("ctrla: phy%d: sas_addr: %llx, sas rate:0x%x-0x%x,"
 
963
                            " sata rate:0x%x-0x%x, flags:0x%x\n",
 
964
                            i,
 
965
                            SAS_ADDR(asd_ha->hw_prof.phy_desc[i].sas_addr),
 
966
                            asd_ha->hw_prof.phy_desc[i].max_sas_lrate,
 
967
                            asd_ha->hw_prof.phy_desc[i].min_sas_lrate,
 
968
                            asd_ha->hw_prof.phy_desc[i].max_sata_lrate,
 
969
                            asd_ha->hw_prof.phy_desc[i].min_sata_lrate,
 
970
                            asd_ha->hw_prof.phy_desc[i].flags);
 
971
        }
 
972
 
 
973
        return 0;
 
974
}
 
975
 
 
976
/**
 
977
 * asd_process_ctrl_a_user - process CTRL-A user settings
 
978
 * @asd_ha: pointer to the host adapter structure
 
979
 * @flash_dir: pointer to the flash directory
 
980
 */
 
981
static int asd_process_ctrl_a_user(struct asd_ha_struct *asd_ha,
 
982
                                   struct asd_flash_dir *flash_dir)
 
983
{
 
984
        int err, i;
 
985
        u32 offs, size;
 
986
        struct asd_ll_el *el;
 
987
        struct asd_ctrla_phy_settings *ps;
 
988
        struct asd_ctrla_phy_settings dflt_ps;
 
989
 
 
990
        err = asd_find_flash_de(flash_dir, FLASH_DE_CTRL_A_USER, &offs, &size);
 
991
        if (err) {
 
992
                ASD_DPRINTK("couldn't find CTRL-A user settings section\n");
 
993
                ASD_DPRINTK("Creating default CTRL-A user settings section\n");
 
994
 
 
995
                dflt_ps.id0 = 'h';
 
996
                dflt_ps.num_phys = 8;
 
997
                for (i =0; i < ASD_MAX_PHYS; i++) {
 
998
                        memcpy(dflt_ps.phy_ent[i].sas_addr,
 
999
                               asd_ha->hw_prof.sas_addr, SAS_ADDR_SIZE);
 
1000
                        dflt_ps.phy_ent[i].sas_link_rates = 0x98;
 
1001
                        dflt_ps.phy_ent[i].flags = 0x0;
 
1002
                        dflt_ps.phy_ent[i].sata_link_rates = 0x0;
 
1003
                }
 
1004
 
 
1005
                size = sizeof(struct asd_ctrla_phy_settings);
 
1006
                ps = &dflt_ps;
 
1007
        }
 
1008
 
 
1009
        if (size == 0)
 
1010
                goto out;
 
1011
 
 
1012
        err = -ENOMEM;
 
1013
        el = kmalloc(size, GFP_KERNEL);
 
1014
        if (!el) {
 
1015
                ASD_DPRINTK("no mem for ctrla user settings section\n");
 
1016
                goto out;
 
1017
        }
 
1018
 
 
1019
        err = asd_read_flash_seg(asd_ha, (void *)el, offs, size);
 
1020
        if (err) {
 
1021
                ASD_DPRINTK("couldn't read ctrla phy settings section\n");
 
1022
                goto out2;
 
1023
        }
 
1024
 
 
1025
        err = -ENOENT;
 
1026
        ps = asd_find_ll_by_id(el, 'h', 0xFF);
 
1027
        if (!ps) {
 
1028
                ASD_DPRINTK("couldn't find ctrla phy settings struct\n");
 
1029
                goto out2;
 
1030
        }
 
1031
 
 
1032
        err = asd_process_ctrla_phy_settings(asd_ha, ps);
 
1033
        if (err) {
 
1034
                ASD_DPRINTK("couldn't process ctrla phy settings\n");
 
1035
                goto out2;
 
1036
        }
 
1037
out2:
 
1038
        kfree(el);
 
1039
out:
 
1040
        return err;
 
1041
}
 
1042
 
 
1043
/**
 
1044
 * asd_read_flash - read flash memory
 
1045
 * @asd_ha: pointer to the host adapter structure
 
1046
 */
 
1047
int asd_read_flash(struct asd_ha_struct *asd_ha)
 
1048
{
 
1049
        int err;
 
1050
        struct asd_flash_dir *flash_dir;
 
1051
 
 
1052
        err = asd_flash_getid(asd_ha);
 
1053
        if (err)
 
1054
                return err;
 
1055
 
 
1056
        flash_dir = kmalloc(sizeof(*flash_dir), GFP_KERNEL);
 
1057
        if (!flash_dir)
 
1058
                return -ENOMEM;
 
1059
 
 
1060
        err = -ENOENT;
 
1061
        if (!asd_find_flash_dir(asd_ha, flash_dir)) {
 
1062
                ASD_DPRINTK("couldn't find flash directory\n");
 
1063
                goto out;
 
1064
        }
 
1065
 
 
1066
        if (le32_to_cpu(flash_dir->rev) != 2) {
 
1067
                asd_printk("unsupported flash dir version:0x%x\n",
 
1068
                           le32_to_cpu(flash_dir->rev));
 
1069
                goto out;
 
1070
        }
 
1071
 
 
1072
        err = asd_process_ms(asd_ha, flash_dir);
 
1073
        if (err) {
 
1074
                ASD_DPRINTK("couldn't process manuf sector settings\n");
 
1075
                goto out;
 
1076
        }
 
1077
 
 
1078
        err = asd_process_ctrl_a_user(asd_ha, flash_dir);
 
1079
        if (err) {
 
1080
                ASD_DPRINTK("couldn't process CTRL-A user settings\n");
 
1081
                goto out;
 
1082
        }
 
1083
 
 
1084
out:
 
1085
        kfree(flash_dir);
 
1086
        return err;
 
1087
}
 
1088
 
 
1089
/**
 
1090
 * asd_verify_flash_seg - verify data with flash memory
 
1091
 * @asd_ha: pointer to the host adapter structure
 
1092
 * @src: pointer to the source data to be verified
 
1093
 * @dest_offset: offset from flash memory
 
1094
 * @bytes_to_verify: total bytes to verify
 
1095
 */
 
1096
int asd_verify_flash_seg(struct asd_ha_struct *asd_ha,
 
1097
                         const void *src, u32 dest_offset, u32 bytes_to_verify)
 
1098
{
 
1099
        const u8 *src_buf;
 
1100
        u8 flash_char;
 
1101
        int err;
 
1102
        u32 nv_offset, reg, i;
 
1103
 
 
1104
        reg = asd_ha->hw_prof.flash.bar;
 
1105
        src_buf = NULL;
 
1106
 
 
1107
        err = FLASH_OK;
 
1108
        nv_offset = dest_offset;
 
1109
        src_buf = (const u8 *)src;
 
1110
        for (i = 0; i < bytes_to_verify; i++) {
 
1111
                flash_char = asd_read_reg_byte(asd_ha, reg + nv_offset + i);
 
1112
                if (flash_char != src_buf[i]) {
 
1113
                        err = FAIL_VERIFY;
 
1114
                        break;
 
1115
                }
 
1116
        }
 
1117
        return err;
 
1118
}
 
1119
 
 
1120
/**
 
1121
 * asd_write_flash_seg - write data into flash memory
 
1122
 * @asd_ha: pointer to the host adapter structure
 
1123
 * @src: pointer to the source data to be written
 
1124
 * @dest_offset: offset from flash memory
 
1125
 * @bytes_to_write: total bytes to write
 
1126
 */
 
1127
int asd_write_flash_seg(struct asd_ha_struct *asd_ha,
 
1128
                        const void *src, u32 dest_offset, u32 bytes_to_write)
 
1129
{
 
1130
        const u8 *src_buf;
 
1131
        u32 nv_offset, reg, i;
 
1132
        int err;
 
1133
 
 
1134
        reg = asd_ha->hw_prof.flash.bar;
 
1135
        src_buf = NULL;
 
1136
 
 
1137
        err = asd_check_flash_type(asd_ha);
 
1138
        if (err) {
 
1139
                ASD_DPRINTK("couldn't find the type of flash. err=%d\n", err);
 
1140
                return err;
 
1141
        }
 
1142
 
 
1143
        nv_offset = dest_offset;
 
1144
        err = asd_erase_nv_sector(asd_ha, nv_offset, bytes_to_write);
 
1145
        if (err) {
 
1146
                ASD_DPRINTK("Erase failed at offset:0x%x\n",
 
1147
                        nv_offset);
 
1148
                return err;
 
1149
        }
 
1150
 
 
1151
        err = asd_reset_flash(asd_ha);
 
1152
        if (err) {
 
1153
                ASD_DPRINTK("couldn't reset flash. err=%d\n", err);
 
1154
                return err;
 
1155
        }
 
1156
 
 
1157
        src_buf = (const u8 *)src;
 
1158
        for (i = 0; i < bytes_to_write; i++) {
 
1159
                /* Setup program command sequence */
 
1160
                switch (asd_ha->hw_prof.flash.method) {
 
1161
                case FLASH_METHOD_A:
 
1162
                {
 
1163
                        asd_write_reg_byte(asd_ha,
 
1164
                                        (reg + 0xAAA), 0xAA);
 
1165
                        asd_write_reg_byte(asd_ha,
 
1166
                                        (reg + 0x555), 0x55);
 
1167
                        asd_write_reg_byte(asd_ha,
 
1168
                                        (reg + 0xAAA), 0xA0);
 
1169
                        asd_write_reg_byte(asd_ha,
 
1170
                                        (reg + nv_offset + i),
 
1171
                                        (*(src_buf + i)));
 
1172
                        break;
 
1173
                }
 
1174
                case FLASH_METHOD_B:
 
1175
                {
 
1176
                        asd_write_reg_byte(asd_ha,
 
1177
                                        (reg + 0x555), 0xAA);
 
1178
                        asd_write_reg_byte(asd_ha,
 
1179
                                        (reg + 0x2AA), 0x55);
 
1180
                        asd_write_reg_byte(asd_ha,
 
1181
                                        (reg + 0x555), 0xA0);
 
1182
                        asd_write_reg_byte(asd_ha,
 
1183
                                        (reg + nv_offset + i),
 
1184
                                        (*(src_buf + i)));
 
1185
                        break;
 
1186
                }
 
1187
                default:
 
1188
                        break;
 
1189
                }
 
1190
                if (asd_chk_write_status(asd_ha,
 
1191
                                (nv_offset + i), 0) != 0) {
 
1192
                        ASD_DPRINTK("aicx: Write failed at offset:0x%x\n",
 
1193
                                reg + nv_offset + i);
 
1194
                        return FAIL_WRITE_FLASH;
 
1195
                }
 
1196
        }
 
1197
 
 
1198
        err = asd_reset_flash(asd_ha);
 
1199
        if (err) {
 
1200
                ASD_DPRINTK("couldn't reset flash. err=%d\n", err);
 
1201
                return err;
 
1202
        }
 
1203
        return 0;
 
1204
}
 
1205
 
 
1206
int asd_chk_write_status(struct asd_ha_struct *asd_ha,
 
1207
         u32 sector_addr, u8 erase_flag)
 
1208
{
 
1209
        u32 reg;
 
1210
        u32 loop_cnt;
 
1211
        u8  nv_data1, nv_data2;
 
1212
        u8  toggle_bit1;
 
1213
 
 
1214
        /*
 
1215
         * Read from DQ2 requires sector address
 
1216
         * while it's dont care for DQ6
 
1217
         */
 
1218
        reg = asd_ha->hw_prof.flash.bar;
 
1219
 
 
1220
        for (loop_cnt = 0; loop_cnt < 50000; loop_cnt++) {
 
1221
                nv_data1 = asd_read_reg_byte(asd_ha, reg);
 
1222
                nv_data2 = asd_read_reg_byte(asd_ha, reg);
 
1223
 
 
1224
                toggle_bit1 = ((nv_data1 & FLASH_STATUS_BIT_MASK_DQ6)
 
1225
                                 ^ (nv_data2 & FLASH_STATUS_BIT_MASK_DQ6));
 
1226
 
 
1227
                if (toggle_bit1 == 0) {
 
1228
                        return 0;
 
1229
                } else {
 
1230
                        if (nv_data2 & FLASH_STATUS_BIT_MASK_DQ5) {
 
1231
                                nv_data1 = asd_read_reg_byte(asd_ha,
 
1232
                                                                reg);
 
1233
                                nv_data2 = asd_read_reg_byte(asd_ha,
 
1234
                                                                reg);
 
1235
                                toggle_bit1 =
 
1236
                                ((nv_data1 & FLASH_STATUS_BIT_MASK_DQ6)
 
1237
                                ^ (nv_data2 & FLASH_STATUS_BIT_MASK_DQ6));
 
1238
 
 
1239
                                if (toggle_bit1 == 0)
 
1240
                                        return 0;
 
1241
                        }
 
1242
                }
 
1243
 
 
1244
                /*
 
1245
                 * ERASE is a sector-by-sector operation and requires
 
1246
                 * more time to finish while WRITE is byte-byte-byte
 
1247
                 * operation and takes lesser time to finish.
 
1248
                 *
 
1249
                 * For some strange reason a reduced ERASE delay gives different
 
1250
                 * behaviour across different spirit boards. Hence we set
 
1251
                 * a optimum balance of 50mus for ERASE which works well
 
1252
                 * across all boards.
 
1253
                 */
 
1254
                if (erase_flag) {
 
1255
                        udelay(FLASH_STATUS_ERASE_DELAY_COUNT);
 
1256
                } else {
 
1257
                        udelay(FLASH_STATUS_WRITE_DELAY_COUNT);
 
1258
                }
 
1259
        }
 
1260
        return -1;
 
1261
}
 
1262
 
 
1263
/**
 
1264
 * asd_hwi_erase_nv_sector - Erase the flash memory sectors.
 
1265
 * @asd_ha: pointer to the host adapter structure
 
1266
 * @flash_addr: pointer to offset from flash memory
 
1267
 * @size: total bytes to erase.
 
1268
 */
 
1269
int asd_erase_nv_sector(struct asd_ha_struct *asd_ha, u32 flash_addr, u32 size)
 
1270
{
 
1271
        u32 reg;
 
1272
        u32 sector_addr;
 
1273
 
 
1274
        reg = asd_ha->hw_prof.flash.bar;
 
1275
 
 
1276
        /* sector staring address */
 
1277
        sector_addr = flash_addr & FLASH_SECTOR_SIZE_MASK;
 
1278
 
 
1279
        /*
 
1280
         * Erasing an flash sector needs to be done in six consecutive
 
1281
         * write cyles.
 
1282
         */
 
1283
        while (sector_addr < flash_addr+size) {
 
1284
                switch (asd_ha->hw_prof.flash.method) {
 
1285
                case FLASH_METHOD_A:
 
1286
                        asd_write_reg_byte(asd_ha, (reg + 0xAAA), 0xAA);
 
1287
                        asd_write_reg_byte(asd_ha, (reg + 0x555), 0x55);
 
1288
                        asd_write_reg_byte(asd_ha, (reg + 0xAAA), 0x80);
 
1289
                        asd_write_reg_byte(asd_ha, (reg + 0xAAA), 0xAA);
 
1290
                        asd_write_reg_byte(asd_ha, (reg + 0x555), 0x55);
 
1291
                        asd_write_reg_byte(asd_ha, (reg + sector_addr), 0x30);
 
1292
                        break;
 
1293
                case FLASH_METHOD_B:
 
1294
                        asd_write_reg_byte(asd_ha, (reg + 0x555), 0xAA);
 
1295
                        asd_write_reg_byte(asd_ha, (reg + 0x2AA), 0x55);
 
1296
                        asd_write_reg_byte(asd_ha, (reg + 0x555), 0x80);
 
1297
                        asd_write_reg_byte(asd_ha, (reg + 0x555), 0xAA);
 
1298
                        asd_write_reg_byte(asd_ha, (reg + 0x2AA), 0x55);
 
1299
                        asd_write_reg_byte(asd_ha, (reg + sector_addr), 0x30);
 
1300
                        break;
 
1301
                default:
 
1302
                        break;
 
1303
                }
 
1304
 
 
1305
                if (asd_chk_write_status(asd_ha, sector_addr, 1) != 0)
 
1306
                        return FAIL_ERASE_FLASH;
 
1307
 
 
1308
                sector_addr += FLASH_SECTOR_SIZE;
 
1309
        }
 
1310
 
 
1311
        return 0;
 
1312
}
 
1313
 
 
1314
int asd_check_flash_type(struct asd_ha_struct *asd_ha)
 
1315
{
 
1316
        u8 manuf_id;
 
1317
        u8 dev_id;
 
1318
        u8 sec_prot;
 
1319
        u32 inc;
 
1320
        u32 reg;
 
1321
        int err;
 
1322
 
 
1323
        /* get Flash memory base address */
 
1324
        reg = asd_ha->hw_prof.flash.bar;
 
1325
 
 
1326
        /* Determine flash info */
 
1327
        err = asd_reset_flash(asd_ha);
 
1328
        if (err) {
 
1329
                ASD_DPRINTK("couldn't reset flash. err=%d\n", err);
 
1330
                return err;
 
1331
        }
 
1332
 
 
1333
        asd_ha->hw_prof.flash.method = FLASH_METHOD_UNKNOWN;
 
1334
        asd_ha->hw_prof.flash.manuf = FLASH_MANUF_ID_UNKNOWN;
 
1335
        asd_ha->hw_prof.flash.dev_id = FLASH_DEV_ID_UNKNOWN;
 
1336
 
 
1337
        /* Get flash info. This would most likely be AMD Am29LV family flash.
 
1338
         * First try the sequence for word mode.  It is the same as for
 
1339
         * 008B (byte mode only), 160B (word mode) and 800D (word mode).
 
1340
         */
 
1341
        inc = asd_ha->hw_prof.flash.wide ? 2 : 1;
 
1342
        asd_write_reg_byte(asd_ha, reg + 0xAAA, 0xAA);
 
1343
        asd_write_reg_byte(asd_ha, reg + 0x555, 0x55);
 
1344
        asd_write_reg_byte(asd_ha, reg + 0xAAA, 0x90);
 
1345
        manuf_id = asd_read_reg_byte(asd_ha, reg);
 
1346
        dev_id = asd_read_reg_byte(asd_ha, reg + inc);
 
1347
        sec_prot = asd_read_reg_byte(asd_ha, reg + inc + inc);
 
1348
        /* Get out of autoselect mode. */
 
1349
        err = asd_reset_flash(asd_ha);
 
1350
        if (err) {
 
1351
                ASD_DPRINTK("couldn't reset flash. err=%d\n", err);
 
1352
                return err;
 
1353
        }
 
1354
        ASD_DPRINTK("Flash MethodA manuf_id(0x%x) dev_id(0x%x) "
 
1355
                "sec_prot(0x%x)\n", manuf_id, dev_id, sec_prot);
 
1356
        err = asd_reset_flash(asd_ha);
 
1357
        if (err != 0)
 
1358
                return err;
 
1359
 
 
1360
        switch (manuf_id) {
 
1361
        case FLASH_MANUF_ID_AMD:
 
1362
                switch (sec_prot) {
 
1363
                case FLASH_DEV_ID_AM29LV800DT:
 
1364
                case FLASH_DEV_ID_AM29LV640MT:
 
1365
                case FLASH_DEV_ID_AM29F800B:
 
1366
                        asd_ha->hw_prof.flash.method = FLASH_METHOD_A;
 
1367
                        break;
 
1368
                default:
 
1369
                        break;
 
1370
                }
 
1371
                break;
 
1372
        case FLASH_MANUF_ID_ST:
 
1373
                switch (sec_prot) {
 
1374
                case FLASH_DEV_ID_STM29W800DT:
 
1375
                case FLASH_DEV_ID_STM29LV640:
 
1376
                        asd_ha->hw_prof.flash.method = FLASH_METHOD_A;
 
1377
                        break;
 
1378
                default:
 
1379
                        break;
 
1380
                }
 
1381
                break;
 
1382
        case FLASH_MANUF_ID_FUJITSU:
 
1383
                switch (sec_prot) {
 
1384
                case FLASH_DEV_ID_MBM29LV800TE:
 
1385
                case FLASH_DEV_ID_MBM29DL800TA:
 
1386
                        asd_ha->hw_prof.flash.method = FLASH_METHOD_A;
 
1387
                        break;
 
1388
                }
 
1389
                break;
 
1390
        case FLASH_MANUF_ID_MACRONIX:
 
1391
                switch (sec_prot) {
 
1392
                case FLASH_DEV_ID_MX29LV800BT:
 
1393
                        asd_ha->hw_prof.flash.method = FLASH_METHOD_A;
 
1394
                        break;
 
1395
                }
 
1396
                break;
 
1397
        }
 
1398
 
 
1399
        if (asd_ha->hw_prof.flash.method == FLASH_METHOD_UNKNOWN) {
 
1400
                err = asd_reset_flash(asd_ha);
 
1401
                if (err) {
 
1402
                        ASD_DPRINTK("couldn't reset flash. err=%d\n", err);
 
1403
                        return err;
 
1404
                }
 
1405
 
 
1406
                /* Issue Unlock sequence for AM29LV008BT */
 
1407
                asd_write_reg_byte(asd_ha, (reg + 0x555), 0xAA);
 
1408
                asd_write_reg_byte(asd_ha, (reg + 0x2AA), 0x55);
 
1409
                asd_write_reg_byte(asd_ha, (reg + 0x555), 0x90);
 
1410
                manuf_id = asd_read_reg_byte(asd_ha, reg);
 
1411
                dev_id = asd_read_reg_byte(asd_ha, reg + inc);
 
1412
                sec_prot = asd_read_reg_byte(asd_ha, reg + inc + inc);
 
1413
 
 
1414
                ASD_DPRINTK("Flash MethodB manuf_id(0x%x) dev_id(0x%x) sec_prot"
 
1415
                        "(0x%x)\n", manuf_id, dev_id, sec_prot);
 
1416
 
 
1417
                err = asd_reset_flash(asd_ha);
 
1418
                if (err != 0) {
 
1419
                        ASD_DPRINTK("couldn't reset flash. err=%d\n", err);
 
1420
                        return err;
 
1421
                }
 
1422
 
 
1423
                switch (manuf_id) {
 
1424
                case FLASH_MANUF_ID_AMD:
 
1425
                        switch (dev_id) {
 
1426
                        case FLASH_DEV_ID_AM29LV008BT:
 
1427
                                asd_ha->hw_prof.flash.method = FLASH_METHOD_B;
 
1428
                                break;
 
1429
                        default:
 
1430
                                break;
 
1431
                        }
 
1432
                        break;
 
1433
                case FLASH_MANUF_ID_ST:
 
1434
                        switch (dev_id) {
 
1435
                        case FLASH_DEV_ID_STM29008:
 
1436
                                asd_ha->hw_prof.flash.method = FLASH_METHOD_B;
 
1437
                                break;
 
1438
                        default:
 
1439
                                break;
 
1440
                        }
 
1441
                        break;
 
1442
                case FLASH_MANUF_ID_FUJITSU:
 
1443
                        switch (dev_id) {
 
1444
                        case FLASH_DEV_ID_MBM29LV008TA:
 
1445
                                asd_ha->hw_prof.flash.method = FLASH_METHOD_B;
 
1446
                                break;
 
1447
                        }
 
1448
                        break;
 
1449
                case FLASH_MANUF_ID_INTEL:
 
1450
                        switch (dev_id) {
 
1451
                        case FLASH_DEV_ID_I28LV00TAT:
 
1452
                                asd_ha->hw_prof.flash.method = FLASH_METHOD_B;
 
1453
                                break;
 
1454
                        }
 
1455
                        break;
 
1456
                case FLASH_MANUF_ID_MACRONIX:
 
1457
                        switch (dev_id) {
 
1458
                        case FLASH_DEV_ID_I28LV00TAT:
 
1459
                                asd_ha->hw_prof.flash.method = FLASH_METHOD_B;
 
1460
                                break;
 
1461
                        }
 
1462
                        break;
 
1463
                default:
 
1464
                        return FAIL_FIND_FLASH_ID;
 
1465
                }
 
1466
        }
 
1467
 
 
1468
        if (asd_ha->hw_prof.flash.method == FLASH_METHOD_UNKNOWN)
 
1469
              return FAIL_FIND_FLASH_ID;
 
1470
 
 
1471
        asd_ha->hw_prof.flash.manuf = manuf_id;
 
1472
        asd_ha->hw_prof.flash.dev_id = dev_id;
 
1473
        asd_ha->hw_prof.flash.sec_prot = sec_prot;
 
1474
        return 0;
 
1475
}