From 68ce1eb54056e4fad6e73968e958b926d28cb0dd Mon Sep 17 00:00:00 2001 From: Andrew Morton Date: Wed, 21 Sep 2005 09:46:54 -0700 Subject: [SCSI] lpfc build fix gcc-2.95.x doesn't do anonymous unions. Signed-off-by: Andrew Morton Signed-off-by: James Bottomley --- drivers/scsi/lpfc/lpfc_attr.c | 8 ++++---- drivers/scsi/lpfc/lpfc_hbadisc.c | 4 ++-- drivers/scsi/lpfc/lpfc_hw.h | 4 ++-- drivers/scsi/lpfc/lpfc_init.c | 6 +++--- 4 files changed, 11 insertions(+), 11 deletions(-) diff --git a/drivers/scsi/lpfc/lpfc_attr.c b/drivers/scsi/lpfc/lpfc_attr.c index 86eaf6d408d..acae7c48ef7 100644 --- a/drivers/scsi/lpfc/lpfc_attr.c +++ b/drivers/scsi/lpfc/lpfc_attr.c @@ -973,10 +973,10 @@ lpfc_get_host_fabric_name (struct Scsi_Host *shost) if ((phba->fc_flag & FC_FABRIC) || ((phba->fc_topology == TOPOLOGY_LOOP) && (phba->fc_flag & FC_PUBLIC_LOOP))) - node_name = wwn_to_u64(phba->fc_fabparam.nodeName.wwn); + node_name = wwn_to_u64(phba->fc_fabparam.nodeName.u.wwn); else /* fabric is local port if there is no F/FL_Port */ - node_name = wwn_to_u64(phba->fc_nodename.wwn); + node_name = wwn_to_u64(phba->fc_nodename.u.wwn); spin_unlock_irq(shost->host_lock); @@ -1110,7 +1110,7 @@ lpfc_get_starget_node_name(struct scsi_target *starget) /* Search the mapped list for this target ID */ list_for_each_entry(ndlp, &phba->fc_nlpmap_list, nlp_listp) { if (starget->id == ndlp->nlp_sid) { - node_name = wwn_to_u64(ndlp->nlp_nodename.wwn); + node_name = wwn_to_u64(ndlp->nlp_nodename.u.wwn); break; } } @@ -1131,7 +1131,7 @@ lpfc_get_starget_port_name(struct scsi_target *starget) /* Search the mapped list for this target ID */ list_for_each_entry(ndlp, &phba->fc_nlpmap_list, nlp_listp) { if (starget->id == ndlp->nlp_sid) { - port_name = wwn_to_u64(ndlp->nlp_portname.wwn); + port_name = wwn_to_u64(ndlp->nlp_portname.u.wwn); break; } } diff --git a/drivers/scsi/lpfc/lpfc_hbadisc.c b/drivers/scsi/lpfc/lpfc_hbadisc.c index 4fb8eb0c84c..56052f4510c 100644 --- a/drivers/scsi/lpfc/lpfc_hbadisc.c +++ b/drivers/scsi/lpfc/lpfc_hbadisc.c @@ -1019,8 +1019,8 @@ lpfc_register_remote_port(struct lpfc_hba * phba, struct fc_rport_identifiers rport_ids; /* Remote port has reappeared. Re-register w/ FC transport */ - rport_ids.node_name = wwn_to_u64(ndlp->nlp_nodename.wwn); - rport_ids.port_name = wwn_to_u64(ndlp->nlp_portname.wwn); + rport_ids.node_name = wwn_to_u64(ndlp->nlp_nodename.u.wwn); + rport_ids.port_name = wwn_to_u64(ndlp->nlp_portname.u.wwn); rport_ids.port_id = ndlp->nlp_DID; rport_ids.roles = FC_RPORT_ROLE_UNKNOWN; if (ndlp->nlp_type & NLP_FCP_TARGET) diff --git a/drivers/scsi/lpfc/lpfc_hw.h b/drivers/scsi/lpfc/lpfc_hw.h index 047a87c26cc..86c41981188 100644 --- a/drivers/scsi/lpfc/lpfc_hw.h +++ b/drivers/scsi/lpfc/lpfc_hw.h @@ -280,9 +280,9 @@ struct lpfc_name { #define NAME_CCITT_GR_TYPE 0xE uint8_t IEEEextLsb; /* FC Word 0, bit 16:23, IEEE extended Lsb */ uint8_t IEEE[6]; /* FC IEEE address */ - }; + } s; uint8_t wwn[8]; - }; + } u; }; struct csp { diff --git a/drivers/scsi/lpfc/lpfc_init.c b/drivers/scsi/lpfc/lpfc_init.c index 454058f655d..0856ff7d3b3 100644 --- a/drivers/scsi/lpfc/lpfc_init.c +++ b/drivers/scsi/lpfc/lpfc_init.c @@ -285,7 +285,7 @@ lpfc_config_port_post(struct lpfc_hba * phba) if (phba->SerialNumber[0] == 0) { uint8_t *outptr; - outptr = (uint8_t *) & phba->fc_nodename.IEEE[0]; + outptr = &phba->fc_nodename.u.s.IEEE[0]; for (i = 0; i < 12; i++) { status = *outptr++; j = ((status & 0xf0) >> 4); @@ -1523,8 +1523,8 @@ lpfc_pci_probe_one(struct pci_dev *pdev, const struct pci_device_id *pid) * Must done after lpfc_sli_hba_setup() */ - fc_host_node_name(host) = wwn_to_u64(phba->fc_nodename.wwn); - fc_host_port_name(host) = wwn_to_u64(phba->fc_portname.wwn); + fc_host_node_name(host) = wwn_to_u64(phba->fc_nodename.u.wwn); + fc_host_port_name(host) = wwn_to_u64(phba->fc_portname.u.wwn); fc_host_supported_classes(host) = FC_COS_CLASS3; memset(fc_host_supported_fc4s(host), 0, -- cgit v1.2.3 From 49bfd8db4a39ea14fb3780b162012b4b3611fce8 Mon Sep 17 00:00:00 2001 From: adam radford Date: Wed, 21 Sep 2005 17:20:14 -0700 Subject: [SCSI] 3ware 9000: Add support for 9550SX controllers Signed-off-by: Adam Radford Signed-off-by: James Bottomley --- drivers/scsi/3w-9xxx.c | 55 ++++++++++++++++++++++++++++++++++++++++++-------- drivers/scsi/3w-9xxx.h | 17 +++++++++------- 2 files changed, 57 insertions(+), 15 deletions(-) diff --git a/drivers/scsi/3w-9xxx.c b/drivers/scsi/3w-9xxx.c index a6ac61611f3..a748fbfb669 100644 --- a/drivers/scsi/3w-9xxx.c +++ b/drivers/scsi/3w-9xxx.c @@ -60,6 +60,7 @@ Remove un-needed eh_abort handler. Add support for embedded firmware error strings. 2.26.02.003 - Correctly handle single sgl's with use_sg=1. + 2.26.02.004 - Add support for 9550SX controllers. */ #include @@ -82,7 +83,7 @@ #include "3w-9xxx.h" /* Globals */ -#define TW_DRIVER_VERSION "2.26.02.003" +#define TW_DRIVER_VERSION "2.26.02.004" static TW_Device_Extension *twa_device_extension_list[TW_MAX_SLOT]; static unsigned int twa_device_extension_count; static int twa_major = -1; @@ -892,11 +893,6 @@ static int twa_decode_bits(TW_Device_Extension *tw_dev, u32 status_reg_value) writel(TW_CONTROL_CLEAR_QUEUE_ERROR, TW_CONTROL_REG_ADDR(tw_dev)); } - if (status_reg_value & TW_STATUS_SBUF_WRITE_ERROR) { - TW_PRINTK(tw_dev->host, TW_DRIVER, 0xf, "SBUF Write Error: clearing"); - writel(TW_CONTROL_CLEAR_SBUF_WRITE_ERROR, TW_CONTROL_REG_ADDR(tw_dev)); - } - if (status_reg_value & TW_STATUS_MICROCONTROLLER_ERROR) { if (tw_dev->reset_print == 0) { TW_PRINTK(tw_dev->host, TW_DRIVER, 0x10, "Microcontroller Error: clearing"); @@ -930,6 +926,36 @@ out: return retval; } /* End twa_empty_response_queue() */ +/* This function will clear the pchip/response queue on 9550SX */ +static int twa_empty_response_queue_large(TW_Device_Extension *tw_dev) +{ + u32 status_reg_value, response_que_value; + int count = 0, retval = 1; + + if (tw_dev->tw_pci_dev->device == PCI_DEVICE_ID_3WARE_9550SX) { + status_reg_value = readl(TW_STATUS_REG_ADDR(tw_dev)); + + while (((status_reg_value & TW_STATUS_RESPONSE_QUEUE_EMPTY) == 0) && (count < TW_MAX_RESPONSE_DRAIN)) { + response_que_value = readl(TW_RESPONSE_QUEUE_REG_ADDR_LARGE(tw_dev)); + if ((response_que_value & TW_9550SX_DRAIN_COMPLETED) == TW_9550SX_DRAIN_COMPLETED) { + /* P-chip settle time */ + msleep(500); + retval = 0; + goto out; + } + status_reg_value = readl(TW_STATUS_REG_ADDR(tw_dev)); + count++; + } + if (count == TW_MAX_RESPONSE_DRAIN) + goto out; + + retval = 0; + } else + retval = 0; +out: + return retval; +} /* End twa_empty_response_queue_large() */ + /* This function passes sense keys from firmware to scsi layer */ static int twa_fill_sense(TW_Device_Extension *tw_dev, int request_id, int copy_sense, int print_host) { @@ -1613,8 +1639,16 @@ static int twa_reset_sequence(TW_Device_Extension *tw_dev, int soft_reset) int tries = 0, retval = 1, flashed = 0, do_soft_reset = soft_reset; while (tries < TW_MAX_RESET_TRIES) { - if (do_soft_reset) + if (do_soft_reset) { TW_SOFT_RESET(tw_dev); + /* Clear pchip/response queue on 9550SX */ + if (twa_empty_response_queue_large(tw_dev)) { + TW_PRINTK(tw_dev->host, TW_DRIVER, 0x36, "Response queue (large) empty failed during reset sequence"); + do_soft_reset = 1; + tries++; + continue; + } + } /* Make sure controller is in a good state */ if (twa_poll_status(tw_dev, TW_STATUS_MICROCONTROLLER_READY | (do_soft_reset == 1 ? TW_STATUS_ATTENTION_INTERRUPT : 0), 60)) { @@ -2034,7 +2068,10 @@ static int __devinit twa_probe(struct pci_dev *pdev, const struct pci_device_id goto out_free_device_extension; } - mem_addr = pci_resource_start(pdev, 1); + if (pdev->device == PCI_DEVICE_ID_3WARE_9000) + mem_addr = pci_resource_start(pdev, 1); + else + mem_addr = pci_resource_start(pdev, 2); /* Save base address */ tw_dev->base_addr = ioremap(mem_addr, PAGE_SIZE); @@ -2148,6 +2185,8 @@ static void twa_remove(struct pci_dev *pdev) static struct pci_device_id twa_pci_tbl[] __devinitdata = { { PCI_VENDOR_ID_3WARE, PCI_DEVICE_ID_3WARE_9000, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, + { PCI_VENDOR_ID_3WARE, PCI_DEVICE_ID_3WARE_9550SX, + PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, { } }; MODULE_DEVICE_TABLE(pci, twa_pci_tbl); diff --git a/drivers/scsi/3w-9xxx.h b/drivers/scsi/3w-9xxx.h index 8c8ecbed3b5..46f22cdc829 100644 --- a/drivers/scsi/3w-9xxx.h +++ b/drivers/scsi/3w-9xxx.h @@ -267,7 +267,6 @@ static twa_message_type twa_error_table[] = { #define TW_CONTROL_CLEAR_PARITY_ERROR 0x00800000 #define TW_CONTROL_CLEAR_QUEUE_ERROR 0x00400000 #define TW_CONTROL_CLEAR_PCI_ABORT 0x00100000 -#define TW_CONTROL_CLEAR_SBUF_WRITE_ERROR 0x00000008 /* Status register bit definitions */ #define TW_STATUS_MAJOR_VERSION_MASK 0xF0000000 @@ -285,9 +284,8 @@ static twa_message_type twa_error_table[] = { #define TW_STATUS_MICROCONTROLLER_READY 0x00002000 #define TW_STATUS_COMMAND_QUEUE_EMPTY 0x00001000 #define TW_STATUS_EXPECTED_BITS 0x00002000 -#define TW_STATUS_UNEXPECTED_BITS 0x00F00008 -#define TW_STATUS_SBUF_WRITE_ERROR 0x00000008 -#define TW_STATUS_VALID_INTERRUPT 0x00DF0008 +#define TW_STATUS_UNEXPECTED_BITS 0x00F00000 +#define TW_STATUS_VALID_INTERRUPT 0x00DF0000 /* RESPONSE QUEUE BIT DEFINITIONS */ #define TW_RESPONSE_ID_MASK 0x00000FF0 @@ -324,9 +322,9 @@ static twa_message_type twa_error_table[] = { /* Compatibility defines */ #define TW_9000_ARCH_ID 0x5 -#define TW_CURRENT_DRIVER_SRL 28 -#define TW_CURRENT_DRIVER_BUILD 9 -#define TW_CURRENT_DRIVER_BRANCH 4 +#define TW_CURRENT_DRIVER_SRL 30 +#define TW_CURRENT_DRIVER_BUILD 80 +#define TW_CURRENT_DRIVER_BRANCH 0 /* Phase defines */ #define TW_PHASE_INITIAL 0 @@ -334,6 +332,7 @@ static twa_message_type twa_error_table[] = { #define TW_PHASE_SGLIST 2 /* Misc defines */ +#define TW_9550SX_DRAIN_COMPLETED 0xFFFF #define TW_SECTOR_SIZE 512 #define TW_ALIGNMENT_9000 4 /* 4 bytes */ #define TW_ALIGNMENT_9000_SGL 0x3 @@ -417,6 +416,9 @@ static twa_message_type twa_error_table[] = { #ifndef PCI_DEVICE_ID_3WARE_9000 #define PCI_DEVICE_ID_3WARE_9000 0x1002 #endif +#ifndef PCI_DEVICE_ID_3WARE_9550SX +#define PCI_DEVICE_ID_3WARE_9550SX 0x1003 +#endif /* Bitmask macros to eliminate bitfields */ @@ -443,6 +445,7 @@ static twa_message_type twa_error_table[] = { #define TW_STATUS_REG_ADDR(x) ((unsigned char __iomem *)x->base_addr + 0x4) #define TW_COMMAND_QUEUE_REG_ADDR(x) (sizeof(dma_addr_t) > 4 ? ((unsigned char __iomem *)x->base_addr + 0x20) : ((unsigned char __iomem *)x->base_addr + 0x8)) #define TW_RESPONSE_QUEUE_REG_ADDR(x) ((unsigned char __iomem *)x->base_addr + 0xC) +#define TW_RESPONSE_QUEUE_REG_ADDR_LARGE(x) ((unsigned char __iomem *)x->base_addr + 0x30) #define TW_CLEAR_ALL_INTERRUPTS(x) (writel(TW_STATUS_VALID_INTERRUPT, TW_CONTROL_REG_ADDR(x))) #define TW_CLEAR_ATTENTION_INTERRUPT(x) (writel(TW_CONTROL_CLEAR_ATTENTION_INTERRUPT, TW_CONTROL_REG_ADDR(x))) #define TW_CLEAR_HOST_INTERRUPT(x) (writel(TW_CONTROL_CLEAR_HOST_INTERRUPT, TW_CONTROL_REG_ADDR(x))) -- cgit v1.2.3 From 6f3a20242db2597312c50abc11f1e747c5d2326a Mon Sep 17 00:00:00 2001 From: James Bottomley Date: Thu, 22 Sep 2005 20:33:28 -0500 Subject: [SCSI] allow REPORT LUN scanning even for LUN 0 PQ of 3 Currently we just ignore the device, which means there are a few arrays out there that we don't find. This patch updates the scsi_report_lun_scan() to take a target instead of a device so it can be called on a return of SCSI_SCAN_TARGET_PRESENT, which is what a PQ 3 device returns. Signed-off-by: James Bottomley --- drivers/scsi/scsi_scan.c | 96 +++++++++++++++++++++++----------------------- include/scsi/scsi_device.h | 1 + 2 files changed, 48 insertions(+), 49 deletions(-) diff --git a/drivers/scsi/scsi_scan.c b/drivers/scsi/scsi_scan.c index fcf9f6cbb14..327c5d7e5bd 100644 --- a/drivers/scsi/scsi_scan.c +++ b/drivers/scsi/scsi_scan.c @@ -587,6 +587,7 @@ static int scsi_probe_lun(struct scsi_device *sdev, char *inq_result, if (sdev->scsi_level >= 2 || (sdev->scsi_level == 1 && (inq_result[3] & 0x0f) == 1)) sdev->scsi_level++; + sdev->sdev_target->scsi_level = sdev->scsi_level; return 0; } @@ -771,6 +772,15 @@ static int scsi_add_lun(struct scsi_device *sdev, char *inq_result, int *bflags) return SCSI_SCAN_LUN_PRESENT; } +static inline void scsi_destroy_sdev(struct scsi_device *sdev) +{ + if (sdev->host->hostt->slave_destroy) + sdev->host->hostt->slave_destroy(sdev); + transport_destroy_device(&sdev->sdev_gendev); + put_device(&sdev->sdev_gendev); +} + + /** * scsi_probe_and_add_lun - probe a LUN, if a LUN is found add it * @starget: pointer to target device structure @@ -803,9 +813,9 @@ static int scsi_probe_and_add_lun(struct scsi_target *starget, * The rescan flag is used as an optimization, the first scan of a * host adapter calls into here with rescan == 0. */ - if (rescan) { - sdev = scsi_device_lookup_by_target(starget, lun); - if (sdev) { + sdev = scsi_device_lookup_by_target(starget, lun); + if (sdev) { + if (rescan || sdev->sdev_state != SDEV_CREATED) { SCSI_LOG_SCAN_BUS(3, printk(KERN_INFO "scsi scan: device exists on %s\n", sdev->sdev_gendev.bus_id)); @@ -820,9 +830,9 @@ static int scsi_probe_and_add_lun(struct scsi_target *starget, sdev->model); return SCSI_SCAN_LUN_PRESENT; } - } - - sdev = scsi_alloc_sdev(starget, lun, hostdata); + scsi_device_put(sdev); + } else + sdev = scsi_alloc_sdev(starget, lun, hostdata); if (!sdev) goto out; @@ -877,12 +887,8 @@ static int scsi_probe_and_add_lun(struct scsi_target *starget, res = SCSI_SCAN_NO_RESPONSE; } } - } else { - if (sdev->host->hostt->slave_destroy) - sdev->host->hostt->slave_destroy(sdev); - transport_destroy_device(&sdev->sdev_gendev); - put_device(&sdev->sdev_gendev); - } + } else + scsi_destroy_sdev(sdev); out: return res; } @@ -1054,7 +1060,7 @@ EXPORT_SYMBOL(int_to_scsilun); * 0: scan completed (or no memory, so further scanning is futile) * 1: no report lun scan, or not configured **/ -static int scsi_report_lun_scan(struct scsi_device *sdev, int bflags, +static int scsi_report_lun_scan(struct scsi_target *starget, int bflags, int rescan) { char devname[64]; @@ -1067,7 +1073,8 @@ static int scsi_report_lun_scan(struct scsi_device *sdev, int bflags, struct scsi_lun *lunp, *lun_data; u8 *data; struct scsi_sense_hdr sshdr; - struct scsi_target *starget = scsi_target(sdev); + struct scsi_device *sdev; + struct Scsi_Host *shost = dev_to_shost(&starget->dev); /* * Only support SCSI-3 and up devices if BLIST_NOREPORTLUN is not set. @@ -1075,15 +1082,23 @@ static int scsi_report_lun_scan(struct scsi_device *sdev, int bflags, * support more than 8 LUNs. */ if ((bflags & BLIST_NOREPORTLUN) || - sdev->scsi_level < SCSI_2 || - (sdev->scsi_level < SCSI_3 && - (!(bflags & BLIST_REPORTLUN2) || sdev->host->max_lun <= 8)) ) + starget->scsi_level < SCSI_2 || + (starget->scsi_level < SCSI_3 && + (!(bflags & BLIST_REPORTLUN2) || shost->max_lun <= 8)) ) return 1; if (bflags & BLIST_NOLUN) return 0; + if (!(sdev = scsi_device_lookup_by_target(starget, 0))) { + sdev = scsi_alloc_sdev(starget, 0, NULL); + if (!sdev) + return 0; + if (scsi_device_get(sdev)) + return 0; + } + sprintf(devname, "host %d channel %d id %d", - sdev->host->host_no, sdev->channel, sdev->id); + shost->host_no, sdev->channel, sdev->id); /* * Allocate enough to hold the header (the same size as one scsi_lun) @@ -1098,8 +1113,10 @@ static int scsi_report_lun_scan(struct scsi_device *sdev, int bflags, length = (max_scsi_report_luns + 1) * sizeof(struct scsi_lun); lun_data = kmalloc(length, GFP_ATOMIC | (sdev->host->unchecked_isa_dma ? __GFP_DMA : 0)); - if (!lun_data) + if (!lun_data) { + printk(ALLOC_FAILURE_MSG, __FUNCTION__); goto out; + } scsi_cmd[0] = REPORT_LUNS; @@ -1201,10 +1218,6 @@ static int scsi_report_lun_scan(struct scsi_device *sdev, int bflags, for (i = 0; i < sizeof(struct scsi_lun); i++) printk("%02x", data[i]); printk(" has a LUN larger than currently supported.\n"); - } else if (lun == 0) { - /* - * LUN 0 has already been scanned. - */ } else if (lun > sdev->host->max_lun) { printk(KERN_WARNING "scsi: %s lun%d has a LUN larger" " than allowed by the host adapter\n", @@ -1227,13 +1240,13 @@ static int scsi_report_lun_scan(struct scsi_device *sdev, int bflags, } kfree(lun_data); - return 0; - out: - /* - * We are out of memory, don't try scanning any further. - */ - printk(ALLOC_FAILURE_MSG, __FUNCTION__); + scsi_device_put(sdev); + if (sdev->sdev_state == SDEV_CREATED) + /* + * the sdev we used didn't appear in the report luns scan + */ + scsi_destroy_sdev(sdev); return 0; } @@ -1299,7 +1312,6 @@ static void __scsi_scan_target(struct device *parent, unsigned int channel, struct Scsi_Host *shost = dev_to_shost(parent); int bflags = 0; int res; - struct scsi_device *sdev = NULL; struct scsi_target *starget; if (shost->this_id == id) @@ -1325,27 +1337,16 @@ static void __scsi_scan_target(struct device *parent, unsigned int channel, * Scan LUN 0, if there is some response, scan further. Ideally, we * would not configure LUN 0 until all LUNs are scanned. */ - res = scsi_probe_and_add_lun(starget, 0, &bflags, &sdev, rescan, NULL); - if (res == SCSI_SCAN_LUN_PRESENT) { - if (scsi_report_lun_scan(sdev, bflags, rescan) != 0) + res = scsi_probe_and_add_lun(starget, 0, &bflags, NULL, rescan, NULL); + if (res == SCSI_SCAN_LUN_PRESENT || res == SCSI_SCAN_TARGET_PRESENT) { + if (scsi_report_lun_scan(starget, bflags, rescan) != 0) /* * The REPORT LUN did not scan the target, * do a sequential scan. */ scsi_sequential_lun_scan(starget, bflags, - res, sdev->scsi_level, rescan); - } else if (res == SCSI_SCAN_TARGET_PRESENT) { - /* - * There's a target here, but lun 0 is offline so we - * can't use the report_lun scan. Fall back to a - * sequential lun scan with a bflags of SPARSELUN and - * a default scsi level of SCSI_2 - */ - scsi_sequential_lun_scan(starget, BLIST_SPARSELUN, - SCSI_SCAN_TARGET_PRESENT, SCSI_2, rescan); + res, starget->scsi_level, rescan); } - if (sdev) - scsi_device_put(sdev); out_reap: /* now determine if the target has any children at all @@ -1542,10 +1543,7 @@ void scsi_free_host_dev(struct scsi_device *sdev) { BUG_ON(sdev->id != sdev->host->this_id); - if (sdev->host->hostt->slave_destroy) - sdev->host->hostt->slave_destroy(sdev); - transport_destroy_device(&sdev->sdev_gendev); - put_device(&sdev->sdev_gendev); + scsi_destroy_sdev(sdev); } EXPORT_SYMBOL(scsi_free_host_dev); diff --git a/include/scsi/scsi_device.h b/include/scsi/scsi_device.h index c0e4c67d836..7ece05666fe 100644 --- a/include/scsi/scsi_device.h +++ b/include/scsi/scsi_device.h @@ -163,6 +163,7 @@ struct scsi_target { unsigned int id; /* target id ... replace * scsi_device.id eventually */ unsigned long create:1; /* signal that it needs to be added */ + char scsi_level; void *hostdata; /* available to low-level driver */ unsigned long starget_data[0]; /* for the transport */ /* starget_data must be the last element!!!! */ -- cgit v1.2.3 From 44550322cb601ac3f882e7438bbeec971fa1b1a3 Mon Sep 17 00:00:00 2001 From: Andrew Vasquez Date: Tue, 20 Sep 2005 13:32:11 -0700 Subject: [SCSI] qla2xxx: fix remote port timeout with qla2xxx driver This patch fixes a hole in the rport unblock handling when processing fabric events via the ADISC/PLOGI device state machine. Original code would not properly 'unblock' the port upon the port reloging into the fabric. Signed-off-by: Andrew Vasquez Signed-off-by: James Bottomley --- drivers/scsi/qla2xxx/qla_rscn.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/drivers/scsi/qla2xxx/qla_rscn.c b/drivers/scsi/qla2xxx/qla_rscn.c index bdc3bc74bbe..1eba9882863 100644 --- a/drivers/scsi/qla2xxx/qla_rscn.c +++ b/drivers/scsi/qla2xxx/qla_rscn.c @@ -330,6 +330,8 @@ qla2x00_update_login_fcport(scsi_qla_host_t *ha, struct mbx_entry *mbxstat, fcport->flags &= ~FCF_FAILOVER_NEEDED; fcport->iodesc_idx_sent = IODESC_INVALID_INDEX; atomic_set(&fcport->state, FCS_ONLINE); + if (fcport->rport) + fc_remote_port_unblock(fcport->rport); } -- cgit v1.2.3 From f04da5def8c460b1b52d3142da827ab01efa3a15 Mon Sep 17 00:00:00 2001 From: Ben Dooks Date: Sun, 25 Sep 2005 23:02:49 +0100 Subject: [ARM] 2933/1: S3C2410 - fix serial port warnings Patch from Ben Dooks Fix the following warnings produced from drivers/char/s3c2410.c. drivers/serial/s3c2410.c:757: warning: 'clk' may be used uninitialized drivers/serial/s3c2410.c:756: warning: 'clksrc' may be used uninitialized Signed-off-by: Ben Dooks Signed-off-by: Russell King --- drivers/serial/s3c2410.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/serial/s3c2410.c b/drivers/serial/s3c2410.c index c361c6fb080..1195e6a0901 100644 --- a/drivers/serial/s3c2410.c +++ b/drivers/serial/s3c2410.c @@ -753,8 +753,8 @@ static void s3c24xx_serial_set_termios(struct uart_port *port, { struct s3c2410_uartcfg *cfg = s3c24xx_port_to_cfg(port); struct s3c24xx_uart_port *ourport = to_ourport(port); - struct s3c24xx_uart_clksrc *clksrc; - struct clk *clk; + struct s3c24xx_uart_clksrc *clksrc = NULL; + struct clk *clk = NULL; unsigned long flags; unsigned int baud, quot; unsigned int ulcon; -- cgit v1.2.3 From fe8b2304e54552cea113318e2f66c45628130fdc Mon Sep 17 00:00:00 2001 From: Christoph Hellwig Date: Sun, 25 Sep 2005 23:10:33 +0200 Subject: [SCSI] sas: fix remote phy removal Brown paperbag bug: sas_rphy_delete was ordered completely wrong. Fix it up to be the same order as sas_phy_delete or fc_rport_terminate and fix rphy objects that leaked after module removal. Signed-off-by: Christoph Hellwig Signed-off-by: James Bottomley --- drivers/scsi/scsi_transport_sas.c | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/drivers/scsi/scsi_transport_sas.c b/drivers/scsi/scsi_transport_sas.c index ff724bbe661..1d145d2f9a3 100644 --- a/drivers/scsi/scsi_transport_sas.c +++ b/drivers/scsi/scsi_transport_sas.c @@ -628,17 +628,16 @@ sas_rphy_delete(struct sas_rphy *rphy) struct Scsi_Host *shost = dev_to_shost(parent->dev.parent); struct sas_host_attrs *sas_host = to_sas_host_attrs(shost); - transport_destroy_device(&rphy->dev); + scsi_remove_target(dev); - scsi_remove_target(&rphy->dev); + transport_remove_device(dev); + device_del(dev); + transport_destroy_device(dev); spin_lock(&sas_host->lock); list_del(&rphy->list); spin_unlock(&sas_host->lock); - transport_remove_device(dev); - device_del(dev); - transport_destroy_device(dev); put_device(&parent->dev); } EXPORT_SYMBOL(sas_rphy_delete); -- cgit v1.2.3 From c4a3e0a529ab3e65223e81681c7c6b1bc188fa58 Mon Sep 17 00:00:00 2001 From: "Bagalkote, Sreenivas" Date: Tue, 20 Sep 2005 17:46:58 -0400 Subject: [SCSI] MegaRAID SAS RAID: new driver Signed-off-by: Sreenivas Bagalkote Signed-off-by: James Bottomley --- drivers/scsi/Makefile | 1 + drivers/scsi/megaraid/Kconfig.megaraid | 9 + drivers/scsi/megaraid/Makefile | 1 + drivers/scsi/megaraid/megaraid_sas.c | 2805 ++++++++++++++++++++++++++++++++ drivers/scsi/megaraid/megaraid_sas.h | 1142 +++++++++++++ include/linux/pci_ids.h | 2 + 6 files changed, 3960 insertions(+) create mode 100644 drivers/scsi/megaraid/megaraid_sas.c create mode 100644 drivers/scsi/megaraid/megaraid_sas.h diff --git a/drivers/scsi/Makefile b/drivers/scsi/Makefile index 1e4edbdf273..48529d180ca 100644 --- a/drivers/scsi/Makefile +++ b/drivers/scsi/Makefile @@ -99,6 +99,7 @@ obj-$(CONFIG_SCSI_DC395x) += dc395x.o obj-$(CONFIG_SCSI_DC390T) += tmscsim.o obj-$(CONFIG_MEGARAID_LEGACY) += megaraid.o obj-$(CONFIG_MEGARAID_NEWGEN) += megaraid/ +obj-$(CONFIG_MEGARAID_SAS) += megaraid/ obj-$(CONFIG_SCSI_ACARD) += atp870u.o obj-$(CONFIG_SCSI_SUNESP) += esp.o obj-$(CONFIG_SCSI_GDTH) += gdth.o diff --git a/drivers/scsi/megaraid/Kconfig.megaraid b/drivers/scsi/megaraid/Kconfig.megaraid index 917d591d90b..7363e12663a 100644 --- a/drivers/scsi/megaraid/Kconfig.megaraid +++ b/drivers/scsi/megaraid/Kconfig.megaraid @@ -76,3 +76,12 @@ config MEGARAID_LEGACY To compile this driver as a module, choose M here: the module will be called megaraid endif + +config MEGARAID_SAS + tristate "LSI Logic MegaRAID SAS RAID Module" + depends on PCI && SCSI + help + Module for LSI Logic's SAS based RAID controllers. + To compile this driver as a module, choose 'm' here. + Module will be called megaraid_sas + diff --git a/drivers/scsi/megaraid/Makefile b/drivers/scsi/megaraid/Makefile index 6dd99f27572..f469915b97c 100644 --- a/drivers/scsi/megaraid/Makefile +++ b/drivers/scsi/megaraid/Makefile @@ -1,2 +1,3 @@ obj-$(CONFIG_MEGARAID_MM) += megaraid_mm.o obj-$(CONFIG_MEGARAID_MAILBOX) += megaraid_mbox.o +obj-$(CONFIG_MEGARAID_SAS) += megaraid_sas.o diff --git a/drivers/scsi/megaraid/megaraid_sas.c b/drivers/scsi/megaraid/megaraid_sas.c new file mode 100644 index 00000000000..1b3148e842a --- /dev/null +++ b/drivers/scsi/megaraid/megaraid_sas.c @@ -0,0 +1,2805 @@ +/* + * + * Linux MegaRAID driver for SAS based RAID controllers + * + * Copyright (c) 2003-2005 LSI Logic Corporation. + * + * 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. + * + * FILE : megaraid_sas.c + * Version : v00.00.02.00-rc4 + * + * Authors: + * Sreenivas Bagalkote + * Sumant Patro + * + * List of supported controllers + * + * OEM Product Name VID DID SSVID SSID + * --- ------------ --- --- ---- ---- + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include "megaraid_sas.h" + +MODULE_LICENSE("GPL"); +MODULE_VERSION(MEGASAS_VERSION); +MODULE_AUTHOR("sreenivas.bagalkote@lsil.com"); +MODULE_DESCRIPTION("LSI Logic MegaRAID SAS Driver"); + +/* + * PCI ID table for all supported controllers + */ +static struct pci_device_id megasas_pci_table[] = { + + { + PCI_VENDOR_ID_LSI_LOGIC, + PCI_DEVICE_ID_LSI_SAS1064R, + PCI_ANY_ID, + PCI_ANY_ID, + }, + { + PCI_VENDOR_ID_DELL, + PCI_DEVICE_ID_DELL_PERC5, + PCI_ANY_ID, + PCI_ANY_ID, + }, + {0} /* Terminating entry */ +}; + +MODULE_DEVICE_TABLE(pci, megasas_pci_table); + +static int megasas_mgmt_majorno; +static struct megasas_mgmt_info megasas_mgmt_info; +static struct fasync_struct *megasas_async_queue; +static DECLARE_MUTEX(megasas_async_queue_mutex); + +/** + * megasas_get_cmd - Get a command from the free pool + * @instance: Adapter soft state + * + * Returns a free command from the pool + */ +static inline struct megasas_cmd *megasas_get_cmd(struct megasas_instance + *instance) +{ + unsigned long flags; + struct megasas_cmd *cmd = NULL; + + spin_lock_irqsave(&instance->cmd_pool_lock, flags); + + if (!list_empty(&instance->cmd_pool)) { + cmd = list_entry((&instance->cmd_pool)->next, + struct megasas_cmd, list); + list_del_init(&cmd->list); + } else { + printk(KERN_ERR "megasas: Command pool empty!\n"); + } + + spin_unlock_irqrestore(&instance->cmd_pool_lock, flags); + return cmd; +} + +/** + * megasas_return_cmd - Return a cmd to free command pool + * @instance: Adapter soft state + * @cmd: Command packet to be returned to free command pool + */ +static inline void +megasas_return_cmd(struct megasas_instance *instance, struct megasas_cmd *cmd) +{ + unsigned long flags; + + spin_lock_irqsave(&instance->cmd_pool_lock, flags); + + cmd->scmd = NULL; + list_add_tail(&cmd->list, &instance->cmd_pool); + + spin_unlock_irqrestore(&instance->cmd_pool_lock, flags); +} + +/** + * megasas_enable_intr - Enables interrupts + * @regs: MFI register set + */ +static inline void +megasas_enable_intr(struct megasas_register_set __iomem * regs) +{ + writel(1, &(regs)->outbound_intr_mask); + + /* Dummy readl to force pci flush */ + readl(®s->outbound_intr_mask); +} + +/** + * megasas_disable_intr - Disables interrupts + * @regs: MFI register set + */ +static inline void +megasas_disable_intr(struct megasas_register_set __iomem * regs) +{ + u32 mask = readl(®s->outbound_intr_mask) & (~0x00000001); + writel(mask, ®s->outbound_intr_mask); + + /* Dummy readl to force pci flush */ + readl(®s->outbound_intr_mask); +} + +/** + * megasas_issue_polled - Issues a polling command + * @instance: Adapter soft state + * @cmd: Command packet to be issued + * + * For polling, MFI requires the cmd_status to be set to 0xFF before posting. + */ +static int +megasas_issue_polled(struct megasas_instance *instance, struct megasas_cmd *cmd) +{ + int i; + u32 msecs = MFI_POLL_TIMEOUT_SECS * 1000; + + struct megasas_header *frame_hdr = &cmd->frame->hdr; + + frame_hdr->cmd_status = 0xFF; + frame_hdr->flags |= MFI_FRAME_DONT_POST_IN_REPLY_QUEUE; + + /* + * Issue the frame using inbound queue port + */ + writel(cmd->frame_phys_addr >> 3, + &instance->reg_set->inbound_queue_port); + + /* + * Wait for cmd_status to change + */ + for (i = 0; (i < msecs) && (frame_hdr->cmd_status == 0xff); i++) { + rmb(); + msleep(1); + } + + if (frame_hdr->cmd_status == 0xff) + return -ETIME; + + return 0; +} + +/** + * megasas_issue_blocked_cmd - Synchronous wrapper around regular FW cmds + * @instance: Adapter soft state + * @cmd: Command to be issued + * + * This function waits on an event for the command to be returned from ISR. + * Used to issue ioctl commands. + */ +static int +megasas_issue_blocked_cmd(struct megasas_instance *instance, + struct megasas_cmd *cmd) +{ + cmd->cmd_status = ENODATA; + + writel(cmd->frame_phys_addr >> 3, + &instance->reg_set->inbound_queue_port); + + wait_event(instance->int_cmd_wait_q, (cmd->cmd_status != ENODATA)); + + return 0; +} + +/** + * megasas_issue_blocked_abort_cmd - Aborts previously issued cmd + * @instance: Adapter soft state + * @cmd_to_abort: Previously issued cmd to be aborted + * + * MFI firmware can abort previously issued AEN comamnd (automatic event + * notification). The megasas_issue_blocked_abort_cmd() issues such abort + * cmd and blocks till it is completed. + */ +static int +megasas_issue_blocked_abort_cmd(struct megasas_instance *instance, + struct megasas_cmd *cmd_to_abort) +{ + struct megasas_cmd *cmd; + struct megasas_abort_frame *abort_fr; + + cmd = megasas_get_cmd(instance); + + if (!cmd) + return -1; + + abort_fr = &cmd->frame->abort; + + /* + * Prepare and issue the abort frame + */ + abort_fr->cmd = MFI_CMD_ABORT; + abort_fr->cmd_status = 0xFF; + abort_fr->flags = 0; + abort_fr->abort_context = cmd_to_abort->index; + abort_fr->abort_mfi_phys_addr_lo = cmd_to_abort->frame_phys_addr; + abort_fr->abort_mfi_phys_addr_hi = 0; + + cmd->sync_cmd = 1; + cmd->cmd_status = 0xFF; + + writel(cmd->frame_phys_addr >> 3, + &instance->reg_set->inbound_queue_port); + + /* + * Wait for this cmd to complete + */ + wait_event(instance->abort_cmd_wait_q, (cmd->cmd_status != 0xFF)); + + megasas_return_cmd(instance, cmd); + return 0; +} + +/** + * megasas_make_sgl32 - Prepares 32-bit SGL + * @instance: Adapter soft state + * @scp: SCSI command from the mid-layer + * @mfi_sgl: SGL to be filled in + * + * If successful, this function returns the number of SG elements. Otherwise, + * it returnes -1. + */ +static inline int +megasas_make_sgl32(struct megasas_instance *instance, struct scsi_cmnd *scp, + union megasas_sgl *mfi_sgl) +{ + int i; + int sge_count; + struct scatterlist *os_sgl; + + /* + * Return 0 if there is no data transfer + */ + if (!scp->request_buffer || !scp->request_bufflen) + return 0; + + if (!scp->use_sg) { + mfi_sgl->sge32[0].phys_addr = pci_map_single(instance->pdev, + scp-> + request_buffer, + scp-> + request_bufflen, + scp-> + sc_data_direction); + mfi_sgl->sge32[0].length = scp->request_bufflen; + + return 1; + } + + os_sgl = (struct scatterlist *)scp->request_buffer; + sge_count = pci_map_sg(instance->pdev, os_sgl, scp->use_sg, + scp->sc_data_direction); + + for (i = 0; i < sge_count; i++, os_sgl++) { + mfi_sgl->sge32[i].length = sg_dma_len(os_sgl); + mfi_sgl->sge32[i].phys_addr = sg_dma_address(os_sgl); + } + + return sge_count; +} + +/** + * megasas_make_sgl64 - Prepares 64-bit SGL + * @instance: Adapter soft state + * @scp: SCSI command from the mid-layer + * @mfi_sgl: SGL to be filled in + * + * If successful, this function returns the number of SG elements. Otherwise, + * it returnes -1. + */ +static inline int +megasas_make_sgl64(struct megasas_instance *instance, struct scsi_cmnd *scp, + union megasas_sgl *mfi_sgl) +{ + int i; + int sge_count; + struct scatterlist *os_sgl; + + /* + * Return 0 if there is no data transfer + */ + if (!scp->request_buffer || !scp->request_bufflen) + return 0; + + if (!scp->use_sg) { + mfi_sgl->sge64[0].phys_addr = pci_map_single(instance->pdev, + scp-> + request_buffer, + scp-> + request_bufflen, + scp-> + sc_data_direction); + + mfi_sgl->sge64[0].length = scp->request_bufflen; + + return 1; + } + + os_sgl = (struct scatterlist *)scp->request_buffer; + sge_count = pci_map_sg(instance->pdev, os_sgl, scp->use_sg, + scp->sc_data_direction); + + for (i = 0; i < sge_count; i++, os_sgl++) { + mfi_sgl->sge64[i].length = sg_dma_len(os_sgl); + mfi_sgl->sge64[i].phys_addr = sg_dma_address(os_sgl); + } + + return sge_count; +} + +/** + * megasas_build_dcdb - Prepares a direct cdb (DCDB) command + * @instance: Adapter soft state + * @scp: SCSI command + * @cmd: Command to be prepared in + * + * This function prepares CDB commands. These are typcially pass-through + * commands to the devices. + */ +static inline int +megasas_build_dcdb(struct megasas_instance *instance, struct scsi_cmnd *scp, + struct megasas_cmd *cmd) +{ + u32 sge_sz; + int sge_bytes; + u32 is_logical; + u32 device_id; + u16 flags = 0; + struct megasas_pthru_frame *pthru; + + is_logical = MEGASAS_IS_LOGICAL(scp); + device_id = MEGASAS_DEV_INDEX(instance, scp); + pthru = (struct megasas_pthru_frame *)cmd->frame; + + if (scp->sc_data_direction == PCI_DMA_TODEVICE) + flags = MFI_FRAME_DIR_WRITE; + else if (scp->sc_data_direction == PCI_DMA_FROMDEVICE) + flags = MFI_FRAME_DIR_READ; + else if (scp->sc_data_direction == PCI_DMA_NONE) + flags = MFI_FRAME_DIR_NONE; + + /* + * Prepare the DCDB frame + */ + pthru->cmd = (is_logical) ? MFI_CMD_LD_SCSI_IO : MFI_CMD_PD_SCSI_IO; + pthru->cmd_status = 0x0; + pthru->scsi_status = 0x0; + pthru->target_id = device_id; + pthru->lun = scp->device->lun; + pthru->cdb_len = scp->cmd_len; + pthru->timeout = 0; + pthru->flags = flags; + pthru->data_xfer_len = scp->request_bufflen; + + memcpy(pthru->cdb, scp->cmnd, scp->cmd_len); + + /* + * Construct SGL + */ + sge_sz = (IS_DMA64) ? sizeof(struct megasas_sge64) : + sizeof(struct megasas_sge32); + + if (IS_DMA64) { + pthru->flags |= MFI_FRAME_SGL64; + pthru->sge_count = megasas_make_sgl64(instance, scp, + &pthru->sgl); + } else + pthru->sge_count = megasas_make_sgl32(instance, scp, + &pthru->sgl); + + /* + * Sense info specific + */ + pthru->sense_len = SCSI_SENSE_BUFFERSIZE; + pthru->sense_buf_phys_addr_hi = 0; + pthru->sense_buf_phys_addr_lo = cmd->sense_phys_addr; + + sge_bytes = sge_sz * pthru->sge_count; + + /* + * Compute the total number of frames this command consumes. FW uses + * this number to pull sufficient number of frames from host memory. + */ + cmd->frame_count = (sge_bytes / MEGAMFI_FRAME_SIZE) + + ((sge_bytes % MEGAMFI_FRAME_SIZE) ? 1 : 0) + 1; + + if (cmd->frame_count > 7) + cmd->frame_count = 8; + + return cmd->frame_count; +} + +/** + * megasas_build_ldio - Prepares IOs to logical devices + * @instance: Adapter soft state + * @scp: SCSI command + * @cmd: Command to to be prepared + * + * Frames (and accompanying SGLs) for regular SCSI IOs use this function. + */ +static inline int +megasas_build_ldio(struct megasas_instance *instance, struct scsi_cmnd *scp, + struct megasas_cmd *cmd) +{ + u32 sge_sz; + int sge_bytes; + u32 device_id; + u8 sc = scp->cmnd[0]; + u16 flags = 0; + struct megasas_io_frame *ldio; + + device_id = MEGASAS_DEV_INDEX(instance, scp); + ldio = (struct megasas_io_frame *)cmd->frame; + + if (scp->sc_data_direction == PCI_DMA_TODEVICE) + flags = MFI_FRAME_DIR_WRITE; + else if (scp->sc_data_direction == PCI_DMA_FROMDEVICE) + flags = MFI_FRAME_DIR_READ; + + /* + * Preare the Logical IO frame: 2nd bit is zero for all read cmds + */ + ldio->cmd = (sc & 0x02) ? MFI_CMD_LD_WRITE : MFI_CMD_LD_READ; + ldio->cmd_status = 0x0; + ldio->scsi_status = 0x0; + ldio->target_id = device_id; + ldio->timeout = 0; + ldio->reserved_0 = 0; + ldio->pad_0 = 0; + ldio->flags = flags; + ldio->start_lba_hi = 0; + ldio->access_byte = (scp->cmd_len != 6) ? scp->cmnd[1] : 0; + + /* + * 6-byte READ(0x08) or WRITE(0x0A) cdb + */ + if (scp->cmd_len == 6) { + ldio->lba_count = (u32) scp->cmnd[4]; + ldio->start_lba_lo = ((u32) scp->cmnd[1] << 16) | + ((u32) scp->cmnd[2] << 8) | (u32) scp->cmnd[3]; + + ldio->start_lba_lo &= 0x1FFFFF; + } + + /* + * 10-byte READ(0x28) or WRITE(0x2A) cdb + */ + else if (scp->cmd_len == 10) { + ldio->lba_count = (u32) scp->cmnd[8] | + ((u32) scp->cmnd[7] << 8); + ldio->start_lba_lo = ((u32) scp->cmnd[2] << 24) | + ((u32) scp->cmnd[3] << 16) | + ((u32) scp->cmnd[4] << 8) | (u32) scp->cmnd[5]; + } + + /* + * 12-byte READ(0xA8) or WRITE(0xAA) cdb + */ + else if (scp->cmd_len == 12) { + ldio->lba_count = ((u32) scp->cmnd[6] << 24) | + ((u32) scp->cmnd[7] << 16) | + ((u32) scp->cmnd[8] << 8) | (u32) scp->cmnd[9]; + + ldio->start_lba_lo = ((u32) scp->cmnd[2] << 24) | + ((u32) scp->cmnd[3] << 16) | + ((u32) scp->cmnd[4] << 8) | (u32) scp->cmnd[5]; + } + + /* + * 16-byte READ(0x88) or WRITE(0x8A) cdb + */ + else if (scp->cmd_len == 16) { + ldio->lba_count = ((u32) scp->cmnd[10] << 24) | + ((u32) scp->cmnd[11] << 16) | + ((u32) scp->cmnd[12] << 8) | (u32) scp->cmnd[13]; + + ldio->start_lba_lo = ((u32) scp->cmnd[6] << 24) | + ((u32) scp->cmnd[7] << 16) | + ((u32) scp->cmnd[8] << 8) | (u32) scp->cmnd[9]; + + ldio->start_lba_hi = ((u32) scp->cmnd[2] << 24) | + ((u32) scp->cmnd[3] << 16) | + ((u32) scp->cmnd[4] << 8) | (u32) scp->cmnd[5]; + + } + + /* + * Construct SGL + */ + sge_sz = (IS_DMA64) ? sizeof(struct megasas_sge64) : + sizeof(struct megasas_sge32); + + if (IS_DMA64) { + ldio->flags |= MFI_FRAME_SGL64; + ldio->sge_count = megasas_make_sgl64(instance, scp, &ldio->sgl); + } else + ldio->sge_count = megasas_make_sgl32(instance, scp, &ldio->sgl); + + /* + * Sense info specific + */ + ldio->sense_len = SCSI_SENSE_BUFFERSIZE; + ldio->sense_buf_phys_addr_hi = 0; + ldio->sense_buf_phys_addr_lo = cmd->sense_phys_addr; + + sge_bytes = sge_sz * ldio->sge_count; + + cmd->frame_count = (sge_bytes / MEGAMFI_FRAME_SIZE) + + ((sge_bytes % MEGAMFI_FRAME_SIZE) ? 1 : 0) + 1; + + if (cmd->frame_count > 7) + cmd->frame_count = 8; + + return cmd->frame_count; +} + +/** + * megasas_build_cmd - Prepares a command packet + * @instance: Adapter soft state + * @scp: SCSI command + * @frame_count: [OUT] Number of frames used to prepare this command + */ +static inline struct megasas_cmd *megasas_build_cmd(struct megasas_instance + *instance, + struct scsi_cmnd *scp, + int *frame_count) +{ + u32 logical_cmd; + struct megasas_cmd *cmd; + + /* + * Find out if this is logical or physical drive command. + */ + logical_cmd = MEGASAS_IS_LOGICAL(scp); + + /* + * Logical drive command + */ + if (logical_cmd) { + + if (scp->device->id >= MEGASAS_MAX_LD) { + scp->result = DID_BAD_TARGET << 16; + return NULL; + } + + switch (scp->cmnd[0]) { + + case READ_10: + case WRITE_10: + case READ_12: + case WRITE_12: + case READ_6: + case WRITE_6: + case READ_16: + case WRITE_16: + /* + * Fail for LUN > 0 + */ + if (scp->device->lun) { + scp->result = DID_BAD_TARGET << 16; + return NULL; + } + + cmd = megasas_get_cmd(instance); + + if (!cmd) { + scp->result = DID_IMM_RETRY << 16; + return NULL; + } + + *frame_count = megasas_build_ldio(instance, scp, cmd); + + if (!(*frame_count)) { + megasas_return_cmd(instance, cmd); + return NULL; + } + + return cmd; + + default: + /* + * Fail for LUN > 0 + */ + if (scp->device->lun) { + scp->result = DID_BAD_TARGET << 16; + return NULL; + } + + cmd = megasas_get_cmd(instance); + + if (!cmd) { + scp->result = DID_IMM_RETRY << 16; + return NULL; + } + + *frame_count = megasas_build_dcdb(instance, scp, cmd); + + if (!(*frame_count)) { + megasas_return_cmd(instance, cmd); + return NULL; + } + + return cmd; + } + } else { + cmd = megasas_get_cmd(instance); + + if (!cmd) { + scp->result = DID_IMM_RETRY << 16; + return NULL; + } + + *frame_count = megasas_build_dcdb(instance, scp, cmd); + + if (!(*frame_count)) { + megasas_return_cmd(instance, cmd); + return NULL; + } + + return cmd; + } + + return NULL; +} + +/** + * megasas_queue_command - Queue entry point + * @scmd: SCSI command to be queued + * @done: Callback entry point + */ +static int +megasas_queue_command(struct scsi_cmnd *scmd, void (*done) (struct scsi_cmnd *)) +{ + u32 frame_count; + unsigned long flags; + struct megasas_cmd *cmd; + struct megasas_instance *instance; + + instance = (struct megasas_instance *) + scmd->device->host->hostdata; + scmd->scsi_done = done; + scmd->result = 0; + + cmd = megasas_build_cmd(instance, scmd, &frame_count); + + if (!cmd) { + done(scmd); + return 0; + } + + cmd->scmd = scmd; + scmd->SCp.ptr = (char *)cmd; + scmd->SCp.sent_command = jiffies; + + /* + * Issue the command to the FW + */ + spin_lock_irqsave(&instance->instance_lock, flags); + instance->fw_outstanding++; + spin_unlock_irqrestore(&instance->instance_lock, flags); + + writel(((cmd->frame_phys_addr >> 3) | (cmd->frame_count - 1)), + &instance->reg_set->inbound_queue_port); + + return 0; +} + +/** + * megasas_wait_for_outstanding - Wait for all outstanding cmds + * @instance: Adapter soft state + * + * This function waits for upto MEGASAS_RESET_WAIT_TIME seconds for FW to + * complete all its outstanding commands. Returns error if one or more IOs + * are pending after this time period. It also marks the controller dead. + */ +static int megasas_wait_for_outstanding(struct megasas_instance *instance) +{ + int i; + u32 wait_time = MEGASAS_RESET_WAIT_TIME; + + for (i = 0; i < wait_time; i++) { + + if (!instance->fw_outstanding) + break; + + if (!(i % MEGASAS_RESET_NOTICE_INTERVAL)) { + printk(KERN_NOTICE "megasas: [%2d]waiting for %d " + "commands to complete\n", i, + instance->fw_outstanding); + } + + msleep(1000); + } + + if (instance->fw_outstanding) { + instance->hw_crit_error = 1; + return FAILED; + } + + return SUCCESS; +} + +/** + * megasas_generic_reset - Generic reset routine + * @scmd: Mid-layer SCSI command + * + * This routine implements a generic reset handler for device, bus and host + * reset requests. Device, bus and host specific reset handlers can use this + * function after they do their specific tasks. + */ +static int megasas_generic_reset(struct scsi_cmnd *scmd) +{ + int ret_val; + struct megasas_instance *instance; + + instance = (struct megasas_instance *)scmd->device->host->hostdata; + + printk(KERN_NOTICE "megasas: RESET -%ld cmd=%x \n", + scmd->serial_number, scmd->cmnd[0], scmd->device->channel, + scmd->device->id, scmd->device->lun); + + if (instance->hw_crit_error) { + printk(KERN_ERR "megasas: cannot recover from previous reset " + "failures\n"); + return FAILED; + } + + spin_unlock(scmd->device->host->host_lock); + + ret_val = megasas_wait_for_outstanding(instance); + + if (ret_val == SUCCESS) + printk(KERN_NOTICE "megasas: reset successful \n"); + else + printk(KERN_ERR "megasas: failed to do reset\n"); + + spin_lock(scmd->device->host->host_lock); + + return ret_val; +} + +static enum scsi_eh_timer_return megasas_reset_timer(struct scsi_cmnd *scmd) +{ + unsigned long seconds; + + if (scmd->SCp.ptr) { + seconds = (jiffies - scmd->SCp.sent_command) / HZ; + + if (seconds < 90) { + return EH_RESET_TIMER; + } else { + return EH_NOT_HANDLED; + } + } + + return EH_HANDLED; +} + +/** + * megasas_reset_device - Device reset handler entry point + */ +static int megasas_reset_device(struct scsi_cmnd *scmd) +{ + int ret; + + /* + * First wait for all commands to complete + */ + ret = megasas_generic_reset(scmd); + + return ret; +} + +/** + * megasas_reset_bus_host - Bus & host reset handler entry point + */ +static int megasas_reset_bus_host(struct scsi_cmnd *scmd) +{ + int ret; + + /* + * Frist wait for all commands to complete + */ + ret = megasas_generic_reset(scmd); + + return ret; +} + +/** + * megasas_service_aen - Processes an event notification + * @instance: Adapter soft state + * @cmd: AEN command completed by the ISR + * + * For AEN, driver sends a command down to FW that is held by the FW till an + * event occurs. When an event of interest occurs, FW completes the command + * that it was previously holding. + * + * This routines sends SIGIO signal to processes that have registered with the + * driver for AEN. + */ +static void +megasas_service_aen(struct megasas_instance *instance, struct megasas_cmd *cmd) +{ + /* + * Don't signal app if it is just an aborted previously registered aen + */ + if (!cmd->abort_aen) + kill_fasync(&megasas_async_queue, SIGIO, POLL_IN); + else + cmd->abort_aen = 0; + + instance->aen_cmd = NULL; + megasas_return_cmd(instance, cmd); +} + +/* + * Scsi host template for megaraid_sas driver + */ +static struct scsi_host_template megasas_template = { + + .module = THIS_MODULE, + .name = "LSI Logic SAS based MegaRAID driver", + .proc_name = "megaraid_sas", + .queuecommand = megasas_queue_command, + .eh_device_reset_handler = megasas_reset_device, + .eh_bus_reset_handler = megasas_reset_bus_host, + .eh_host_reset_handler = megasas_reset_bus_host, + .eh_timed_out = megasas_reset_timer, + .use_clustering = ENABLE_CLUSTERING, +}; + +/** + * megasas_complete_int_cmd - Completes an internal command + * @instance: Adapter soft state + * @cmd: Command to be completed + * + * The megasas_issue_blocked_cmd() function waits for a command to complete + * after it issues a command. This function wakes up that waiting routine by + * calling wake_up() on the wait queue. + */ +static void +megasas_complete_int_cmd(struct megasas_instance *instance, + struct megasas_cmd *cmd) +{ + cmd->cmd_status = cmd->frame->io.cmd_status; + + if (cmd->cmd_status == ENODATA) { + cmd->cmd_status = 0; + } + wake_up(&instance->int_cmd_wait_q); +} + +/** + * megasas_complete_abort - Completes aborting a command + * @instance: Adapter soft state + * @cmd: Cmd that was issued to abort another cmd + * + * The megasas_issue_blocked_abort_cmd() function waits on abort_cmd_wait_q + * after it issues an abort on a previously issued command. This function + * wakes up all functions waiting on the same wait queue. + */ +static void +megasas_complete_abort(struct megasas_instance *instance, + struct megasas_cmd *cmd) +{ + if (cmd->sync_cmd) { + cmd->sync_cmd = 0; + cmd->cmd_status = 0; + wake_up(&instance->abort_cmd_wait_q); + } + + return; +} + +/** + * megasas_unmap_sgbuf - Unmap SG buffers + * @instance: Adapter soft state + * @cmd: Completed command + */ +static inline void +megasas_unmap_sgbuf(struct megasas_instance *instance, struct megasas_cmd *cmd) +{ + dma_addr_t buf_h; + u8 opcode; + + if (cmd->scmd->use_sg) { + pci_unmap_sg(instance->pdev, cmd->scmd->request_buffer, + cmd->scmd->use_sg, cmd->scmd->sc_data_direction); + return; + } + + if (!cmd->scmd->request_bufflen) + return; + + opcode = cmd->frame->hdr.cmd; + + if ((opcode == MFI_CMD_LD_READ) || (opcode == MFI_CMD_LD_WRITE)) { + if (IS_DMA64) + buf_h = cmd->frame->io.sgl.sge64[0].phys_addr; + else + buf_h = cmd->frame->io.sgl.sge32[0].phys_addr; + } else { + if (IS_DMA64) + buf_h = cmd->frame->pthru.sgl.sge64[0].phys_addr; + else + buf_h = cmd->frame->pthru.sgl.sge32[0].phys_addr; + } + + pci_unmap_single(instance->pdev, buf_h, cmd->scmd->request_bufflen, + cmd->scmd->sc_data_direction); + return; +} + +/** + * megasas_complete_cmd - Completes a command + * @instance: Adapter soft state + * @cmd: Command to be completed + * @alt_status: If non-zero, use this value as status to + * SCSI mid-layer instead of the value returned + * by the FW. This should be used if caller wants + * an alternate status (as in the case of aborted + * commands) + */ +static inline void +megasas_complete_cmd(struct megasas_instance *instance, struct megasas_cmd *cmd, + u8 alt_status) +{ + int exception = 0; + struct megasas_header *hdr = &cmd->frame->hdr; + unsigned long flags; + + if (cmd->scmd) { + cmd->scmd->SCp.ptr = (char *)0; + } + + switch (hdr->cmd) { + + case MFI_CMD_PD_SCSI_IO: + case MFI_CMD_LD_SCSI_IO: + + /* + * MFI_CMD_PD_SCSI_IO and MFI_CMD_LD_SCSI_IO could have been + * issued either through an IO path or an IOCTL path. If it + * was via IOCTL, we will send it to internal completion. + */ + if (cmd->sync_cmd) { + cmd->sync_cmd = 0; + megasas_complete_int_cmd(instance, cmd); + break; + } + + /* + * Don't export physical disk devices to mid-layer. + */ + if (!MEGASAS_IS_LOGICAL(cmd->scmd) && + (hdr->cmd_status == MFI_STAT_OK) && + (cmd->scmd->cmnd[0] == INQUIRY)) { + + if (((*(u8 *) cmd->scmd->request_buffer) & 0x1F) == + TYPE_DISK) { + cmd->scmd->result = DID_BAD_TARGET << 16; + exception = 1; + } + } + + case MFI_CMD_LD_READ: + case MFI_CMD_LD_WRITE: + + if (alt_status) { + cmd->scmd->result = alt_status << 16; + exception = 1; + } + + if (exception) { + + spin_lock_irqsave(&instance->instance_lock, flags); + instance->fw_outstanding--; + spin_unlock_irqrestore(&instance->instance_lock, flags); + + megasas_unmap_sgbuf(instance, cmd); + cmd->scmd->scsi_done(cmd->scmd); + megasas_return_cmd(instance, cmd); + + break; + } + + switch (hdr->cmd_status) { + + case MFI_STAT_OK: + cmd->scmd->result = DID_OK << 16; + break; + + case MFI_STAT_SCSI_IO_FAILED: + case MFI_STAT_LD_INIT_IN_PROGRESS: + cmd->scmd->result = + (DID_ERROR << 16) | hdr->scsi_status; + break; + + case MFI_STAT_SCSI_DONE_WITH_ERROR: + + cmd->scmd->result = (DID_OK << 16) | hdr->scsi_status; + + if (hdr->scsi_status == SAM_STAT_CHECK_CONDITION) { + memset(cmd->scmd->sense_buffer, 0, + SCSI_SENSE_BUFFERSIZE); + memcpy(cmd->scmd->sense_buffer, cmd->sense, + hdr->sense_len); + + cmd->scmd->result |= DRIVER_SENSE << 24; + } + + break; + + case MFI_STAT_LD_OFFLINE: + case MFI_STAT_DEVICE_NOT_FOUND: + cmd->scmd->result = DID_BAD_TARGET << 16; + break; + + default: + printk(KERN_DEBUG "megasas: MFI FW status %#x\n", + hdr->cmd_status); + cmd->scmd->result = DID_ERROR << 16; + break; + } + + spin_lock_irqsave(&instance->instance_lock, flags); + instance->fw_outstanding--; + spin_unlock_irqrestore(&instance->instance_lock, flags); + + megasas_unmap_sgbuf(instance, cmd); + cmd->scmd->scsi_done(cmd->scmd); + megasas_return_cmd(instance, cmd); + + break; + + case MFI_CMD_SMP: + case MFI_CMD_STP: + case MFI_CMD_DCMD: + + /* + * See if got an event notification + */ + if (cmd->frame->dcmd.opcode == MR_DCMD_CTRL_EVENT_WAIT) + megasas_service_aen(instance, cmd); + else + megasas_complete_int_cmd(instance, cmd); + + break; + + case MFI_CMD_ABORT: + /* + * Cmd issued to abort another cmd returned + */ + megasas_complete_abort(instance, cmd); + break; + + default: + printk("megasas: Unknown command completed! [0x%X]\n", + hdr->cmd); + break; + } +} + +/** + * megasas_deplete_reply_queue - Processes all completed commands + * @instance: Adapter soft state + * @alt_status: Alternate status to be returned to + * SCSI mid-layer instead of the status + * returned by the FW + */ +static inline int +megasas_deplete_reply_queue(struct megasas_instance *instance, u8 alt_status) +{ + u32 status; + u32 producer; + u32 consumer; + u32 context; + struct megasas_cmd *cmd; + + /* + * Check if it is our interrupt + */ + status = readl(&instance->reg_set->outbound_intr_status); + + if (!(status & MFI_OB_INTR_STATUS_MASK)) { + return IRQ_NONE; + } + + /* + * Clear the interrupt by writing back the same value + */ + writel(status, &instance->reg_set->outbound_intr_status); + + producer = *instance->producer; + consumer = *instance->consumer; + + while (consumer != producer) { + context = instance->reply_queue[consumer]; + + cmd = instance->cmd_list[context]; + + megasas_complete_cmd(instance, cmd, alt_status); + + consumer++; + if (consumer == (instance->max_fw_cmds + 1)) { + consumer = 0; + } + } + + *instance->consumer = producer; + + return IRQ_HANDLED; +} + +/** + * megasas_isr - isr entry point + */ +static irqreturn_t megasas_isr(int irq, void *devp, struct pt_regs *regs) +{ + return megasas_deplete_reply_queue((struct megasas_instance *)devp, + DID_OK); +} + +/** + * megasas_transition_to_ready - Move the FW to READY state + * @reg_set: MFI register set + * + * During the initialization, FW passes can potentially be in any one of + * several possible states. If the FW in operational, waiting-for-handshake + * states, driver must take steps to bring it to ready state. Otherwise, it + * has to wait for the ready state. + */ +static int +megasas_transition_to_ready(struct megasas_register_set __iomem * reg_set) +{ + int i; + u8 max_wait; + u32 fw_state; + u32 cur_state; + + fw_state = readl(®_set->outbound_msg_0) & MFI_STATE_MASK; + + while (fw_state != MFI_STATE_READY) { + + printk(KERN_INFO "megasas: Waiting for FW to come to ready" + " state\n"); + switch (fw_state) { + + case MFI_STATE_FAULT: + + printk(KERN_DEBUG "megasas: FW in FAULT state!!\n"); + return -ENODEV; + + case MFI_STATE_WAIT_HANDSHAKE: + /* + * Set the CLR bit in inbound doorbell + */ + writel(MFI_INIT_CLEAR_HANDSHAKE, + ®_set->inbound_doorbell); + + max_wait = 2; + cur_state = MFI_STATE_WAIT_HANDSHAKE; + break; + + case MFI_STATE_OPERATIONAL: + /* + * Bring it to READY state; assuming max wait 2 secs + */ + megasas_disable_intr(reg_set); + writel(MFI_INIT_READY, ®_set->inbound_doorbell); + + max_wait = 10; + cur_state = MFI_STATE_OPERATIONAL; + break; + + case MFI_STATE_UNDEFINED: + /* + * This state should not last for more than 2 seconds + */ + max_wait = 2; + cur_state = MFI_STATE_UNDEFINED; + break; + + case MFI_STATE_BB_INIT: + max_wait = 2; + cur_state = MFI_STATE_BB_INIT; + break; + + case MFI_STATE_FW_INIT: + max_wait = 20; + cur_state = MFI_STATE_FW_INIT; + break; + + case MFI_STATE_FW_INIT_2: + max_wait = 20; + cur_state = MFI_STATE_FW_INIT_2; + break; + + case MFI_STATE_DEVICE_SCAN: + max_wait = 20; + cur_state = MFI_STATE_DEVICE_SCAN; + break; + + case MFI_STATE_FLUSH_CACHE: + max_wait = 20; + cur_state = MFI_STATE_FLUSH_CACHE; + break; + + default: + printk(KERN_DEBUG "megasas: Unknown state 0x%x\n", + fw_state); + return -ENODEV; + } + + /* + * The cur_state should not last for more than max_wait secs + */ + for (i = 0; i < (max_wait * 1000); i++) { + fw_state = MFI_STATE_MASK & + readl(®_set->outbound_msg_0); + + if (fw_state == cur_state) { + msleep(1); + } else + break; + } + + /* + * Return error if fw_state hasn't changed after max_wait + */ + if (fw_state == cur_state) { + printk(KERN_DEBUG "FW state [%d] hasn't changed " + "in %d secs\n", fw_state, max_wait); + return -ENODEV; + } + }; + + return 0; +} + +/** + * megasas_teardown_frame_pool - Destroy the cmd frame DMA pool + * @instance: Adapter soft state + */ +static void megasas_teardown_frame_pool(struct megasas_instance *instance) +{ + int i; + u32 max_cmd = instance->max_fw_cmds; + struct megasas_cmd *cmd; + + if (!instance->frame_dma_pool) + return; + + /* + * Return all frames to pool + */ + for (i = 0; i < max_cmd; i++) { + + cmd = instance->cmd_list[i]; + + if (cmd->frame) + pci_pool_free(instance->frame_dma_pool, cmd->frame, + cmd->frame_phys_addr); + + if (cmd->sense) + pci_pool_free(instance->sense_dma_pool, cmd->frame, + cmd->sense_phys_addr); + } + + /* + * Now destroy the pool itself + */ + pci_pool_destroy(instance->frame_dma_pool); + pci_pool_destroy(instance->sense_dma_pool); + + instance->frame_dma_pool = NULL; + instance->sense_dma_pool = NULL; +} + +/** + * megasas_create_frame_pool - Creates DMA pool for cmd frames + * @instance: Adapter soft state + * + * Each command packet has an embedded DMA memory buffer that is used for + * filling MFI frame and the SG list that immediately follows the frame. This + * function creates those DMA memory buffers for each command packet by using + * PCI pool facility. + */ +static int megasas_create_frame_pool(struct megasas_instance *instance) +{ + int i; + u32 max_cmd; + u32 sge_sz; + u32 sgl_sz; + u32 total_sz; + u32 frame_count; + struct megasas_cmd *cmd; + + max_cmd = instance->max_fw_cmds; + + /* + * Size of our frame is 64 bytes for MFI frame, followed by max SG + * elements and finally SCSI_SENSE_BUFFERSIZE bytes for sense buffer + */ + sge_sz = (IS_DMA64) ? sizeof(struct megasas_sge64) : + sizeof(struct megasas_sge32); + + /* + * Calculated the number of 64byte frames required for SGL + */ + sgl_sz = sge_sz * instance->max_num_sge; + frame_count = (sgl_sz + MEGAMFI_FRAME_SIZE - 1) / MEGAMFI_FRAME_SIZE; + + /* + * We need one extra frame for the MFI command + */ + frame_count++; + + total_sz = MEGAMFI_FRAME_SIZE * frame_count; + /* + * Use DMA pool facility provided by PCI layer + */ + instance->frame_dma_pool = pci_pool_create("megasas frame pool", + instance->pdev, total_sz, 64, + 0); + + if (!instance->frame_dma_pool) { + printk(KERN_DEBUG "megasas: failed to setup frame pool\n"); + return -ENOMEM; + } + + instance->sense_dma_pool = pci_pool_create("megasas sense pool", + instance->pdev, 128, 4, 0); + + if (!instance->sense_dma_pool) { + printk(KERN_DEBUG "megasas: failed to setup sense pool\n"); + + pci_pool_destroy(instance->frame_dma_pool); + instance->frame_dma_pool = NULL; + + return -ENOMEM; + } + + /* + * Allocate and attach a frame to each of the commands in cmd_list. + * By making cmd->index as the context instead of the &cmd, we can + * always use 32bit context regardless of the architecture + */ + for (i = 0; i < max_cmd; i++) { + + cmd = instance->cmd_list[i]; + + cmd->frame = pci_pool_alloc(instance->frame_dma_pool, + GFP_KERNEL, &cmd->frame_phys_addr); + + cmd->sense = pci_pool_alloc(instance->sense_dma_pool, + GFP_KERNEL, &cmd->sense_phys_addr); + + /* + * megasas_teardown_frame_pool() takes care of freeing + * whatever has been allocated + */ + if (!cmd->frame || !cmd->sense) { + printk(KERN_DEBUG "megasas: pci_pool_alloc failed \n"); + megasas_teardown_frame_pool(instance); + return -ENOMEM; + } + + cmd->frame->io.context = cmd->index; + } + + return 0; +} + +/** + * megasas_free_cmds - Free all the cmds in the free cmd pool + * @instance: Adapter soft state + */ +static void megasas_free_cmds(struct megasas_instance *instance) +{ + int i; + /* First free the MFI frame pool */ + megasas_teardown_frame_pool(instance); + + /* Free all the commands in the cmd_list */ + for (i = 0; i < instance->max_fw_cmds; i++) + kfree(instance->cmd_list[i]); + + /* Free the cmd_list buffer itself */ + kfree(instance->cmd_list); + instance->cmd_list = NULL; + + INIT_LIST_HEAD(&instance->cmd_pool); +} + +/** + * megasas_alloc_cmds - Allocates the command packets + * @instance: Adapter soft state + * + * Each command that is issued to the FW, whether IO commands from the OS or + * internal commands like IOCTLs, are wrapped in local data structure called + * megasas_cmd. The frame embedded in this megasas_cmd is actually issued to + * the FW. + * + * Each frame has a 32-bit field called context (tag). This context is used + * to get back the megasas_cmd from the frame when a frame gets completed in + * the ISR. Typically the address of the megasas_cmd itself would be used as + * the context. But we wanted to keep the differences between 32 and 64 bit + * systems to the mininum. We always use 32 bit integers for the context. In + * this driver, the 32 bit values are the indices into an array cmd_list. + * This array is used only to look up the megasas_cmd given the context. The + * free commands themselves are maintained in a linked list called cmd_pool. + */ +static int megasas_alloc_cmds(struct megasas_instance *instance) +{ + int i; + int j; + u32 max_cmd; + struct megasas_cmd *cmd; + + max_cmd = instance->max_fw_cmds; + + /* + * instance->cmd_list is an array of struct megasas_cmd pointers. + * Allocate the dynamic array first and then allocate individual + * commands. + */ + instance->cmd_list = kmalloc(sizeof(struct megasas_cmd *) * max_cmd, + GFP_KERNEL); + + if (!instance->cmd_list) { + printk(KERN_DEBUG "megasas: out of memory\n"); + return -ENOMEM; + } + + memset(instance->cmd_list, 0, sizeof(struct megasas_cmd *) * max_cmd); + + for (i = 0; i < max_cmd; i++) { + instance->cmd_list[i] = kmalloc(sizeof(struct megasas_cmd), + GFP_KERNEL); + + if (!instance->cmd_list[i]) { + + for (j = 0; j < i; j++) + kfree(instance->cmd_list[j]); + + kfree(instance->cmd_list); + instance->cmd_list = NULL; + + return -ENOMEM; + } + } + + /* + * Add all the commands to command pool (instance->cmd_pool) + */ + for (i = 0; i < max_cmd; i++) { + cmd = instance->cmd_list[i]; + memset(cmd, 0, sizeof(struct megasas_cmd)); + cmd->index = i; + cmd->instance = instance; + + list_add_tail(&cmd->list, &instance->cmd_pool); + } + + /* + * Create a frame pool and assign one frame to each cmd + */ + if (megasas_create_frame_pool(instance)) { + printk(KERN_DEBUG "megasas: Error creating frame DMA pool\n"); + megasas_free_cmds(instance); + } + + return 0; +} + +/** + * megasas_get_controller_info - Returns FW's controller structure + * @instance: Adapter soft state + * @ctrl_info: Controller information structure + * + * Issues an internal command (DCMD) to get the FW's controller structure. + * This information is mainly used to find out the maximum IO transfer per + * command supported by the FW. + */ +static int +megasas_get_ctrl_info(struct megasas_instance *instance, + struct megasas_ctrl_info *ctrl_info) +{ + int ret = 0; + struct megasas_cmd *cmd; + struct megasas_dcmd_frame *dcmd; + struct megasas_ctrl_info *ci; + dma_addr_t ci_h = 0; + + cmd = megasas_get_cmd(instance); + + if (!cmd) { + printk(KERN_DEBUG "megasas: Failed to get a free cmd\n"); + return -ENOMEM; + } + + dcmd = &cmd->frame->dcmd; + + ci = pci_alloc_consistent(instance->pdev, + sizeof(struct megasas_ctrl_info), &ci_h); + + if (!ci) { + printk(KERN_DEBUG "Failed to alloc mem for ctrl info\n"); + megasas_return_cmd(instance, cmd); + return -ENOMEM; + } + + memset(ci, 0, sizeof(*ci)); + memset(dcmd->mbox.b, 0, MFI_MBOX_SIZE); + + dcmd->cmd = MFI_CMD_DCMD; + dcmd->cmd_status = 0xFF; + dcmd->sge_count = 1; + dcmd->flags = MFI_FRAME_DIR_READ; + dcmd->timeout = 0; + dcmd->data_xfer_len = sizeof(struct megasas_ctrl_info); + dcmd->opcode = MR_DCMD_CTRL_GET_INFO; + dcmd->sgl.sge32[0].phys_addr = ci_h; + dcmd->sgl.sge32[0].length = sizeof(struct megasas_ctrl_info); + + if (!megasas_issue_polled(instance, cmd)) { + ret = 0; + memcpy(ctrl_info, ci, sizeof(struct megasas_ctrl_info)); + } else { + ret = -1; + } + + pci_free_consistent(instance->pdev, sizeof(struct megasas_ctrl_info), + ci, ci_h); + + megasas_return_cmd(instance, cmd); + return ret; +} + +/** + * megasas_init_mfi - Initializes the FW + * @instance: Adapter soft state + * + * This is the main function for initializing MFI firmware. + */ +static int megasas_init_mfi(struct megasas_instance *instance) +{ + u32 context_sz; + u32 reply_q_sz; + u32 max_sectors_1; + u32 max_sectors_2; + struct megasas_register_set __iomem *reg_set; + + struct megasas_cmd *cmd; + struct megasas_ctrl_info *ctrl_info; + + struct megasas_init_frame *init_frame; + struct megasas_init_queue_info *initq_info; + dma_addr_t init_frame_h; + dma_addr_t initq_info_h; + + /* + * Map the message registers + */ + instance->base_addr = pci_resource_start(instance->pdev, 0); + + if (pci_request_regions(instance->pdev, "megasas: LSI Logic")) { + printk(KERN_DEBUG "megasas: IO memory region busy!\n"); + return -EBUSY; + } + + instance->reg_set = ioremap_nocache(instance->base_addr, 8192); + + if (!instance->reg_set) { + printk(KERN_DEBUG "megasas: Failed to map IO mem\n"); + goto fail_ioremap; + } + + reg_set = instance->reg_set; + + /* + * We expect the FW state to be READY + */ + if (megasas_transition_to_ready(instance->reg_set)) + goto fail_ready_state; + + /* + * Get various operational parameters from status register + */ + instance->max_fw_cmds = readl(®_set->outbound_msg_0) & 0x00FFFF; + instance->max_num_sge = (readl(®_set->outbound_msg_0) & 0xFF0000) >> + 0x10; + /* + * Create a pool of commands + */ + if (megasas_alloc_cmds(instance)) + goto fail_alloc_cmds; + + /* + * Allocate memory for reply queue. Length of reply queue should + * be _one_ more than the maximum commands handled by the firmware. + * + * Note: When FW completes commands, it places corresponding contex + * values in this circular reply queue. This circular queue is a fairly + * typical producer-consumer queue. FW is the producer (of completed + * commands) and the driver is the consumer. + */ + context_sz = sizeof(u32); + reply_q_sz = context_sz * (instance->max_fw_cmds + 1); + + instance->reply_queue = pci_alloc_consistent(instance->pdev, + reply_q_sz, + &instance->reply_queue_h); + + if (!instance->reply_queue) { + printk(KERN_DEBUG "megasas: Out of DMA mem for reply queue\n"); + goto fail_reply_queue; + } + + /* + * Prepare a init frame. Note the init frame points to queue info + * structure. Each frame has SGL allocated after first 64 bytes. For + * this frame - since we don't need any SGL - we use SGL's space as + * queue info structure + * + * We will not get a NULL command below. We just created the pool. + */ + cmd = megasas_get_cmd(instance); + + init_frame = (struct megasas_init_frame *)cmd->frame; + initq_info = (struct megasas_init_queue_info *) + ((unsigned long)init_frame + 64); + + init_frame_h = cmd->frame_phys_addr; + initq_info_h = init_frame_h + 64; + + memset(init_frame, 0, MEGAMFI_FRAME_SIZE); + memset(initq_info, 0, sizeof(struct megasas_init_queue_info)); + + initq_info->reply_queue_entries = instance->max_fw_cmds + 1; + initq_info->reply_queue_start_phys_addr_lo = instance->reply_queue_h; + + initq_info->producer_index_phys_addr_lo = instance->producer_h; + initq_info->consumer_index_phys_addr_lo = instance->consumer_h; + + init_frame->cmd = MFI_CMD_INIT; + init_frame->cmd_status = 0xFF; + init_frame->queue_info_new_phys_addr_lo = initq_info_h; + + init_frame->data_xfer_len = sizeof(struct megasas_init_queue_info); + + /* + * Issue the init frame in polled mode + */ + if (megasas_issue_polled(instance, cmd)) { + printk(KERN_DEBUG "megasas: Failed to init firmware\n"); + goto fail_fw_init; + } + + megasas_return_cmd(instance, cmd); + + ctrl_info = kmalloc(sizeof(struct megasas_ctrl_info), GFP_KERNEL); + + /* + * Compute the max allowed sectors per IO: The controller info has two + * limits on max sectors. Driver should use the minimum of these two. + * + * 1 << stripe_sz_ops.min = max sectors per strip + * + * Note that older firmwares ( < FW ver 30) didn't report information + * to calculate max_sectors_1. So the number ended up as zero always. + */ + if (ctrl_info && !megasas_get_ctrl_info(instance, ctrl_info)) { + + max_sectors_1 = (1 << ctrl_info->stripe_sz_ops.min) * + ctrl_info->max_strips_per_io; + max_sectors_2 = ctrl_info->max_request_size; + + instance->max_sectors_per_req = (max_sectors_1 < max_sectors_2) + ? max_sectors_1 : max_sectors_2; + } else + instance->max_sectors_per_req = instance->max_num_sge * + PAGE_SIZE / 512; + + kfree(ctrl_info); + + return 0; + + fail_fw_init: + megasas_return_cmd(instance, cmd); + + pci_free_consistent(instance->pdev, reply_q_sz, + instance->reply_queue, instance->reply_queue_h); + fail_reply_queue: + megasas_free_cmds(instance); + + fail_alloc_cmds: + fail_ready_state: + iounmap(instance->reg_set); + + fail_ioremap: + pci_release_regions(instance->pdev); + + return -EINVAL; +} + +/** + * megasas_release_mfi - Reverses the FW initialization + * @intance: Adapter soft state + */ +static void megasas_release_mfi(struct megasas_instance *instance) +{ + u32 reply_q_sz = sizeof(u32) * (instance->max_fw_cmds + 1); + + pci_free_consistent(instance->pdev, reply_q_sz, + instance->reply_queue, instance->reply_queue_h); + + megasas_free_cmds(instance); + + iounmap(instance->reg_set); + + pci_release_regions(instance->pdev); +} + +/** + * megasas_get_seq_num - Gets latest event sequence numbers + * @instance: Adapter soft state + * @eli: FW event log sequence numbers information + * + * FW maintains a log of all events in a non-volatile area. Upper layers would + * usually find out the latest sequence number of the events, the seq number at + * the boot etc. They would "read" all the events below the latest seq number + * by issuing a direct fw cmd (DCMD). For the future events (beyond latest seq + * number), they would subsribe to AEN (asynchronous event notification) and + * wait for the events to happen. + */ +static int +megasas_get_seq_num(struct megasas_instance *instance, + struct megasas_evt_log_info *eli) +{ + struct megasas_cmd *cmd; + struct megasas_dcmd_frame *dcmd; + struct megasas_evt_log_info *el_info; + dma_addr_t el_info_h = 0; + + cmd = megasas_get_cmd(instance); + + if (!cmd) { + return -ENOMEM; + } + + dcmd = &cmd->frame->dcmd; + el_info = pci_alloc_consistent(instance->pdev, + sizeof(struct megasas_evt_log_info), + &el_info_h); + + if (!el_info) { + megasas_return_cmd(instance, cmd); + return -ENOMEM; + } + + memset(el_info, 0, sizeof(*el_info)); + memset(dcmd->mbox.b, 0, MFI_MBOX_SIZE); + + dcmd->cmd = MFI_CMD_DCMD; + dcmd->cmd_status = 0x0; + dcmd->sge_count = 1; + dcmd->flags = MFI_FRAME_DIR_READ; + dcmd->timeout = 0; + dcmd->data_xfer_len = sizeof(struct megasas_evt_log_info); + dcmd->opcode = MR_DCMD_CTRL_EVENT_GET_INFO; + dcmd->sgl.sge32[0].phys_addr = el_info_h; + dcmd->sgl.sge32[0].length = sizeof(struct megasas_evt_log_info); + + megasas_issue_blocked_cmd(instance, cmd); + + /* + * Copy the data back into callers buffer + */ + memcpy(eli, el_info, sizeof(struct megasas_evt_log_info)); + + pci_free_consistent(instance->pdev, sizeof(struct megasas_evt_log_info), + el_info, el_info_h); + + megasas_return_cmd(instance, cmd); + + return 0; +} + +/** + * megasas_register_aen - Registers for asynchronous event notification + * @instance: Adapter soft state + * @seq_num: The starting sequence number + * @class_locale: Class of the event + * + * This function subscribes for AEN for events beyond the @seq_num. It requests + * to be notified if and only if the event is of type @class_locale + */ +static int +megasas_register_aen(struct megasas_instance *instance, u32 seq_num, + u32 class_locale_word) +{ + int ret_val; + struct megasas_cmd *cmd; + struct megasas_dcmd_frame *dcmd; + union megasas_evt_class_locale curr_aen; + union megasas_evt_class_locale prev_aen; + + /* + * If there an AEN pending already (aen_cmd), check if the + * class_locale of that pending AEN is inclusive of the new + * AEN request we currently have. If it is, then we don't have + * to do anything. In other words, whichever events the current + * AEN request is subscribing to, have already been subscribed + * to. + * + * If the old_cmd is _not_ inclusive, then we have to abort + * that command, form a class_locale that is superset of both + * old and current and re-issue to the FW + */ + + curr_aen.word = class_locale_word; + + if (instance->aen_cmd) { + + prev_aen.word = instance->aen_cmd->frame->dcmd.mbox.w[1]; + + /* + * A class whose enum value is smaller is inclusive of all + * higher values. If a PROGRESS (= -1) was previously + * registered, then a new registration requests for higher + * classes need not be sent to FW. They are automatically + * included. + * + * Locale numbers don't have such hierarchy. They are bitmap + * values + */ + if ((prev_aen.members.class <= curr_aen.members.class) && + !((prev_aen.members.locale & curr_aen.members.locale) ^ + curr_aen.members.locale)) { + /* + * Previously issued event registration includes + * current request. Nothing to do. + */ + return 0; + } else { + curr_aen.members.locale |= prev_aen.members.locale; + + if (prev_aen.members.class < curr_aen.members.class) + curr_aen.members.class = prev_aen.members.class; + + instance->aen_cmd->abort_aen = 1; + ret_val = megasas_issue_blocked_abort_cmd(instance, + instance-> + aen_cmd); + + if (ret_val) { + printk(KERN_DEBUG "megasas: Failed to abort " + "previous AEN command\n"); + return ret_val; + } + } + } + + cmd = megasas_get_cmd(instance); + + if (!cmd) + return -ENOMEM; + + dcmd = &cmd->frame->dcmd; + + memset(instance->evt_detail, 0, sizeof(struct megasas_evt_detail)); + + /* + * Prepare DCMD for aen registration + */ + memset(dcmd->mbox.b, 0, MFI_MBOX_SIZE); + + dcmd->cmd = MFI_CMD_DCMD; + dcmd->cmd_status = 0x0; + dcmd->sge_count = 1; + dcmd->flags = MFI_FRAME_DIR_READ; + dcmd->timeout = 0; + dcmd->data_xfer_len = sizeof(struct megasas_evt_detail); + dcmd->opcode = MR_DCMD_CTRL_EVENT_WAIT; + dcmd->mbox.w[0] = seq_num; + dcmd->mbox.w[1] = curr_aen.word; + dcmd->sgl.sge32[0].phys_addr = (u32) instance->evt_detail_h; + dcmd->sgl.sge32[0].length = sizeof(struct megasas_evt_detail); + + /* + * Store reference to the cmd used to register for AEN. When an + * application wants us to register for AEN, we have to abort this + * cmd and re-register with a new EVENT LOCALE supplied by that app + */ + instance->aen_cmd = cmd; + + /* + * Issue the aen registration frame + */ + writel(cmd->frame_phys_addr >> 3, + &instance->reg_set->inbound_queue_port); + + return 0; +} + +/** + * megasas_start_aen - Subscribes to AEN during driver load time + * @instance: Adapter soft state + */ +static int megasas_start_aen(struct megasas_instance *instance) +{ + struct megasas_evt_log_info eli; + union megasas_evt_class_locale class_locale; + + /* + * Get the latest sequence number from FW + */ + memset(&eli, 0, sizeof(eli)); + + if (megasas_get_seq_num(instance, &eli)) + return -1; + + /* + * Register AEN with FW for latest sequence number plus 1 + */ + class_locale.members.reserved = 0; + class_locale.members.locale = MR_EVT_LOCALE_ALL; + class_locale.members.class = MR_EVT_CLASS_DEBUG; + + return megasas_register_aen(instance, eli.newest_seq_num + 1, + class_locale.word); +} + +/** + * megasas_io_attach - Attaches this driver to SCSI mid-layer + * @instance: Adapter soft state + */ +static int megasas_io_attach(struct megasas_instance *instance) +{ + struct Scsi_Host *host = instance->host; + + /* + * Export parameters required by SCSI mid-layer + */ + host->irq = instance->pdev->irq; + host->unique_id = instance->unique_id; + host->can_queue = instance->max_fw_cmds - MEGASAS_INT_CMDS; + host->this_id = instance->init_id; + host->sg_tablesize = instance->max_num_sge; + host->max_sectors = instance->max_sectors_per_req; + host->cmd_per_lun = 128; + host->max_channel = MEGASAS_MAX_CHANNELS - 1; + host->max_id = MEGASAS_MAX_DEV_PER_CHANNEL; + host->max_lun = MEGASAS_MAX_LUN; + + /* + * Notify the mid-layer about the new controller + */ + if (scsi_add_host(host, &instance->pdev->dev)) { + printk(KERN_DEBUG "megasas: scsi_add_host failed\n"); + return -ENODEV; + } + + /* + * Trigger SCSI to scan our drives + */ + scsi_scan_host(host); + return 0; +} + +/** + * megasas_probe_one - PCI hotplug entry point + * @pdev: PCI device structure + * @id: PCI ids of supported hotplugged adapter + */ +static int __devinit +megasas_probe_one(struct pci_dev *pdev, const struct pci_device_id *id) +{ + int rval; + struct Scsi_Host *host; + struct megasas_instance *instance; + + /* + * Announce PCI information + */ + printk(KERN_INFO "megasas: %#4.04x:%#4.04x:%#4.04x:%#4.04x: ", + pdev->vendor, pdev->device, pdev->subsystem_vendor, + pdev->subsystem_device); + + printk("bus %d:slot %d:func %d\n", + pdev->bus->number, PCI_SLOT(pdev->devfn), PCI_FUNC(pdev->devfn)); + + /* + * PCI prepping: enable device set bus mastering and dma mask + */ + rval = pci_enable_device(pdev); + + if (rval) { + return rval; + } + + pci_set_master(pdev); + + /* + * All our contollers are capable of performing 64-bit DMA + */ + if (IS_DMA64) { + if (pci_set_dma_mask(pdev, DMA_64BIT_MASK) != 0) { + + if (pci_set_dma_mask(pdev, DMA_32BIT_MASK) != 0) + goto fail_set_dma_mask; + } + } else { + if (pci_set_dma_mask(pdev, DMA_32BIT_MASK) != 0) + goto fail_set_dma_mask; + } + + host = scsi_host_alloc(&megasas_template, + sizeof(struct megasas_instance)); + + if (!host) { + printk(KERN_DEBUG "megasas: scsi_host_alloc failed\n"); + goto fail_alloc_instance; + } + + instance = (struct megasas_instance *)host->hostdata; + memset(instance, 0, sizeof(*instance)); + + instance->producer = pci_alloc_consistent(pdev, sizeof(u32), + &instance->producer_h); + instance->consumer = pci_alloc_consistent(pdev, sizeof(u32), + &instance->consumer_h); + + if (!instance->producer || !instance->consumer) { + printk(KERN_DEBUG "megasas: Failed to allocate memory for " + "producer, consumer\n"); + goto fail_alloc_dma_buf; + } + + *instance->producer = 0; + *instance->consumer = 0; + + instance->evt_detail = pci_alloc_consistent(pdev, + sizeof(struct + megasas_evt_detail), + &instance->evt_detail_h); + + if (!instance->evt_detail) { + printk(KERN_DEBUG "megasas: Failed to allocate memory for " + "event detail structure\n"); + goto fail_alloc_dma_buf; + } + + /* + * Initialize locks and queues + */ + INIT_LIST_HEAD(&instance->cmd_pool); + + init_waitqueue_head(&instance->int_cmd_wait_q); + init_waitqueue_head(&instance->abort_cmd_wait_q); + + spin_lock_init(&instance->cmd_pool_lock); + spin_lock_init(&instance->instance_lock); + + sema_init(&instance->aen_mutex, 1); + sema_init(&instance->ioctl_sem, MEGASAS_INT_CMDS); + + /* + * Initialize PCI related and misc parameters + */ + instance->pdev = pdev; + instance->host = host; + instance->unique_id = pdev->bus->number << 8 | pdev->devfn; + instance->init_id = MEGASAS_DEFAULT_INIT_ID; + + /* + * Initialize MFI Firmware + */ + if (megasas_init_mfi(instance)) + goto fail_init_mfi; + + /* + * Register IRQ + */ + if (request_irq(pdev->irq, megasas_isr, SA_SHIRQ, "megasas", instance)) { + printk(KERN_DEBUG "megasas: Failed to register IRQ\n"); + goto fail_irq; + } + + megasas_enable_intr(instance->reg_set); + + /* + * Store instance in PCI softstate + */ + pci_set_drvdata(pdev, instance); + + /* + * Add this controller to megasas_mgmt_info structure so that it + * can be exported to management applications + */ + megasas_mgmt_info.count++; + megasas_mgmt_info.instance[megasas_mgmt_info.max_index] = instance; + megasas_mgmt_info.max_index++; + + /* + * Initiate AEN (Asynchronous Event Notification) + */ + if (megasas_start_aen(instance)) { + printk(KERN_DEBUG "megasas: start aen failed\n"); + goto fail_start_aen; + } + + /* + * Register with SCSI mid-layer + */ + if (megasas_io_attach(instance)) + goto fail_io_attach; + + return 0; + + fail_start_aen: + fail_io_attach: + megasas_mgmt_info.count--; + megasas_mgmt_info.instance[megasas_mgmt_info.max_index] = NULL; + megasas_mgmt_info.max_index--; + + pci_set_drvdata(pdev, NULL); + megasas_disable_intr(instance->reg_set); + free_irq(instance->pdev->irq, instance); + + megasas_release_mfi(instance); + + fail_irq: + fail_init_mfi: + fail_alloc_dma_buf: + if (instance->evt_detail) + pci_free_consistent(pdev, sizeof(struct megasas_evt_detail), + instance->evt_detail, + instance->evt_detail_h); + + if (instance->producer) + pci_free_consistent(pdev, sizeof(u32), instance->producer, + instance->producer_h); + if (instance->consumer) + pci_free_consistent(pdev, sizeof(u32), instance->consumer, + instance->consumer_h); + scsi_host_put(host); + + fail_alloc_instance: + fail_set_dma_mask: + pci_disable_device(pdev); + + return -ENODEV; +} + +/** + * megasas_flush_cache - Requests FW to flush all its caches + * @instance: Adapter soft state + */ +static void megasas_flush_cache(struct megasas_instance *instance) +{ + struct megasas_cmd *cmd; + struct megasas_dcmd_frame *dcmd; + + cmd = megasas_get_cmd(instance); + + if (!cmd) + return; + + dcmd = &cmd->frame->dcmd; + + memset(dcmd->mbox.b, 0, MFI_MBOX_SIZE); + + dcmd->cmd = MFI_CMD_DCMD; + dcmd->cmd_status = 0x0; + dcmd->sge_count = 0; + dcmd->flags = MFI_FRAME_DIR_NONE; + dcmd->timeout = 0; + dcmd->data_xfer_len = 0; + dcmd->opcode = MR_DCMD_CTRL_CACHE_FLUSH; + dcmd->mbox.b[0] = MR_FLUSH_CTRL_CACHE | MR_FLUSH_DISK_CACHE; + + megasas_issue_blocked_cmd(instance, cmd); + + megasas_return_cmd(instance, cmd); + + return; +} + +/** + * megasas_shutdown_controller - Instructs FW to shutdown the controller + * @instance: Adapter soft state + */ +static void megasas_shutdown_controller(struct megasas_instance *instance) +{ + struct megasas_cmd *cmd; + struct megasas_dcmd_frame *dcmd; + + cmd = megasas_get_cmd(instance); + + if (!cmd) + return; + + if (instance->aen_cmd) + megasas_issue_blocked_abort_cmd(instance, instance->aen_cmd); + + dcmd = &cmd->frame->dcmd; + + memset(dcmd->mbox.b, 0, MFI_MBOX_SIZE); + + dcmd->cmd = MFI_CMD_DCMD; + dcmd->cmd_status = 0x0; + dcmd->sge_count = 0; + dcmd->flags = MFI_FRAME_DIR_NONE; + dcmd->timeout = 0; + dcmd->data_xfer_len = 0; + dcmd->opcode = MR_DCMD_CTRL_SHUTDOWN; + + megasas_issue_blocked_cmd(instance, cmd); + + megasas_return_cmd(instance, cmd); + + return; +} + +/** + * megasas_detach_one - PCI hot"un"plug entry point + * @pdev: PCI device structure + */ +static void megasas_detach_one(struct pci_dev *pdev) +{ + int i; + struct Scsi_Host *host; + struct megasas_instance *instance; + + instance = pci_get_drvdata(pdev); + host = instance->host; + + scsi_remove_host(instance->host); + megasas_flush_cache(instance); + megasas_shutdown_controller(instance); + + /* + * Take the instance off the instance array. Note that we will not + * decrement the max_index. We let this array be sparse array + */ + for (i = 0; i < megasas_mgmt_info.max_index; i++) { + if (megasas_mgmt_info.instance[i] == instance) { + megasas_mgmt_info.count--; + megasas_mgmt_info.instance[i] = NULL; + + break; + } + } + + pci_set_drvdata(instance->pdev, NULL); + + megasas_disable_intr(instance->reg_set); + + free_irq(instance->pdev->irq, instance); + + megasas_release_mfi(instance); + + pci_free_consistent(pdev, sizeof(struct megasas_evt_detail), + instance->evt_detail, instance->evt_detail_h); + + pci_free_consistent(pdev, sizeof(u32), instance->producer, + instance->producer_h); + + pci_free_consistent(pdev, sizeof(u32), instance->consumer, + instance->consumer_h); + + scsi_host_put(host); + + pci_set_drvdata(pdev, NULL); + + pci_disable_device(pdev); + + return; +} + +/** + * megasas_shutdown - Shutdown entry point + * @device: Generic device structure + */ +static void megasas_shutdown(struct pci_dev *pdev) +{ + struct megasas_instance *instance = pci_get_drvdata(pdev); + megasas_flush_cache(instance); +} + +/** + * megasas_mgmt_open - char node "open" entry point + */ +static int megasas_mgmt_open(struct inode *inode, struct file *filep) +{ + /* + * Allow only those users with admin rights + */ + if (!capable(CAP_SYS_ADMIN)) + return -EACCES; + + return 0; +} + +/** + * megasas_mgmt_release - char node "release" entry point + */ +static int megasas_mgmt_release(struct inode *inode, struct file *filep) +{ + filep->private_data = NULL; + fasync_helper(-1, filep, 0, &megasas_async_queue); + + return 0; +} + +/** + * megasas_mgmt_fasync - Async notifier registration from applications + * + * This function adds the calling process to a driver global queue. When an + * event occurs, SIGIO will be sent to all processes in this queue. + */ +static int megasas_mgmt_fasync(int fd, struct file *filep, int mode) +{ + int rc; + + down(&megasas_async_queue_mutex); + + rc = fasync_helper(fd, filep, mode, &megasas_async_queue); + + up(&megasas_async_queue_mutex); + + if (rc >= 0) { + /* For sanity check when we get ioctl */ + filep->private_data = filep; + return 0; + } + + printk(KERN_DEBUG "megasas: fasync_helper failed [%d]\n", rc); + + return rc; +} + +/** + * megasas_mgmt_fw_ioctl - Issues management ioctls to FW + * @instance: Adapter soft state + * @argp: User's ioctl packet + */ +static int +megasas_mgmt_fw_ioctl(struct megasas_instance *instance, + struct megasas_iocpacket __user * user_ioc, + struct megasas_iocpacket *ioc) +{ + struct megasas_sge32 *kern_sge32; + struct megasas_cmd *cmd; + void *kbuff_arr[MAX_IOCTL_SGE]; + dma_addr_t buf_handle = 0; + int error = 0, i; + void *sense = NULL; + dma_addr_t sense_handle; + u32 *sense_ptr; + + memset(kbuff_arr, 0, sizeof(kbuff_arr)); + + if (ioc->sge_count > MAX_IOCTL_SGE) { + printk(KERN_DEBUG "megasas: SGE count [%d] > max limit [%d]\n", + ioc->sge_count, MAX_IOCTL_SGE); + return -EINVAL; + } + + cmd = megasas_get_cmd(instance); + if (!cmd) { + printk(KERN_DEBUG "megasas: Failed to get a cmd packet\n"); + return -ENOMEM; + } + + /* + * User's IOCTL packet has 2 frames (maximum). Copy those two + * frames into our cmd's frames. cmd->frame's context will get + * overwritten when we copy from user's frames. So set that value + * alone separately + */ + memcpy(cmd->frame, ioc->frame.raw, 2 * MEGAMFI_FRAME_SIZE); + cmd->frame->hdr.context = cmd->index; + + /* + * The management interface between applications and the fw uses + * MFI frames. E.g, RAID configuration changes, LD property changes + * etc are accomplishes through different kinds of MFI frames. The + * driver needs to care only about substituting user buffers with + * kernel buffers in SGLs. The location of SGL is embedded in the + * struct iocpacket itself. + */ + kern_sge32 = (struct megasas_sge32 *) + ((unsigned long)cmd->frame + ioc->sgl_off); + + /* + * For each user buffer, create a mirror buffer and copy in + */ + for (i = 0; i < ioc->sge_count; i++) { + kbuff_arr[i] = pci_alloc_consistent(instance->pdev, + ioc->sgl[i].iov_len, + &buf_handle); + if (!kbuff_arr[i]) { + printk(KERN_DEBUG "megasas: Failed to alloc " + "kernel SGL buffer for IOCTL \n"); + error = -ENOMEM; + goto out; + } + + /* + * We don't change the dma_coherent_mask, so + * pci_alloc_consistent only returns 32bit addresses + */ + kern_sge32[i].phys_addr = (u32) buf_handle; + kern_sge32[i].length = ioc->sgl[i].iov_len; + + /* + * We created a kernel buffer corresponding to the + * user buffer. Now copy in from the user buffer + */ + if (copy_from_user(kbuff_arr[i], ioc->sgl[i].iov_base, + (u32) (ioc->sgl[i].iov_len))) { + error = -EFAULT; + goto out; + } + } + + if (ioc->sense_len) { + sense = pci_alloc_consistent(instance->pdev, ioc->sense_len, + &sense_handle); + if (!sense) { + error = -ENOMEM; + goto out; + } + + sense_ptr = + (u32 *) ((unsigned long)cmd->frame + ioc->sense_off); + *sense_ptr = sense_handle; + } + + /* + * Set the sync_cmd flag so that the ISR knows not to complete this + * cmd to the SCSI mid-layer + */ + cmd->sync_cmd = 1; + megasas_issue_blocked_cmd(instance, cmd); + cmd->sync_cmd = 0; + + /* + * copy out the kernel buffers to user buffers + */ + for (i = 0; i < ioc->sge_count; i++) { + if (copy_to_user(ioc->sgl[i].iov_base, kbuff_arr[i], + ioc->sgl[i].iov_len)) { + error = -EFAULT; + goto out; + } + } + + /* + * copy out the sense + */ + if (ioc->sense_len) { + /* + * sense_ptr points to the location that has the user + * sense buffer address + */ + sense_ptr = (u32 *) ((unsigned long)ioc->frame.raw + + ioc->sense_off); + + if (copy_to_user((void __user *)((unsigned long)(*sense_ptr)), + sense, ioc->sense_len)) { + error = -EFAULT; + goto out; + } + } + + /* + * copy the status codes returned by the fw + */ + if (copy_to_user(&user_ioc->frame.hdr.cmd_status, + &cmd->frame->hdr.cmd_status, sizeof(u8))) { + printk(KERN_DEBUG "megasas: Error copying out cmd_status\n"); + error = -EFAULT; + } + + out: + if (sense) { + pci_free_consistent(instance->pdev, ioc->sense_len, + sense, sense_handle); + } + + for (i = 0; i < ioc->sge_count && kbuff_arr[i]; i++) { + pci_free_consistent(instance->pdev, + kern_sge32[i].length, + kbuff_arr[i], kern_sge32[i].phys_addr); + } + + megasas_return_cmd(instance, cmd); + return error; +} + +static struct megasas_instance *megasas_lookup_instance(u16 host_no) +{ + int i; + + for (i = 0; i < megasas_mgmt_info.max_index; i++) { + + if ((megasas_mgmt_info.instance[i]) && + (megasas_mgmt_info.instance[i]->host->host_no == host_no)) + return megasas_mgmt_info.instance[i]; + } + + return NULL; +} + +static int megasas_mgmt_ioctl_fw(struct file *file, unsigned long arg) +{ + struct megasas_iocpacket __user *user_ioc = + (struct megasas_iocpacket __user *)arg; + struct megasas_iocpacket *ioc; + struct megasas_instance *instance; + int error; + + ioc = kmalloc(sizeof(*ioc), GFP_KERNEL); + if (!ioc) + return -ENOMEM; + + if (copy_from_user(ioc, user_ioc, sizeof(*ioc))) { + error = -EFAULT; + goto out_kfree_ioc; + } + + instance = megasas_lookup_instance(ioc->host_no); + if (!instance) { + error = -ENODEV; + goto out_kfree_ioc; + } + + /* + * We will allow only MEGASAS_INT_CMDS number of parallel ioctl cmds + */ + if (down_interruptible(&instance->ioctl_sem)) { + error = -ERESTARTSYS; + goto out_kfree_ioc; + } + error = megasas_mgmt_fw_ioctl(instance, user_ioc, ioc); + up(&instance->ioctl_sem); + + out_kfree_ioc: + kfree(ioc); + return error; +} + +static int megasas_mgmt_ioctl_aen(struct file *file, unsigned long arg) +{ + struct megasas_instance *instance; + struct megasas_aen aen; + int error; + + if (file->private_data != file) { + printk(KERN_DEBUG "megasas: fasync_helper was not " + "called first\n"); + return -EINVAL; + } + + if (copy_from_user(&aen, (void __user *)arg, sizeof(aen))) + return -EFAULT; + + instance = megasas_lookup_instance(aen.host_no); + + if (!instance) + return -ENODEV; + + down(&instance->aen_mutex); + error = megasas_register_aen(instance, aen.seq_num, + aen.class_locale_word); + up(&instance->aen_mutex); + return error; +} + +/** + * megasas_mgmt_ioctl - char node ioctl entry point + */ +static long +megasas_mgmt_ioctl(struct file *file, unsigned int cmd, unsigned long arg) +{ + switch (cmd) { + case MEGASAS_IOC_FIRMWARE: + return megasas_mgmt_ioctl_fw(file, arg); + + case MEGASAS_IOC_GET_AEN: + return megasas_mgmt_ioctl_aen(file, arg); + } + + return -ENOTTY; +} + +#ifdef CONFIG_COMPAT +static int megasas_mgmt_compat_ioctl_fw(struct file *file, unsigned long arg) +{ + struct compat_megasas_iocpacket __user *cioc = + (struct compat_megasas_iocpacket __user *)arg; + struct megasas_iocpacket __user *ioc = + compat_alloc_user_space(sizeof(struct megasas_iocpacket)); + int i; + int error = 0; + + clear_user(ioc, sizeof(*ioc)); + + if (copy_in_user(&ioc->host_no, &cioc->host_no, sizeof(u16)) || + copy_in_user(&ioc->sgl_off, &cioc->sgl_off, sizeof(u32)) || + copy_in_user(&ioc->sense_off, &cioc->sense_off, sizeof(u32)) || + copy_in_user(&ioc->sense_len, &cioc->sense_len, sizeof(u32)) || + copy_in_user(ioc->frame.raw, cioc->frame.raw, 128) || + copy_in_user(&ioc->sge_count, &cioc->sge_count, sizeof(u32))) + return -EFAULT; + + for (i = 0; i < MAX_IOCTL_SGE; i++) { + compat_uptr_t ptr; + + if (get_user(ptr, &cioc->sgl[i].iov_base) || + put_user(compat_ptr(ptr), &ioc->sgl[i].iov_base) || + copy_in_user(&ioc->sgl[i].iov_len, + &cioc->sgl[i].iov_len, sizeof(compat_size_t))) + return -EFAULT; + } + + error = megasas_mgmt_ioctl_fw(file, (unsigned long)ioc); + + if (copy_in_user(&cioc->frame.hdr.cmd_status, + &ioc->frame.hdr.cmd_status, sizeof(u8))) { + printk(KERN_DEBUG "megasas: error copy_in_user cmd_status\n"); + return -EFAULT; + } + return error; +} + +static long +megasas_mgmt_compat_ioctl(struct file *file, unsigned int cmd, + unsigned long arg) +{ + switch (cmd) { + case MEGASAS_IOC_FIRMWARE:{ + return megasas_mgmt_compat_ioctl_fw(file, arg); + } + case MEGASAS_IOC_GET_AEN: + return megasas_mgmt_ioctl_aen(file, arg); + } + + return -ENOTTY; +} +#endif + +/* + * File operations structure for management interface + */ +static struct file_operations megasas_mgmt_fops = { + .owner = THIS_MODULE, + .open = megasas_mgmt_open, + .release = megasas_mgmt_release, + .fasync = megasas_mgmt_fasync, + .unlocked_ioctl = megasas_mgmt_ioctl, +#ifdef CONFIG_COMPAT + .compat_ioctl = megasas_mgmt_compat_ioctl, +#endif +}; + +/* + * PCI hotplug support registration structure + */ +static struct pci_driver megasas_pci_driver = { + + .name = "megaraid_sas", + .id_table = megasas_pci_table, + .probe = megasas_probe_one, + .remove = __devexit_p(megasas_detach_one), + .shutdown = megasas_shutdown, +}; + +/* + * Sysfs driver attributes + */ +static ssize_t megasas_sysfs_show_version(struct device_driver *dd, char *buf) +{ + return snprintf(buf, strlen(MEGASAS_VERSION) + 2, "%s\n", + MEGASAS_VERSION); +} + +static DRIVER_ATTR(version, S_IRUGO, megasas_sysfs_show_version, NULL); + +static ssize_t +megasas_sysfs_show_release_date(struct device_driver *dd, char *buf) +{ + return snprintf(buf, strlen(MEGASAS_RELDATE) + 2, "%s\n", + MEGASAS_RELDATE); +} + +static DRIVER_ATTR(release_date, S_IRUGO, megasas_sysfs_show_release_date, + NULL); + +/** + * megasas_init - Driver load entry point + */ +static int __init megasas_init(void) +{ + int rval; + + /* + * Announce driver version and other information + */ + printk(KERN_INFO "megasas: %s %s\n", MEGASAS_VERSION, + MEGASAS_EXT_VERSION); + + memset(&megasas_mgmt_info, 0, sizeof(megasas_mgmt_info)); + + /* + * Register character device node + */ + rval = register_chrdev(0, "megaraid_sas_ioctl", &megasas_mgmt_fops); + + if (rval < 0) { + printk(KERN_DEBUG "megasas: failed to open device node\n"); + return rval; + } + + megasas_mgmt_majorno = rval; + + /* + * Register ourselves as PCI hotplug module + */ + rval = pci_module_init(&megasas_pci_driver); + + if (rval) { + printk(KERN_DEBUG "megasas: PCI hotplug regisration failed \n"); + unregister_chrdev(megasas_mgmt_majorno, "megaraid_sas_ioctl"); + } + + driver_create_file(&megasas_pci_driver.driver, &driver_attr_version); + driver_create_file(&megasas_pci_driver.driver, + &driver_attr_release_date); + + return rval; +} + +/** + * megasas_exit - Driver unload entry point + */ +static void __exit megasas_exit(void) +{ + driver_remove_file(&megasas_pci_driver.driver, &driver_attr_version); + driver_remove_file(&megasas_pci_driver.driver, + &driver_attr_release_date); + + pci_unregister_driver(&megasas_pci_driver); + unregister_chrdev(megasas_mgmt_majorno, "megaraid_sas_ioctl"); +} + +module_init(megasas_init); +module_exit(megasas_exit); diff --git a/drivers/scsi/megaraid/megaraid_sas.h b/drivers/scsi/megaraid/megaraid_sas.h new file mode 100644 index 00000000000..eaec9d53142 --- /dev/null +++ b/drivers/scsi/megaraid/megaraid_sas.h @@ -0,0 +1,1142 @@ +/* + * + * Linux MegaRAID driver for SAS based RAID controllers + * + * Copyright (c) 2003-2005 LSI Logic Corporation. + * + * 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. + * + * FILE : megaraid_sas.h + */ + +#ifndef LSI_MEGARAID_SAS_H +#define LSI_MEGARAID_SAS_H + +/** + * MegaRAID SAS Driver meta data + */ +#define MEGASAS_VERSION "00.00.02.00-rc4" +#define MEGASAS_RELDATE "Sep 16, 2005" +#define MEGASAS_EXT_VERSION "Fri Sep 16 12:37:08 EDT 2005" + +/* + * ===================================== + * MegaRAID SAS MFI firmware definitions + * ===================================== + */ + +/* + * MFI stands for MegaRAID SAS FW Interface. This is just a moniker for + * protocol between the software and firmware. Commands are issued using + * "message frames" + */ + +/** + * FW posts its state in upper 4 bits of outbound_msg_0 register + */ +#define MFI_STATE_MASK 0xF0000000 +#define MFI_STATE_UNDEFINED 0x00000000 +#define MFI_STATE_BB_INIT 0x10000000 +#define MFI_STATE_FW_INIT 0x40000000 +#define MFI_STATE_WAIT_HANDSHAKE 0x60000000 +#define MFI_STATE_FW_INIT_2 0x70000000 +#define MFI_STATE_DEVICE_SCAN 0x80000000 +#define MFI_STATE_FLUSH_CACHE 0xA0000000 +#define MFI_STATE_READY 0xB0000000 +#define MFI_STATE_OPERATIONAL 0xC0000000 +#define MFI_STATE_FAULT 0xF0000000 + +#define MEGAMFI_FRAME_SIZE 64 + +/** + * During FW init, clear pending cmds & reset state using inbound_msg_0 + * + * ABORT : Abort all pending cmds + * READY : Move from OPERATIONAL to READY state; discard queue info + * MFIMODE : Discard (possible) low MFA posted in 64-bit mode (??) + * CLR_HANDSHAKE: FW is waiting for HANDSHAKE from BIOS or Driver + */ +#define MFI_INIT_ABORT 0x00000000 +#define MFI_INIT_READY 0x00000002 +#define MFI_INIT_MFIMODE 0x00000004 +#define MFI_INIT_CLEAR_HANDSHAKE 0x00000008 +#define MFI_RESET_FLAGS MFI_INIT_READY|MFI_INIT_MFIMODE + +/** + * MFI frame flags + */ +#define MFI_FRAME_POST_IN_REPLY_QUEUE 0x0000 +#define MFI_FRAME_DONT_POST_IN_REPLY_QUEUE 0x0001 +#define MFI_FRAME_SGL32 0x0000 +#define MFI_FRAME_SGL64 0x0002 +#define MFI_FRAME_SENSE32 0x0000 +#define MFI_FRAME_SENSE64 0x0004 +#define MFI_FRAME_DIR_NONE 0x0000 +#define MFI_FRAME_DIR_WRITE 0x0008 +#define MFI_FRAME_DIR_READ 0x0010 +#define MFI_FRAME_DIR_BOTH 0x0018 + +/** + * Definition for cmd_status + */ +#define MFI_CMD_STATUS_POLL_MODE 0xFF + +/** + * MFI command opcodes + */ +#define MFI_CMD_INIT 0x00 +#define MFI_CMD_LD_READ 0x01 +#define MFI_CMD_LD_WRITE 0x02 +#define MFI_CMD_LD_SCSI_IO 0x03 +#define MFI_CMD_PD_SCSI_IO 0x04 +#define MFI_CMD_DCMD 0x05 +#define MFI_CMD_ABORT 0x06 +#define MFI_CMD_SMP 0x07 +#define MFI_CMD_STP 0x08 + +#define MR_DCMD_CTRL_GET_INFO 0x01010000 + +#define MR_DCMD_CTRL_CACHE_FLUSH 0x01101000 +#define MR_FLUSH_CTRL_CACHE 0x01 +#define MR_FLUSH_DISK_CACHE 0x02 + +#define MR_DCMD_CTRL_SHUTDOWN 0x01050000 +#define MR_ENABLE_DRIVE_SPINDOWN 0x01 + +#define MR_DCMD_CTRL_EVENT_GET_INFO 0x01040100 +#define MR_DCMD_CTRL_EVENT_GET 0x01040300 +#define MR_DCMD_CTRL_EVENT_WAIT 0x01040500 +#define MR_DCMD_LD_GET_PROPERTIES 0x03030000 + +#define MR_DCMD_CLUSTER 0x08000000 +#define MR_DCMD_CLUSTER_RESET_ALL 0x08010100 +#define MR_DCMD_CLUSTER_RESET_LD 0x08010200 + +/** + * MFI command completion codes + */ +enum MFI_STAT { + MFI_STAT_OK = 0x00, + MFI_STAT_INVALID_CMD = 0x01, + MFI_STAT_INVALID_DCMD = 0x02, + MFI_STAT_INVALID_PARAMETER = 0x03, + MFI_STAT_INVALID_SEQUENCE_NUMBER = 0x04, + MFI_STAT_ABORT_NOT_POSSIBLE = 0x05, + MFI_STAT_APP_HOST_CODE_NOT_FOUND = 0x06, + MFI_STAT_APP_IN_USE = 0x07, + MFI_STAT_APP_NOT_INITIALIZED = 0x08, + MFI_STAT_ARRAY_INDEX_INVALID = 0x09, + MFI_STAT_ARRAY_ROW_NOT_EMPTY = 0x0a, + MFI_STAT_CONFIG_RESOURCE_CONFLICT = 0x0b, + MFI_STAT_DEVICE_NOT_FOUND = 0x0c, + MFI_STAT_DRIVE_TOO_SMALL = 0x0d, + MFI_STAT_FLASH_ALLOC_FAIL = 0x0e, + MFI_STAT_FLASH_BUSY = 0x0f, + MFI_STAT_FLASH_ERROR = 0x10, + MFI_STAT_FLASH_IMAGE_BAD = 0x11, + MFI_STAT_FLASH_IMAGE_INCOMPLETE = 0x12, + MFI_STAT_FLASH_NOT_OPEN = 0x13, + MFI_STAT_FLASH_NOT_STARTED = 0x14, + MFI_STAT_FLUSH_FAILED = 0x15, + MFI_STAT_HOST_CODE_NOT_FOUNT = 0x16, + MFI_STAT_LD_CC_IN_PROGRESS = 0x17, + MFI_STAT_LD_INIT_IN_PROGRESS = 0x18, + MFI_STAT_LD_LBA_OUT_OF_RANGE = 0x19, + MFI_STAT_LD_MAX_CONFIGURED = 0x1a, + MFI_STAT_LD_NOT_OPTIMAL = 0x1b, + MFI_STAT_LD_RBLD_IN_PROGRESS = 0x1c, + MFI_STAT_LD_RECON_IN_PROGRESS = 0x1d, + MFI_STAT_LD_WRONG_RAID_LEVEL = 0x1e, + MFI_STAT_MAX_SPARES_EXCEEDED = 0x1f, + MFI_STAT_MEMORY_NOT_AVAILABLE = 0x20, + MFI_STAT_MFC_HW_ERROR = 0x21, + MFI_STAT_NO_HW_PRESENT = 0x22, + MFI_STAT_NOT_FOUND = 0x23, + MFI_STAT_NOT_IN_ENCL = 0x24, + MFI_STAT_PD_CLEAR_IN_PROGRESS = 0x25, + MFI_STAT_PD_TYPE_WRONG = 0x26, + MFI_STAT_PR_DISABLED = 0x27, + MFI_STAT_ROW_INDEX_INVALID = 0x28, + MFI_STAT_SAS_CONFIG_INVALID_ACTION = 0x29, + MFI_STAT_SAS_CONFIG_INVALID_DATA = 0x2a, + MFI_STAT_SAS_CONFIG_INVALID_PAGE = 0x2b, + MFI_STAT_SAS_CONFIG_INVALID_TYPE = 0x2c, + MFI_STAT_SCSI_DONE_WITH_ERROR = 0x2d, + MFI_STAT_SCSI_IO_FAILED = 0x2e, + MFI_STAT_SCSI_RESERVATION_CONFLICT = 0x2f, + MFI_STAT_SHUTDOWN_FAILED = 0x30, + MFI_STAT_TIME_NOT_SET = 0x31, + MFI_STAT_WRONG_STATE = 0x32, + MFI_STAT_LD_OFFLINE = 0x33, + MFI_STAT_PEER_NOTIFICATION_REJECTED = 0x34, + MFI_STAT_PEER_NOTIFICATION_FAILED = 0x35, + MFI_STAT_RESERVATION_IN_PROGRESS = 0x36, + MFI_STAT_I2C_ERRORS_DETECTED = 0x37, + MFI_STAT_PCI_ERRORS_DETECTED = 0x38, + + MFI_STAT_INVALID_STATUS = 0xFF +}; + +/* + * Number of mailbox bytes in DCMD message frame + */ +#define MFI_MBOX_SIZE 12 + +enum MR_EVT_CLASS { + + MR_EVT_CLASS_DEBUG = -2, + MR_EVT_CLASS_PROGRESS = -1, + MR_EVT_CLASS_INFO = 0, + MR_EVT_CLASS_WARNING = 1, + MR_EVT_CLASS_CRITICAL = 2, + MR_EVT_CLASS_FATAL = 3, + MR_EVT_CLASS_DEAD = 4, + +}; + +enum MR_EVT_LOCALE { + + MR_EVT_LOCALE_LD = 0x0001, + MR_EVT_LOCALE_PD = 0x0002, + MR_EVT_LOCALE_ENCL = 0x0004, + MR_EVT_LOCALE_BBU = 0x0008, + MR_EVT_LOCALE_SAS = 0x0010, + MR_EVT_LOCALE_CTRL = 0x0020, + MR_EVT_LOCALE_CONFIG = 0x0040, + MR_EVT_LOCALE_CLUSTER = 0x0080, + MR_EVT_LOCALE_ALL = 0xffff, + +}; + +enum MR_EVT_ARGS { + + MR_EVT_ARGS_NONE, + MR_EVT_ARGS_CDB_SENSE, + MR_EVT_ARGS_LD, + MR_EVT_ARGS_LD_COUNT, + MR_EVT_ARGS_LD_LBA, + MR_EVT_ARGS_LD_OWNER, + MR_EVT_ARGS_LD_LBA_PD_LBA, + MR_EVT_ARGS_LD_PROG, + MR_EVT_ARGS_LD_STATE, + MR_EVT_ARGS_LD_STRIP, + MR_EVT_ARGS_PD, + MR_EVT_ARGS_PD_ERR, + MR_EVT_ARGS_PD_LBA, + MR_EVT_ARGS_PD_LBA_LD, + MR_EVT_ARGS_PD_PROG, + MR_EVT_ARGS_PD_STATE, + MR_EVT_ARGS_PCI, + MR_EVT_ARGS_RATE, + MR_EVT_ARGS_STR, + MR_EVT_ARGS_TIME, + MR_EVT_ARGS_ECC, + +}; + +/* + * SAS controller properties + */ +struct megasas_ctrl_prop { + + u16 seq_num; + u16 pred_fail_poll_interval; + u16 intr_throttle_count; + u16 intr_throttle_timeouts; + u8 rebuild_rate; + u8 patrol_read_rate; + u8 bgi_rate; + u8 cc_rate; + u8 recon_rate; + u8 cache_flush_interval; + u8 spinup_drv_count; + u8 spinup_delay; + u8 cluster_enable; + u8 coercion_mode; + u8 alarm_enable; + u8 disable_auto_rebuild; + u8 disable_battery_warn; + u8 ecc_bucket_size; + u16 ecc_bucket_leak_rate; + u8 restore_hotspare_on_insertion; + u8 expose_encl_devices; + u8 reserved[38]; + +} __attribute__ ((packed)); + +/* + * SAS controller information + */ +struct megasas_ctrl_info { + + /* + * PCI device information + */ + struct { + + u16 vendor_id; + u16 device_id; + u16 sub_vendor_id; + u16 sub_device_id; + u8 reserved[24]; + + } __attribute__ ((packed)) pci; + + /* + * Host interface information + */ + struct { + + u8 PCIX:1; + u8 PCIE:1; + u8 iSCSI:1; + u8 SAS_3G:1; + u8 reserved_0:4; + u8 reserved_1[6]; + u8 port_count; + u64 port_addr[8]; + + } __attribute__ ((packed)) host_interface; + + /* + * Device (backend) interface information + */ + struct { + + u8 SPI:1; + u8 SAS_3G:1; + u8 SATA_1_5G:1; + u8 SATA_3G:1; + u8 reserved_0:4; + u8 reserved_1[6]; + u8 port_count; + u64 port_addr[8]; + + } __attribute__ ((packed)) device_interface; + + /* + * List of components residing in flash. All str are null terminated + */ + u32 image_check_word; + u32 image_component_count; + + struct { + + char name[8]; + char version[32]; + char build_date[16]; + char built_time[16]; + + } __attribute__ ((packed)) image_component[8]; + + /* + * List of flash components that have been flashed on the card, but + * are not in use, pending reset of the adapter. This list will be + * empty if a flash operation has not occurred. All stings are null + * terminated + */ + u32 pending_image_component_count; + + struct { + + char name[8]; + char version[32]; + char build_date[16]; + char build_time[16]; + + } __attribute__ ((packed)) pending_image_component[8]; + + u8 max_arms; + u8 max_spans; + u8 max_arrays; + u8 max_lds; + + char product_name[80]; + char serial_no[32]; + + /* + * Other physical/controller/operation information. Indicates the + * presence of the hardware + */ + struct { + + u32 bbu:1; + u32 alarm:1; + u32 nvram:1; + u32 uart:1; + u32 reserved:28; + + } __attribute__ ((packed)) hw_present; + + u32 current_fw_time; + + /* + * Maximum data transfer sizes + */ + u16 max_concurrent_cmds; + u16 max_sge_count; + u32 max_request_size; + + /* + * Logical and physical device counts + */ + u16 ld_present_count; + u16 ld_degraded_count; + u16 ld_offline_count; + + u16 pd_present_count; + u16 pd_disk_present_count; + u16 pd_disk_pred_failure_count; + u16 pd_disk_failed_count; + + /* + * Memory size information + */ + u16 nvram_size; + u16 memory_size; + u16 flash_size; + + /* + * Error counters + */ + u16 mem_correctable_error_count; + u16 mem_uncorrectable_error_count; + + /* + * Cluster information + */ + u8 cluster_permitted; + u8 cluster_active; + + /* + * Additional max data transfer sizes + */ + u16 max_strips_per_io; + + /* + * Controller capabilities structures + */ + struct { + + u32 raid_level_0:1; + u32 raid_level_1:1; + u32 raid_level_5:1; + u32 raid_level_1E:1; + u32 raid_level_6:1; + u32 reserved:27; + + } __attribute__ ((packed)) raid_levels; + + struct { + + u32 rbld_rate:1; + u32 cc_rate:1; + u32 bgi_rate:1; + u32 recon_rate:1; + u32 patrol_rate:1; + u32 alarm_control:1; + u32 cluster_supported:1; + u32 bbu:1; + u32 spanning_allowed:1; + u32 dedicated_hotspares:1; + u32 revertible_hotspares:1; + u32 foreign_config_import:1; + u32 self_diagnostic:1; + u32 mixed_redundancy_arr:1; + u32 global_hot_spares:1; + u32 reserved:17; + + } __attribute__ ((packed)) adapter_operations; + + struct { + + u32 read_policy:1; + u32 write_policy:1; + u32 io_policy:1; + u32 access_policy:1; + u32 disk_cache_policy:1; + u32 reserved:27; + + } __attribute__ ((packed)) ld_operations; + + struct { + + u8 min; + u8 max; + u8 reserved[2]; + + } __attribute__ ((packed)) stripe_sz_ops; + + struct { + + u32 force_online:1; + u32 force_offline:1; + u32 force_rebuild:1; + u32 reserved:29; + + } __attribute__ ((packed)) pd_operations; + + struct { + + u32 ctrl_supports_sas:1; + u32 ctrl_supports_sata:1; + u32 allow_mix_in_encl:1; + u32 allow_mix_in_ld:1; + u32 allow_sata_in_cluster:1; + u32 reserved:27; + + } __attribute__ ((packed)) pd_mix_support; + + /* + * Define ECC single-bit-error bucket information + */ + u8 ecc_bucket_count; + u8 reserved_2[11]; + + /* + * Include the controller properties (changeable items) + */ + struct megasas_ctrl_prop properties; + + /* + * Define FW pkg version (set in envt v'bles on OEM basis) + */ + char package_version[0x60]; + + u8 pad[0x800 - 0x6a0]; + +} __attribute__ ((packed)); + +/* + * =============================== + * MegaRAID SAS driver definitions + * =============================== + */ +#define MEGASAS_MAX_PD_CHANNELS 2 +#define MEGASAS_MAX_LD_CHANNELS 2 +#define MEGASAS_MAX_CHANNELS (MEGASAS_MAX_PD_CHANNELS + \ + MEGASAS_MAX_LD_CHANNELS) +#define MEGASAS_MAX_DEV_PER_CHANNEL 128 +#define MEGASAS_DEFAULT_INIT_ID -1 +#define MEGASAS_MAX_LUN 8 +#define MEGASAS_MAX_LD 64 + +/* + * When SCSI mid-layer calls driver's reset routine, driver waits for + * MEGASAS_RESET_WAIT_TIME seconds for all outstanding IO to complete. Note + * that the driver cannot _actually_ abort or reset pending commands. While + * it is waiting for the commands to complete, it prints a diagnostic message + * every MEGASAS_RESET_NOTICE_INTERVAL seconds + */ +#define MEGASAS_RESET_WAIT_TIME 180 +#define MEGASAS_RESET_NOTICE_INTERVAL 5 + +#define MEGASAS_IOCTL_CMD 0 + +/* + * FW reports the maximum of number of commands that it can accept (maximum + * commands that can be outstanding) at any time. The driver must report a + * lower number to the mid layer because it can issue a few internal commands + * itself (E.g, AEN, abort cmd, IOCTLs etc). The number of commands it needs + * is shown below + */ +#define MEGASAS_INT_CMDS 32 + +/* + * FW can accept both 32 and 64 bit SGLs. We want to allocate 32/64 bit + * SGLs based on the size of dma_addr_t + */ +#define IS_DMA64 (sizeof(dma_addr_t) == 8) + +#define MFI_OB_INTR_STATUS_MASK 0x00000002 +#define MFI_POLL_TIMEOUT_SECS 10 + +struct megasas_register_set { + + u32 reserved_0[4]; /*0000h */ + + u32 inbound_msg_0; /*0010h */ + u32 inbound_msg_1; /*0014h */ + u32 outbound_msg_0; /*0018h */ + u32 outbound_msg_1; /*001Ch */ + + u32 inbound_doorbell; /*0020h */ + u32 inbound_intr_status; /*0024h */ + u32 inbound_intr_mask; /*0028h */ + + u32 outbound_doorbell; /*002Ch */ + u32 outbound_intr_status; /*0030h */ + u32 outbound_intr_mask; /*0034h */ + + u32 reserved_1[2]; /*0038h */ + + u32 inbound_queue_port; /*0040h */ + u32 outbound_queue_port; /*0044h */ + + u32 reserved_2; /*004Ch */ + + u32 index_registers[1004]; /*0050h */ + +} __attribute__ ((packed)); + +struct megasas_sge32 { + + u32 phys_addr; + u32 length; + +} __attribute__ ((packed)); + +struct megasas_sge64 { + + u64 phys_addr; + u32 length; + +} __attribute__ ((packed)); + +union megasas_sgl { + + struct megasas_sge32 sge32[1]; + struct megasas_sge64 sge64[1]; + +} __attribute__ ((packed)); + +struct megasas_header { + + u8 cmd; /*00h */ + u8 sense_len; /*01h */ + u8 cmd_status; /*02h */ + u8 scsi_status; /*03h */ + + u8 target_id; /*04h */ + u8 lun; /*05h */ + u8 cdb_len; /*06h */ + u8 sge_count; /*07h */ + + u32 context; /*08h */ + u32 pad_0; /*0Ch */ + + u16 flags; /*10h */ + u16 timeout; /*12h */ + u32 data_xferlen; /*14h */ + +} __attribute__ ((packed)); + +union megasas_sgl_frame { + + struct megasas_sge32 sge32[8]; + struct megasas_sge64 sge64[5]; + +} __attribute__ ((packed)); + +struct megasas_init_frame { + + u8 cmd; /*00h */ + u8 reserved_0; /*01h */ + u8 cmd_status; /*02h */ + + u8 reserved_1; /*03h */ + u32 reserved_2; /*04h */ + + u32 context; /*08h */ + u32 pad_0; /*0Ch */ + + u16 flags; /*10h */ + u16 reserved_3; /*12h */ + u32 data_xfer_len; /*14h */ + + u32 queue_info_new_phys_addr_lo; /*18h */ + u32 queue_info_new_phys_addr_hi; /*1Ch */ + u32 queue_info_old_phys_addr_lo; /*20h */ + u32 queue_info_old_phys_addr_hi; /*24h */ + + u32 reserved_4[6]; /*28h */ + +} __attribute__ ((packed)); + +struct megasas_init_queue_info { + + u32 init_flags; /*00h */ + u32 reply_queue_entries; /*04h */ + + u32 reply_queue_start_phys_addr_lo; /*08h */ + u32 reply_queue_start_phys_addr_hi; /*0Ch */ + u32 producer_index_phys_addr_lo; /*10h */ + u32 producer_index_phys_addr_hi; /*14h */ + u32 consumer_index_phys_addr_lo; /*18h */ + u32 consumer_index_phys_addr_hi; /*1Ch */ + +} __attribute__ ((packed)); + +struct megasas_io_frame { + + u8 cmd; /*00h */ + u8 sense_len; /*01h */ + u8 cmd_status; /*02h */ + u8 scsi_status; /*03h */ + + u8 target_id; /*04h */ + u8 access_byte; /*05h */ + u8 reserved_0; /*06h */ + u8 sge_count; /*07h */ + + u32 context; /*08h */ + u32 pad_0; /*0Ch */ + + u16 flags; /*10h */ + u16 timeout; /*12h */ + u32 lba_count; /*14h */ + + u32 sense_buf_phys_addr_lo; /*18h */ + u32 sense_buf_phys_addr_hi; /*1Ch */ + + u32 start_lba_lo; /*20h */ + u32 start_lba_hi; /*24h */ + + union megasas_sgl sgl; /*28h */ + +} __attribute__ ((packed)); + +struct megasas_pthru_frame { + + u8 cmd; /*00h */ + u8 sense_len; /*01h */ + u8 cmd_status; /*02h */ + u8 scsi_status; /*03h */ + + u8 target_id; /*04h */ + u8 lun; /*05h */ + u8 cdb_len; /*06h */ + u8 sge_count; /*07h */ + + u32 context; /*08h */ + u32 pad_0; /*0Ch */ + + u16 flags; /*10h */ + u16 timeout; /*12h */ + u32 data_xfer_len; /*14h */ + + u32 sense_buf_phys_addr_lo; /*18h */ + u32 sense_buf_phys_addr_hi; /*1Ch */ + + u8 cdb[16]; /*20h */ + union megasas_sgl sgl; /*30h */ + +} __attribute__ ((packed)); + +struct megasas_dcmd_frame { + + u8 cmd; /*00h */ + u8 reserved_0; /*01h */ + u8 cmd_status; /*02h */ + u8 reserved_1[4]; /*03h */ + u8 sge_count; /*07h */ + + u32 context; /*08h */ + u32 pad_0; /*0Ch */ + + u16 flags; /*10h */ + u16 timeout; /*12h */ + + u32 data_xfer_len; /*14h */ + u32 opcode; /*18h */ + + union { /*1Ch */ + u8 b[12]; + u16 s[6]; + u32 w[3]; + } mbox; + + union megasas_sgl sgl; /*28h */ + +} __attribute__ ((packed)); + +struct megasas_abort_frame { + + u8 cmd; /*00h */ + u8 reserved_0; /*01h */ + u8 cmd_status; /*02h */ + + u8 reserved_1; /*03h */ + u32 reserved_2; /*04h */ + + u32 context; /*08h */ + u32 pad_0; /*0Ch */ + + u16 flags; /*10h */ + u16 reserved_3; /*12h */ + u32 reserved_4; /*14h */ + + u32 abort_context; /*18h */ + u32 pad_1; /*1Ch */ + + u32 abort_mfi_phys_addr_lo; /*20h */ + u32 abort_mfi_phys_addr_hi; /*24h */ + + u32 reserved_5[6]; /*28h */ + +} __attribute__ ((packed)); + +struct megasas_smp_frame { + + u8 cmd; /*00h */ + u8 reserved_1; /*01h */ + u8 cmd_status; /*02h */ + u8 connection_status; /*03h */ + + u8 reserved_2[3]; /*04h */ + u8 sge_count; /*07h */ + + u32 context; /*08h */ + u32 pad_0; /*0Ch */ + + u16 flags; /*10h */ + u16 timeout; /*12h */ + + u32 data_xfer_len; /*14h */ + u64 sas_addr; /*18h */ + + union { + struct megasas_sge32 sge32[2]; /* [0]: resp [1]: req */ + struct megasas_sge64 sge64[2]; /* [0]: resp [1]: req */ + } sgl; + +} __attribute__ ((packed)); + +struct megasas_stp_frame { + + u8 cmd; /*00h */ + u8 reserved_1; /*01h */ + u8 cmd_status; /*02h */ + u8 reserved_2; /*03h */ + + u8 target_id; /*04h */ + u8 reserved_3[2]; /*05h */ + u8 sge_count; /*07h */ + + u32 context; /*08h */ + u32 pad_0; /*0Ch */ + + u16 flags; /*10h */ + u16 timeout; /*12h */ + + u32 data_xfer_len; /*14h */ + + u16 fis[10]; /*18h */ + u32 stp_flags; + + union { + struct megasas_sge32 sge32[2]; /* [0]: resp [1]: data */ + struct megasas_sge64 sge64[2]; /* [0]: resp [1]: data */ + } sgl; + +} __attribute__ ((packed)); + +union megasas_frame { + + struct megasas_header hdr; + struct megasas_init_frame init; + struct megasas_io_frame io; + struct megasas_pthru_frame pthru; + struct megasas_dcmd_frame dcmd; + struct megasas_abort_frame abort; + struct megasas_smp_frame smp; + struct megasas_stp_frame stp; + + u8 raw_bytes[64]; +}; + +struct megasas_cmd; + +union megasas_evt_class_locale { + + struct { + u16 locale; + u8 reserved; + s8 class; + } __attribute__ ((packed)) members; + + u32 word; + +} __attribute__ ((packed)); + +struct megasas_evt_log_info { + u32 newest_seq_num; + u32 oldest_seq_num; + u32 clear_seq_num; + u32 shutdown_seq_num; + u32 boot_seq_num; + +} __attribute__ ((packed)); + +struct megasas_progress { + + u16 progress; + u16 elapsed_seconds; + +} __attribute__ ((packed)); + +struct megasas_evtarg_ld { + + u16 target_id; + u8 ld_index; + u8 reserved; + +} __attribute__ ((packed)); + +struct megasas_evtarg_pd { + u16 device_id; + u8 encl_index; + u8 slot_number; + +} __attribute__ ((packed)); + +struct megasas_evt_detail { + + u32 seq_num; + u32 time_stamp; + u32 code; + union megasas_evt_class_locale cl; + u8 arg_type; + u8 reserved1[15]; + + union { + struct { + struct megasas_evtarg_pd pd; + u8 cdb_length; + u8 sense_length; + u8 reserved[2]; + u8 cdb[16]; + u8 sense[64]; + } __attribute__ ((packed)) cdbSense; + + struct megasas_evtarg_ld ld; + + struct { + struct megasas_evtarg_ld ld; + u64 count; + } __attribute__ ((packed)) ld_count; + + struct { + u64 lba; + struct megasas_evtarg_ld ld; + } __attribute__ ((packed)) ld_lba; + + struct { + struct megasas_evtarg_ld ld; + u32 prevOwner; + u32 newOwner; + } __attribute__ ((packed)) ld_owner; + + struct { + u64 ld_lba; + u64 pd_lba; + struct megasas_evtarg_ld ld; + struct megasas_evtarg_pd pd; + } __attribute__ ((packed)) ld_lba_pd_lba; + + struct { + struct megasas_evtarg_ld ld; + struct megasas_progress prog; + } __attribute__ ((packed)) ld_prog; + + struct { + struct megasas_evtarg_ld ld; + u32 prev_state; + u32 new_state; + } __attribute__ ((packed)) ld_state; + + struct { + u64 strip; + struct megasas_evtarg_ld ld; + } __attribute__ ((packed)) ld_strip; + + struct megasas_evtarg_pd pd; + + struct { + struct megasas_evtarg_pd pd; + u32 err; + } __attribute__ ((packed)) pd_err; + + struct { + u64 lba; + struct megasas_evtarg_pd pd; + } __attribute__ ((packed)) pd_lba; + + struct { + u64 lba; + struct megasas_evtarg_pd pd; + struct megasas_evtarg_ld ld; + } __attribute__ ((packed)) pd_lba_ld; + + struct { + struct megasas_evtarg_pd pd; + struct megasas_progress prog; + } __attribute__ ((packed)) pd_prog; + + struct { + struct megasas_evtarg_pd pd; + u32 prevState; + u32 newState; + } __attribute__ ((packed)) pd_state; + + struct { + u16 vendorId; + u16 deviceId; + u16 subVendorId; + u16 subDeviceId; + } __attribute__ ((packed)) pci; + + u32 rate; + char str[96]; + + struct { + u32 rtc; + u32 elapsedSeconds; + } __attribute__ ((packed)) time; + + struct { + u32 ecar; + u32 elog; + char str[64]; + } __attribute__ ((packed)) ecc; + + u8 b[96]; + u16 s[48]; + u32 w[24]; + u64 d[12]; + } args; + + char description[128]; + +} __attribute__ ((packed)); + +struct megasas_instance { + + u32 *producer; + dma_addr_t producer_h; + u32 *consumer; + dma_addr_t consumer_h; + + u32 *reply_queue; + dma_addr_t reply_queue_h; + + unsigned long base_addr; + struct megasas_register_set __iomem *reg_set; + + s8 init_id; + u8 reserved[3]; + + u16 max_num_sge; + u16 max_fw_cmds; + u32 max_sectors_per_req; + + struct megasas_cmd **cmd_list; + struct list_head cmd_pool; + spinlock_t cmd_pool_lock; + struct dma_pool *frame_dma_pool; + struct dma_pool *sense_dma_pool; + + struct megasas_evt_detail *evt_detail; + dma_addr_t evt_detail_h; + struct megasas_cmd *aen_cmd; + struct semaphore aen_mutex; + struct semaphore ioctl_sem; + + struct Scsi_Host *host; + + wait_queue_head_t int_cmd_wait_q; + wait_queue_head_t abort_cmd_wait_q; + + struct pci_dev *pdev; + u32 unique_id; + + u32 fw_outstanding; + u32 hw_crit_error; + spinlock_t instance_lock; +}; + +#define MEGASAS_IS_LOGICAL(scp) \ + (scp->device->channel < MEGASAS_MAX_PD_CHANNELS) ? 0 : 1 + +#define MEGASAS_DEV_INDEX(inst, scp) \ + ((scp->device->channel % 2) * MEGASAS_MAX_DEV_PER_CHANNEL) + \ + scp->device->id + +struct megasas_cmd { + + union megasas_frame *frame; + dma_addr_t frame_phys_addr; + u8 *sense; + dma_addr_t sense_phys_addr; + + u32 index; + u8 sync_cmd; + u8 cmd_status; + u16 abort_aen; + + struct list_head list; + struct scsi_cmnd *scmd; + struct megasas_instance *instance; + u32 frame_count; +}; + +#define MAX_MGMT_ADAPTERS 1024 +#define MAX_IOCTL_SGE 16 + +struct megasas_iocpacket { + + u16 host_no; + u16 __pad1; + u32 sgl_off; + u32 sge_count; + u32 sense_off; + u32 sense_len; + union { + u8 raw[128]; + struct megasas_header hdr; + } frame; + + struct iovec sgl[MAX_IOCTL_SGE]; + +} __attribute__ ((packed)); + +struct megasas_aen { + u16 host_no; + u16 __pad1; + u32 seq_num; + u32 class_locale_word; +} __attribute__ ((packed)); + +#ifdef CONFIG_COMPAT +struct compat_megasas_iocpacket { + u16 host_no; + u16 __pad1; + u32 sgl_off; + u32 sge_count; + u32 sense_off; + u32 sense_len; + union { + u8 raw[128]; + struct megasas_header hdr; + } frame; + struct compat_iovec sgl[MAX_IOCTL_SGE]; +} __attribute__ ((packed)); + +#define MEGASAS_IOC_FIRMWARE _IOWR('M', 1, struct compat_megasas_iocpacket) +#else +#define MEGASAS_IOC_FIRMWARE _IOWR('M', 1, struct megasas_iocpacket) +#endif + +#define MEGASAS_IOC_GET_AEN _IOW('M', 3, struct megasas_aen) + +struct megasas_mgmt_info { + + u16 count; + struct megasas_instance *instance[MAX_MGMT_ADAPTERS]; + int max_index; +}; + +#endif /*LSI_MEGARAID_SAS_H */ diff --git a/include/linux/pci_ids.h b/include/linux/pci_ids.h index c49d28eca56..20fb79810c3 100644 --- a/include/linux/pci_ids.h +++ b/include/linux/pci_ids.h @@ -185,6 +185,7 @@ #define PCI_DEVICE_ID_LSI_61C102 0x0901 #define PCI_DEVICE_ID_LSI_63C815 0x1000 #define PCI_DEVICE_ID_LSI_SAS1064 0x0050 +#define PCI_DEVICE_ID_LSI_SAS1064R 0x0411 #define PCI_DEVICE_ID_LSI_SAS1066 0x005E #define PCI_DEVICE_ID_LSI_SAS1068 0x0054 #define PCI_DEVICE_ID_LSI_SAS1064A 0x005C @@ -559,6 +560,7 @@ #define PCI_VENDOR_ID_DELL 0x1028 #define PCI_DEVICE_ID_DELL_RACIII 0x0008 #define PCI_DEVICE_ID_DELL_RAC4 0x0012 +#define PCI_DEVICE_ID_DELL_PERC5 0x0015 #define PCI_VENDOR_ID_MATROX 0x102B #define PCI_DEVICE_ID_MATROX_MGA_2 0x0518 -- cgit v1.2.3 From 7a8cf29d69e077dfe90e327859201fd9b75a47ce Mon Sep 17 00:00:00 2001 From: Mark Haverkamp Date: Thu, 22 Sep 2005 09:15:24 -0700 Subject: [SCSI] aacraid: Greater than 2TB capacity support Received from Mark Salyzyn from Adaptec. There are a few adapters that are capable of creating devices with this large of a capacity, but now that we have the large fib support in, the management applications will be capable of generating them. The problem is, once they are created, the driver will not be able to access the devices correctly without this patch. Signed-off-by: Mark Haverkamp Signed-off-by: James Bottomley --- drivers/scsi/aacraid/aachba.c | 269 +++++++++++++++++++++++++++++++++++----- drivers/scsi/aacraid/aacraid.h | 10 +- drivers/scsi/aacraid/comminit.c | 7 ++ drivers/scsi/aacraid/linit.c | 1 + 4 files changed, 254 insertions(+), 33 deletions(-) diff --git a/drivers/scsi/aacraid/aachba.c b/drivers/scsi/aacraid/aachba.c index a8e3dfcd0dc..0a209b2cd69 100644 --- a/drivers/scsi/aacraid/aachba.c +++ b/drivers/scsi/aacraid/aachba.c @@ -313,18 +313,37 @@ int aac_get_containers(struct aac_dev *dev) } dresp = (struct aac_mount *)fib_data(fibptr); + if ((le32_to_cpu(dresp->status) == ST_OK) && + (le32_to_cpu(dresp->mnt[0].vol) == CT_NONE)) { + dinfo->command = cpu_to_le32(VM_NameServe64); + dinfo->count = cpu_to_le32(index); + dinfo->type = cpu_to_le32(FT_FILESYS); + + if (fib_send(ContainerCommand, + fibptr, + sizeof(struct aac_query_mount), + FsaNormal, + 1, 1, + NULL, NULL) < 0) + continue; + } else + dresp->mnt[0].capacityhigh = 0; + dprintk ((KERN_DEBUG - "VM_NameServe cid=%d status=%d vol=%d state=%d cap=%u\n", + "VM_NameServe cid=%d status=%d vol=%d state=%d cap=%llu\n", (int)index, (int)le32_to_cpu(dresp->status), (int)le32_to_cpu(dresp->mnt[0].vol), (int)le32_to_cpu(dresp->mnt[0].state), - (unsigned)le32_to_cpu(dresp->mnt[0].capacity))); + ((u64)le32_to_cpu(dresp->mnt[0].capacity)) + + (((u64)le32_to_cpu(dresp->mnt[0].capacityhigh)) << 32))); if ((le32_to_cpu(dresp->status) == ST_OK) && (le32_to_cpu(dresp->mnt[0].vol) != CT_NONE) && (le32_to_cpu(dresp->mnt[0].state) != FSCS_HIDDEN)) { fsa_dev_ptr[index].valid = 1; fsa_dev_ptr[index].type = le32_to_cpu(dresp->mnt[0].vol); - fsa_dev_ptr[index].size = le32_to_cpu(dresp->mnt[0].capacity); + fsa_dev_ptr[index].size + = ((u64)le32_to_cpu(dresp->mnt[0].capacity)) + + (((u64)le32_to_cpu(dresp->mnt[0].capacityhigh)) << 32); if (le32_to_cpu(dresp->mnt[0].state) & FSCS_READONLY) fsa_dev_ptr[index].ro = 1; } @@ -496,12 +515,30 @@ static int probe_container(struct aac_dev *dev, int cid) dresp = (struct aac_mount *) fib_data(fibptr); + if ((le32_to_cpu(dresp->status) == ST_OK) && + (le32_to_cpu(dresp->mnt[0].vol) == CT_NONE)) { + dinfo->command = cpu_to_le32(VM_NameServe64); + dinfo->count = cpu_to_le32(cid); + dinfo->type = cpu_to_le32(FT_FILESYS); + + if (fib_send(ContainerCommand, + fibptr, + sizeof(struct aac_query_mount), + FsaNormal, + 1, 1, + NULL, NULL) < 0) + goto error; + } else + dresp->mnt[0].capacityhigh = 0; + if ((le32_to_cpu(dresp->status) == ST_OK) && (le32_to_cpu(dresp->mnt[0].vol) != CT_NONE) && (le32_to_cpu(dresp->mnt[0].state) != FSCS_HIDDEN)) { fsa_dev_ptr[cid].valid = 1; fsa_dev_ptr[cid].type = le32_to_cpu(dresp->mnt[0].vol); - fsa_dev_ptr[cid].size = le32_to_cpu(dresp->mnt[0].capacity); + fsa_dev_ptr[cid].size + = ((u64)le32_to_cpu(dresp->mnt[0].capacity)) + + (((u64)le32_to_cpu(dresp->mnt[0].capacityhigh)) << 32); if (le32_to_cpu(dresp->mnt[0].state) & FSCS_READONLY) fsa_dev_ptr[cid].ro = 1; } @@ -854,7 +891,40 @@ static void io_callback(void *context, struct fib * fibptr) dev = (struct aac_dev *)scsicmd->device->host->hostdata; cid = ID_LUN_TO_CONTAINER(scsicmd->device->id, scsicmd->device->lun); - dprintk((KERN_DEBUG "io_callback[cpu %d]: lba = %u, t = %ld.\n", smp_processor_id(), ((scsicmd->cmnd[1] & 0x1F) << 16) | (scsicmd->cmnd[2] << 8) | scsicmd->cmnd[3], jiffies)); + if (nblank(dprintk(x))) { + u64 lba; + switch (scsicmd->cmnd[0]) { + case WRITE_6: + case READ_6: + lba = ((scsicmd->cmnd[1] & 0x1F) << 16) | + (scsicmd->cmnd[2] << 8) | scsicmd->cmnd[3]; + break; + case WRITE_16: + case READ_16: + lba = ((u64)scsicmd->cmnd[2] << 56) | + ((u64)scsicmd->cmnd[3] << 48) | + ((u64)scsicmd->cmnd[4] << 40) | + ((u64)scsicmd->cmnd[5] << 32) | + ((u64)scsicmd->cmnd[6] << 24) | + (scsicmd->cmnd[7] << 16) | + (scsicmd->cmnd[8] << 8) | scsicmd->cmnd[9]; + break; + case WRITE_12: + case READ_12: + lba = ((u64)scsicmd->cmnd[2] << 24) | + (scsicmd->cmnd[3] << 16) | + (scsicmd->cmnd[4] << 8) | scsicmd->cmnd[5]; + break; + default: + lba = ((u64)scsicmd->cmnd[2] << 24) | + (scsicmd->cmnd[3] << 16) | + (scsicmd->cmnd[4] << 8) | scsicmd->cmnd[5]; + break; + } + printk(KERN_DEBUG + "io_callback[cpu %d]: lba = %llu, t = %ld.\n", + smp_processor_id(), (unsigned long long)lba, jiffies); + } if (fibptr == NULL) BUG(); @@ -895,7 +965,7 @@ static void io_callback(void *context, struct fib * fibptr) static int aac_read(struct scsi_cmnd * scsicmd, int cid) { - u32 lba; + u64 lba; u32 count; int status; @@ -907,23 +977,69 @@ static int aac_read(struct scsi_cmnd * scsicmd, int cid) /* * Get block address and transfer length */ - if (scsicmd->cmnd[0] == READ_6) /* 6 byte command */ - { + switch (scsicmd->cmnd[0]) { + case READ_6: dprintk((KERN_DEBUG "aachba: received a read(6) command on id %d.\n", cid)); - lba = ((scsicmd->cmnd[1] & 0x1F) << 16) | (scsicmd->cmnd[2] << 8) | scsicmd->cmnd[3]; + lba = ((scsicmd->cmnd[1] & 0x1F) << 16) | + (scsicmd->cmnd[2] << 8) | scsicmd->cmnd[3]; count = scsicmd->cmnd[4]; if (count == 0) count = 256; - } else { + break; + case READ_16: + dprintk((KERN_DEBUG "aachba: received a read(16) command on id %d.\n", cid)); + + lba = ((u64)scsicmd->cmnd[2] << 56) | + ((u64)scsicmd->cmnd[3] << 48) | + ((u64)scsicmd->cmnd[4] << 40) | + ((u64)scsicmd->cmnd[5] << 32) | + ((u64)scsicmd->cmnd[6] << 24) | + (scsicmd->cmnd[7] << 16) | + (scsicmd->cmnd[8] << 8) | scsicmd->cmnd[9]; + count = (scsicmd->cmnd[10] << 24) | + (scsicmd->cmnd[11] << 16) | + (scsicmd->cmnd[12] << 8) | scsicmd->cmnd[13]; + break; + case READ_12: + dprintk((KERN_DEBUG "aachba: received a read(12) command on id %d.\n", cid)); + + lba = ((u64)scsicmd->cmnd[2] << 24) | + (scsicmd->cmnd[3] << 16) | + (scsicmd->cmnd[4] << 8) | scsicmd->cmnd[5]; + count = (scsicmd->cmnd[6] << 24) | + (scsicmd->cmnd[7] << 16) | + (scsicmd->cmnd[8] << 8) | scsicmd->cmnd[9]; + break; + default: dprintk((KERN_DEBUG "aachba: received a read(10) command on id %d.\n", cid)); - lba = (scsicmd->cmnd[2] << 24) | (scsicmd->cmnd[3] << 16) | (scsicmd->cmnd[4] << 8) | scsicmd->cmnd[5]; + lba = ((u64)scsicmd->cmnd[2] << 24) | + (scsicmd->cmnd[3] << 16) | + (scsicmd->cmnd[4] << 8) | scsicmd->cmnd[5]; count = (scsicmd->cmnd[7] << 8) | scsicmd->cmnd[8]; + break; } - dprintk((KERN_DEBUG "aac_read[cpu %d]: lba = %u, t = %ld.\n", + dprintk((KERN_DEBUG "aac_read[cpu %d]: lba = %llu, t = %ld.\n", smp_processor_id(), (unsigned long long)lba, jiffies)); + if ((!(dev->raw_io_interface) || !(dev->raw_io_64)) && + (lba & 0xffffffff00000000LL)) { + dprintk((KERN_DEBUG "aac_read: Illegal lba\n")); + scsicmd->result = DID_OK << 16 | COMMAND_COMPLETE << 8 | + SAM_STAT_CHECK_CONDITION; + set_sense((u8 *) &dev->fsa_dev[cid].sense_data, + HARDWARE_ERROR, + SENCODE_INTERNAL_TARGET_FAILURE, + ASENCODE_INTERNAL_TARGET_FAILURE, 0, 0, + 0, 0); + memcpy(scsicmd->sense_buffer, &dev->fsa_dev[cid].sense_data, + (sizeof(dev->fsa_dev[cid].sense_data) > sizeof(scsicmd->sense_buffer)) + ? sizeof(scsicmd->sense_buffer) + : sizeof(dev->fsa_dev[cid].sense_data)); + scsicmd->scsi_done(scsicmd); + return 0; + } /* * Alocate and initialize a Fib */ @@ -936,8 +1052,8 @@ static int aac_read(struct scsi_cmnd * scsicmd, int cid) if (dev->raw_io_interface) { struct aac_raw_io *readcmd; readcmd = (struct aac_raw_io *) fib_data(cmd_fibcontext); - readcmd->block[0] = cpu_to_le32(lba); - readcmd->block[1] = 0; + readcmd->block[0] = cpu_to_le32((u32)(lba&0xffffffff)); + readcmd->block[1] = cpu_to_le32((u32)((lba&0xffffffff00000000LL)>>32)); readcmd->count = cpu_to_le32(count<<9); readcmd->cid = cpu_to_le16(cid); readcmd->flags = cpu_to_le16(1); @@ -964,7 +1080,7 @@ static int aac_read(struct scsi_cmnd * scsicmd, int cid) readcmd->command = cpu_to_le32(VM_CtHostRead64); readcmd->cid = cpu_to_le16(cid); readcmd->sector_count = cpu_to_le16(count); - readcmd->block = cpu_to_le32(lba); + readcmd->block = cpu_to_le32((u32)(lba&0xffffffff)); readcmd->pad = 0; readcmd->flags = 0; @@ -989,7 +1105,7 @@ static int aac_read(struct scsi_cmnd * scsicmd, int cid) readcmd = (struct aac_read *) fib_data(cmd_fibcontext); readcmd->command = cpu_to_le32(VM_CtBlockRead); readcmd->cid = cpu_to_le32(cid); - readcmd->block = cpu_to_le32(lba); + readcmd->block = cpu_to_le32((u32)(lba&0xffffffff)); readcmd->count = cpu_to_le32(count * 512); aac_build_sg(scsicmd, &readcmd->sg); @@ -1031,7 +1147,7 @@ static int aac_read(struct scsi_cmnd * scsicmd, int cid) static int aac_write(struct scsi_cmnd * scsicmd, int cid) { - u32 lba; + u64 lba; u32 count; int status; u16 fibsize; @@ -1048,13 +1164,48 @@ static int aac_write(struct scsi_cmnd * scsicmd, int cid) count = scsicmd->cmnd[4]; if (count == 0) count = 256; + } else if (scsicmd->cmnd[0] == WRITE_16) { /* 16 byte command */ + dprintk((KERN_DEBUG "aachba: received a write(16) command on id %d.\n", cid)); + + lba = ((u64)scsicmd->cmnd[2] << 56) | + ((u64)scsicmd->cmnd[3] << 48) | + ((u64)scsicmd->cmnd[4] << 40) | + ((u64)scsicmd->cmnd[5] << 32) | + ((u64)scsicmd->cmnd[6] << 24) | + (scsicmd->cmnd[7] << 16) | + (scsicmd->cmnd[8] << 8) | scsicmd->cmnd[9]; + count = (scsicmd->cmnd[10] << 24) | (scsicmd->cmnd[11] << 16) | + (scsicmd->cmnd[12] << 8) | scsicmd->cmnd[13]; + } else if (scsicmd->cmnd[0] == WRITE_12) { /* 12 byte command */ + dprintk((KERN_DEBUG "aachba: received a write(12) command on id %d.\n", cid)); + + lba = ((u64)scsicmd->cmnd[2] << 24) | (scsicmd->cmnd[3] << 16) + | (scsicmd->cmnd[4] << 8) | scsicmd->cmnd[5]; + count = (scsicmd->cmnd[6] << 24) | (scsicmd->cmnd[7] << 16) + | (scsicmd->cmnd[8] << 8) | scsicmd->cmnd[9]; } else { dprintk((KERN_DEBUG "aachba: received a write(10) command on id %d.\n", cid)); - lba = (scsicmd->cmnd[2] << 24) | (scsicmd->cmnd[3] << 16) | (scsicmd->cmnd[4] << 8) | scsicmd->cmnd[5]; + lba = ((u64)scsicmd->cmnd[2] << 24) | (scsicmd->cmnd[3] << 16) | (scsicmd->cmnd[4] << 8) | scsicmd->cmnd[5]; count = (scsicmd->cmnd[7] << 8) | scsicmd->cmnd[8]; } - dprintk((KERN_DEBUG "aac_write[cpu %d]: lba = %u, t = %ld.\n", + dprintk((KERN_DEBUG "aac_write[cpu %d]: lba = %llu, t = %ld.\n", smp_processor_id(), (unsigned long long)lba, jiffies)); + if ((!(dev->raw_io_interface) || !(dev->raw_io_64)) + && (lba & 0xffffffff00000000LL)) { + dprintk((KERN_DEBUG "aac_write: Illegal lba\n")); + scsicmd->result = DID_OK << 16 | COMMAND_COMPLETE << 8 | SAM_STAT_CHECK_CONDITION; + set_sense((u8 *) &dev->fsa_dev[cid].sense_data, + HARDWARE_ERROR, + SENCODE_INTERNAL_TARGET_FAILURE, + ASENCODE_INTERNAL_TARGET_FAILURE, 0, 0, + 0, 0); + memcpy(scsicmd->sense_buffer, &dev->fsa_dev[cid].sense_data, + (sizeof(dev->fsa_dev[cid].sense_data) > sizeof(scsicmd->sense_buffer)) + ? sizeof(scsicmd->sense_buffer) + : sizeof(dev->fsa_dev[cid].sense_data)); + scsicmd->scsi_done(scsicmd); + return 0; + } /* * Allocate and initialize a Fib then setup a BlockWrite command */ @@ -1068,8 +1219,8 @@ static int aac_write(struct scsi_cmnd * scsicmd, int cid) if (dev->raw_io_interface) { struct aac_raw_io *writecmd; writecmd = (struct aac_raw_io *) fib_data(cmd_fibcontext); - writecmd->block[0] = cpu_to_le32(lba); - writecmd->block[1] = 0; + writecmd->block[0] = cpu_to_le32((u32)(lba&0xffffffff)); + writecmd->block[1] = cpu_to_le32((u32)((lba&0xffffffff00000000LL)>>32)); writecmd->count = cpu_to_le32(count<<9); writecmd->cid = cpu_to_le16(cid); writecmd->flags = 0; @@ -1096,7 +1247,7 @@ static int aac_write(struct scsi_cmnd * scsicmd, int cid) writecmd->command = cpu_to_le32(VM_CtHostWrite64); writecmd->cid = cpu_to_le16(cid); writecmd->sector_count = cpu_to_le16(count); - writecmd->block = cpu_to_le32(lba); + writecmd->block = cpu_to_le32((u32)(lba&0xffffffff)); writecmd->pad = 0; writecmd->flags = 0; @@ -1121,7 +1272,7 @@ static int aac_write(struct scsi_cmnd * scsicmd, int cid) writecmd = (struct aac_write *) fib_data(cmd_fibcontext); writecmd->command = cpu_to_le32(VM_CtBlockWrite); writecmd->cid = cpu_to_le32(cid); - writecmd->block = cpu_to_le32(lba); + writecmd->block = cpu_to_le32((u32)(lba&0xffffffff)); writecmd->count = cpu_to_le32(count * 512); writecmd->sg.count = cpu_to_le32(1); /* ->stable is not used - it did mean which type of write */ @@ -1310,6 +1461,11 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd) */ if ((fsa_dev_ptr[cid].valid & 1) == 0) { switch (scsicmd->cmnd[0]) { + case SERVICE_ACTION_IN: + if (!(dev->raw_io_interface) || + !(dev->raw_io_64) || + ((scsicmd->cmnd[1] & 0x1f) != SAI_READ_CAPACITY_16)) + break; case INQUIRY: case READ_CAPACITY: case TEST_UNIT_READY: @@ -1375,7 +1531,6 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd) memset(&inq_data, 0, sizeof (struct inquiry_data)); inq_data.inqd_ver = 2; /* claim compliance to SCSI-2 */ - inq_data.inqd_dtq = 0x80; /* set RMB bit to one indicating that the medium is removable */ inq_data.inqd_rdf = 2; /* A response data format value of two indicates that the data shall be in the format specified in SCSI-2 */ inq_data.inqd_len = 31; /*Format for "pad2" is RelAdr | WBus32 | WBus16 | Sync | Linked |Reserved| CmdQue | SftRe */ @@ -1397,13 +1552,55 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd) aac_internal_transfer(scsicmd, &inq_data, 0, sizeof(inq_data)); return aac_get_container_name(scsicmd, cid); } + case SERVICE_ACTION_IN: + if (!(dev->raw_io_interface) || + !(dev->raw_io_64) || + ((scsicmd->cmnd[1] & 0x1f) != SAI_READ_CAPACITY_16)) + break; + { + u64 capacity; + char cp[12]; + unsigned int offset = 0; + + dprintk((KERN_DEBUG "READ CAPACITY_16 command.\n")); + capacity = fsa_dev_ptr[cid].size - 1; + if (scsicmd->cmnd[13] > 12) { + offset = scsicmd->cmnd[13] - 12; + if (offset > sizeof(cp)) + break; + memset(cp, 0, offset); + aac_internal_transfer(scsicmd, cp, 0, offset); + } + cp[0] = (capacity >> 56) & 0xff; + cp[1] = (capacity >> 48) & 0xff; + cp[2] = (capacity >> 40) & 0xff; + cp[3] = (capacity >> 32) & 0xff; + cp[4] = (capacity >> 24) & 0xff; + cp[5] = (capacity >> 16) & 0xff; + cp[6] = (capacity >> 8) & 0xff; + cp[7] = (capacity >> 0) & 0xff; + cp[8] = 0; + cp[9] = 0; + cp[10] = 2; + cp[11] = 0; + aac_internal_transfer(scsicmd, cp, offset, sizeof(cp)); + + /* Do not cache partition table for arrays */ + scsicmd->device->removable = 1; + + scsicmd->result = DID_OK << 16 | COMMAND_COMPLETE << 8 | SAM_STAT_GOOD; + scsicmd->scsi_done(scsicmd); + + return 0; + } + case READ_CAPACITY: { u32 capacity; char cp[8]; dprintk((KERN_DEBUG "READ CAPACITY command.\n")); - if (fsa_dev_ptr[cid].size <= 0x100000000LL) + if (fsa_dev_ptr[cid].size <= 0x100000000ULL) capacity = fsa_dev_ptr[cid].size - 1; else capacity = (u32)-1; @@ -1417,6 +1614,8 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd) cp[6] = 2; cp[7] = 0; aac_internal_transfer(scsicmd, cp, 0, sizeof(cp)); + /* Do not cache partition table for arrays */ + scsicmd->device->removable = 1; scsicmd->result = DID_OK << 16 | COMMAND_COMPLETE << 8 | SAM_STAT_GOOD; scsicmd->scsi_done(scsicmd); @@ -1497,6 +1696,8 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd) { case READ_6: case READ_10: + case READ_12: + case READ_16: /* * Hack to keep track of ordinal number of the device that * corresponds to a container. Needed to convert @@ -1504,17 +1705,19 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd) */ spin_unlock_irq(host->host_lock); - if (scsicmd->request->rq_disk) - memcpy(fsa_dev_ptr[cid].devname, - scsicmd->request->rq_disk->disk_name, - 8); - + if (scsicmd->request->rq_disk) + strlcpy(fsa_dev_ptr[cid].devname, + scsicmd->request->rq_disk->disk_name, + min(sizeof(fsa_dev_ptr[cid].devname), + sizeof(scsicmd->request->rq_disk->disk_name) + 1)); ret = aac_read(scsicmd, cid); spin_lock_irq(host->host_lock); return ret; case WRITE_6: case WRITE_10: + case WRITE_12: + case WRITE_16: spin_unlock_irq(host->host_lock); ret = aac_write(scsicmd, cid); spin_lock_irq(host->host_lock); @@ -1745,6 +1948,8 @@ static void aac_srb_callback(void *context, struct fib * fibptr) case WRITE_10: case READ_12: case WRITE_12: + case READ_16: + case WRITE_16: if(le32_to_cpu(srbreply->data_xfer_length) < scsicmd->underflow ) { printk(KERN_WARNING"aacraid: SCSI CMD underflow\n"); } else { @@ -1850,8 +2055,8 @@ static void aac_srb_callback(void *context, struct fib * fibptr) sizeof(scsicmd->sense_buffer) : le32_to_cpu(srbreply->sense_data_size); #ifdef AAC_DETAILED_STATUS_INFO - dprintk((KERN_WARNING "aac_srb_callback: check condition, status = %d len=%d\n", - le32_to_cpu(srbreply->status), len)); + printk(KERN_WARNING "aac_srb_callback: check condition, status = %d len=%d\n", + le32_to_cpu(srbreply->status), len); #endif memcpy(scsicmd->sense_buffer, srbreply->sense_data, len); diff --git a/drivers/scsi/aacraid/aacraid.h b/drivers/scsi/aacraid/aacraid.h index e40528185d4..6fd5074efa5 100644 --- a/drivers/scsi/aacraid/aacraid.h +++ b/drivers/scsi/aacraid/aacraid.h @@ -1,6 +1,10 @@ #if (!defined(dprintk)) # define dprintk(x) #endif +/* eg: if (nblank(dprintk(x))) */ +#define _nblank(x) #x +#define nblank(x) _nblank(x)[0] + /*------------------------------------------------------------------------------ * D E F I N E S @@ -1012,6 +1016,7 @@ struct aac_dev /* macro side-effects BEWARE */ # define raw_io_interface \ init->InitStructRevision==cpu_to_le32(ADAPTER_INIT_STRUCT_REVISION_4) + u8 raw_io_64; u8 printf_enabled; }; @@ -1362,8 +1367,10 @@ struct aac_srb_reply #define VM_CtBlockVerify64 18 #define VM_CtHostRead64 19 #define VM_CtHostWrite64 20 +#define VM_DrvErrTblLog 21 +#define VM_NameServe64 22 -#define MAX_VMCOMMAND_NUM 21 /* used for sizing stats array - leave last */ +#define MAX_VMCOMMAND_NUM 23 /* used for sizing stats array - leave last */ /* * Descriptive information (eg, vital stats) @@ -1472,6 +1479,7 @@ struct aac_mntent { manager (eg, filesystem) */ __le32 altoid; /* != oid <==> snapshot or broken mirror exists */ + __le32 capacityhigh; }; #define FSCS_NOTCLEAN 0x0001 /* fsck is neccessary before mounting */ diff --git a/drivers/scsi/aacraid/comminit.c b/drivers/scsi/aacraid/comminit.c index 75abd045328..7f11c8540ea 100644 --- a/drivers/scsi/aacraid/comminit.c +++ b/drivers/scsi/aacraid/comminit.c @@ -315,6 +315,13 @@ struct aac_dev *aac_init_adapter(struct aac_dev *dev) - sizeof(struct aac_fibhdr) - sizeof(struct aac_write) + sizeof(struct sgmap)) / sizeof(struct sgmap); + dev->raw_io_64 = 0; + if ((!aac_adapter_sync_cmd(dev, GET_ADAPTER_PROPERTIES, + 0, 0, 0, 0, 0, 0, status+0, status+1, status+2, NULL, NULL)) && + (status[0] == 0x00000001)) { + if (status[1] & AAC_OPT_NEW_COMM_64) + dev->raw_io_64 = 1; + } if ((!aac_adapter_sync_cmd(dev, GET_COMM_PREFERRED_SETTINGS, 0, 0, 0, 0, 0, 0, status+0, status+1, status+2, status+3, status+4)) diff --git a/drivers/scsi/aacraid/linit.c b/drivers/scsi/aacraid/linit.c index 4ff29d7f582..31d96b965ee 100644 --- a/drivers/scsi/aacraid/linit.c +++ b/drivers/scsi/aacraid/linit.c @@ -772,6 +772,7 @@ static int __devinit aac_probe_one(struct pci_dev *pdev, shost->irq = pdev->irq; shost->base = pci_resource_start(pdev, 0); shost->unique_id = unique_id; + shost->max_cmd_len = 16; aac = (struct aac_dev *)shost->hostdata; aac->scsi_host_ptr = shost; -- cgit v1.2.3 From 2f130980d14cb938226011875ca5224cd46dc1f9 Mon Sep 17 00:00:00 2001 From: Mark Haverkamp Date: Mon, 26 Sep 2005 13:02:15 -0700 Subject: [SCSI] aacraid: aacraid: AIF preallocation (update) Recevied from Mark Salyzyn from Adaptec. Aif pre-allocation is used to pull the kmalloc outside of the locks. Applies to the scsi-misc-2.6 git tree. Signed-off-by: Mark Haverkamp Signed-off-by: James Bottomley --- drivers/scsi/aacraid/commsup.c | 100 +++++++++++++++++++++++++++++++++-------- 1 file changed, 81 insertions(+), 19 deletions(-) diff --git a/drivers/scsi/aacraid/commsup.c b/drivers/scsi/aacraid/commsup.c index a1d303f0348..3741be2f4bf 100644 --- a/drivers/scsi/aacraid/commsup.c +++ b/drivers/scsi/aacraid/commsup.c @@ -805,7 +805,6 @@ int aac_command_thread(struct aac_dev * dev) { struct hw_fib *hw_fib, *hw_newfib; struct fib *fib, *newfib; - struct aac_queue_block *queues = dev->queues; struct aac_fib_context *fibctx; unsigned long flags; DECLARE_WAITQUEUE(wait, current); @@ -825,21 +824,22 @@ int aac_command_thread(struct aac_dev * dev) * Let the DPC know it has a place to send the AIF's to. */ dev->aif_thread = 1; - add_wait_queue(&queues->queue[HostNormCmdQueue].cmdready, &wait); + add_wait_queue(&dev->queues->queue[HostNormCmdQueue].cmdready, &wait); set_current_state(TASK_INTERRUPTIBLE); + dprintk ((KERN_INFO "aac_command_thread start\n")); while(1) { - spin_lock_irqsave(queues->queue[HostNormCmdQueue].lock, flags); - while(!list_empty(&(queues->queue[HostNormCmdQueue].cmdq))) { + spin_lock_irqsave(dev->queues->queue[HostNormCmdQueue].lock, flags); + while(!list_empty(&(dev->queues->queue[HostNormCmdQueue].cmdq))) { struct list_head *entry; struct aac_aifcmd * aifcmd; set_current_state(TASK_RUNNING); - - entry = queues->queue[HostNormCmdQueue].cmdq.next; + + entry = dev->queues->queue[HostNormCmdQueue].cmdq.next; list_del(entry); - - spin_unlock_irqrestore(queues->queue[HostNormCmdQueue].lock, flags); + + spin_unlock_irqrestore(dev->queues->queue[HostNormCmdQueue].lock, flags); fib = list_entry(entry, struct fib, fiblink); /* * We will process the FIB here or pass it to a @@ -869,9 +869,54 @@ int aac_command_thread(struct aac_dev * dev) u32 time_now, time_last; unsigned long flagv; + unsigned num; + struct hw_fib ** hw_fib_pool, ** hw_fib_p; + struct fib ** fib_pool, ** fib_p; time_now = jiffies/HZ; + /* + * Warning: no sleep allowed while + * holding spinlock. We take the estimate + * and pre-allocate a set of fibs outside the + * lock. + */ + num = le32_to_cpu(dev->init->AdapterFibsSize) + / sizeof(struct hw_fib); /* some extra */ + spin_lock_irqsave(&dev->fib_lock, flagv); + entry = dev->fib_list.next; + while (entry != &dev->fib_list) { + entry = entry->next; + ++num; + } + spin_unlock_irqrestore(&dev->fib_lock, flagv); + hw_fib_pool = NULL; + fib_pool = NULL; + if (num + && ((hw_fib_pool = kmalloc(sizeof(struct hw_fib *) * num, GFP_KERNEL))) + && ((fib_pool = kmalloc(sizeof(struct fib *) * num, GFP_KERNEL)))) { + hw_fib_p = hw_fib_pool; + fib_p = fib_pool; + while (hw_fib_p < &hw_fib_pool[num]) { + if (!(*(hw_fib_p++) = kmalloc(sizeof(struct hw_fib), GFP_KERNEL))) { + --hw_fib_p; + break; + } + if (!(*(fib_p++) = kmalloc(sizeof(struct fib), GFP_KERNEL))) { + kfree(*(--hw_fib_p)); + break; + } + } + if ((num = hw_fib_p - hw_fib_pool) == 0) { + kfree(fib_pool); + fib_pool = NULL; + kfree(hw_fib_pool); + hw_fib_pool = NULL; + } + } else if (hw_fib_pool) { + kfree(hw_fib_pool); + hw_fib_pool = NULL; + } spin_lock_irqsave(&dev->fib_lock, flagv); entry = dev->fib_list.next; /* @@ -880,6 +925,8 @@ int aac_command_thread(struct aac_dev * dev) * fib, and then set the event to wake up the * thread that is waiting for it. */ + hw_fib_p = hw_fib_pool; + fib_p = fib_pool; while (entry != &dev->fib_list) { /* * Extract the fibctx @@ -912,9 +959,11 @@ int aac_command_thread(struct aac_dev * dev) * Warning: no sleep allowed while * holding spinlock */ - hw_newfib = kmalloc(sizeof(struct hw_fib), GFP_ATOMIC); - newfib = kmalloc(sizeof(struct fib), GFP_ATOMIC); - if (newfib && hw_newfib) { + if (hw_fib_p < &hw_fib_pool[num]) { + hw_newfib = *hw_fib_p; + *(hw_fib_p++) = NULL; + newfib = *fib_p; + *(fib_p++) = NULL; /* * Make the copy of the FIB */ @@ -929,15 +978,11 @@ int aac_command_thread(struct aac_dev * dev) fibctx->count++; /* * Set the event to wake up the - * thread that will waiting. + * thread that is waiting. */ up(&fibctx->wait_sem); } else { printk(KERN_WARNING "aifd: didn't allocate NewFib.\n"); - if(newfib) - kfree(newfib); - if(hw_newfib) - kfree(hw_newfib); } entry = entry->next; } @@ -947,21 +992,38 @@ int aac_command_thread(struct aac_dev * dev) *(__le32 *)hw_fib->data = cpu_to_le32(ST_OK); fib_adapter_complete(fib, sizeof(u32)); spin_unlock_irqrestore(&dev->fib_lock, flagv); + /* Free up the remaining resources */ + hw_fib_p = hw_fib_pool; + fib_p = fib_pool; + while (hw_fib_p < &hw_fib_pool[num]) { + if (*hw_fib_p) + kfree(*hw_fib_p); + if (*fib_p) + kfree(*fib_p); + ++fib_p; + ++hw_fib_p; + } + if (hw_fib_pool) + kfree(hw_fib_pool); + if (fib_pool) + kfree(fib_pool); } - spin_lock_irqsave(queues->queue[HostNormCmdQueue].lock, flags); kfree(fib); + spin_lock_irqsave(dev->queues->queue[HostNormCmdQueue].lock, flags); } /* * There are no more AIF's */ - spin_unlock_irqrestore(queues->queue[HostNormCmdQueue].lock, flags); + spin_unlock_irqrestore(dev->queues->queue[HostNormCmdQueue].lock, flags); schedule(); if(signal_pending(current)) break; set_current_state(TASK_INTERRUPTIBLE); } - remove_wait_queue(&queues->queue[HostNormCmdQueue].cmdready, &wait); + if (dev->queues) + remove_wait_queue(&dev->queues->queue[HostNormCmdQueue].cmdready, &wait); dev->aif_thread = 0; complete_and_exit(&dev->aif_completion, 0); + return 0; } -- cgit v1.2.3 From 131256cf203d0df62014dda8453a70cb6af0d0bb Mon Sep 17 00:00:00 2001 From: Mark Haverkamp Date: Mon, 26 Sep 2005 13:04:56 -0700 Subject: [SCSI] aacraid: handle AIF hotplug events (update) Received from Mark Salyzyn from Adaptec. Hotplug sniffs the AIFs (events) from the adapter and if a container change resulting in the device going offline (container zero), online (container zero completed) or changing capacity (morph) it will take actions by calling the appropriate API. Signed-off-by: Mark Haverkamp Signed-off-by: James Bottomley --- drivers/scsi/aacraid/aachba.c | 4 +- drivers/scsi/aacraid/aacraid.h | 4 + drivers/scsi/aacraid/commsup.c | 274 ++++++++++++++++++++++++++++++++++++++++- 3 files changed, 280 insertions(+), 2 deletions(-) diff --git a/drivers/scsi/aacraid/aachba.c b/drivers/scsi/aacraid/aachba.c index 0a209b2cd69..85d133c40bd 100644 --- a/drivers/scsi/aacraid/aachba.c +++ b/drivers/scsi/aacraid/aachba.c @@ -479,7 +479,7 @@ static int aac_get_container_name(struct scsi_cmnd * scsicmd, int cid) * is updated in the struct fsa_dev_info structure rather than returned. */ -static int probe_container(struct aac_dev *dev, int cid) +int probe_container(struct aac_dev *dev, int cid) { struct fsa_dev_info *fsa_dev_ptr; int status; @@ -1471,6 +1471,8 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd) case TEST_UNIT_READY: spin_unlock_irq(host->host_lock); probe_container(dev, cid); + if ((fsa_dev_ptr[cid].valid & 1) == 0) + fsa_dev_ptr[cid].valid = 0; spin_lock_irq(host->host_lock); if (fsa_dev_ptr[cid].valid == 0) { scsicmd->result = DID_NO_CONNECT << 16; diff --git a/drivers/scsi/aacraid/aacraid.h b/drivers/scsi/aacraid/aacraid.h index 6fd5074efa5..0880f4807fc 100644 --- a/drivers/scsi/aacraid/aacraid.h +++ b/drivers/scsi/aacraid/aacraid.h @@ -780,7 +780,9 @@ struct fsa_dev_info { u64 last; u64 size; u32 type; + u32 config_waiting_on; u16 queue_depth; + u8 config_needed; u8 valid; u8 ro; u8 locked; @@ -1715,6 +1717,7 @@ extern struct aac_common aac_config; #define AifCmdJobProgress 2 /* Progress report */ #define AifJobCtrZero 101 /* Array Zero progress */ #define AifJobStsSuccess 1 /* Job completes */ +#define AifJobStsRunning 102 /* Job running */ #define AifCmdAPIReport 3 /* Report from other user of API */ #define AifCmdDriverNotify 4 /* Notify host driver of event */ #define AifDenMorphComplete 200 /* A morph operation completed */ @@ -1785,6 +1788,7 @@ int fib_adapter_complete(struct fib * fibptr, unsigned short size); struct aac_driver_ident* aac_get_driver_ident(int devtype); int aac_get_adapter_info(struct aac_dev* dev); int aac_send_shutdown(struct aac_dev *dev); +int probe_container(struct aac_dev *dev, int cid); extern int numacb; extern int acbsize; extern char aac_driver_version[]; diff --git a/drivers/scsi/aacraid/commsup.c b/drivers/scsi/aacraid/commsup.c index 3741be2f4bf..69985b08a27 100644 --- a/drivers/scsi/aacraid/commsup.c +++ b/drivers/scsi/aacraid/commsup.c @@ -39,6 +39,7 @@ #include #include #include +#include #include #include "aacraid.h" @@ -791,6 +792,268 @@ void aac_printf(struct aac_dev *dev, u32 val) memset(cp, 0, 256); } + +/** + * aac_handle_aif - Handle a message from the firmware + * @dev: Which adapter this fib is from + * @fibptr: Pointer to fibptr from adapter + * + * This routine handles a driver notify fib from the adapter and + * dispatches it to the appropriate routine for handling. + */ + +static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr) +{ + struct hw_fib * hw_fib = fibptr->hw_fib; + struct aac_aifcmd * aifcmd = (struct aac_aifcmd *)hw_fib->data; + int busy; + u32 container; + struct scsi_device *device; + enum { + NOTHING, + DELETE, + ADD, + CHANGE + } device_config_needed; + + /* Sniff for container changes */ + + if (!dev) + return; + container = (u32)-1; + + /* + * We have set this up to try and minimize the number of + * re-configures that take place. As a result of this when + * certain AIF's come in we will set a flag waiting for another + * type of AIF before setting the re-config flag. + */ + switch (le32_to_cpu(aifcmd->command)) { + case AifCmdDriverNotify: + switch (le32_to_cpu(((u32 *)aifcmd->data)[0])) { + /* + * Morph or Expand complete + */ + case AifDenMorphComplete: + case AifDenVolumeExtendComplete: + container = le32_to_cpu(((u32 *)aifcmd->data)[1]); + if (container >= dev->maximum_num_containers) + break; + + /* + * Find the Scsi_Device associated with the SCSI + * address. Make sure we have the right array, and if + * so set the flag to initiate a new re-config once we + * see an AifEnConfigChange AIF come through. + */ + + if ((dev != NULL) && (dev->scsi_host_ptr != NULL)) { + device = scsi_device_lookup(dev->scsi_host_ptr, + CONTAINER_TO_CHANNEL(container), + CONTAINER_TO_ID(container), + CONTAINER_TO_LUN(container)); + if (device) { + dev->fsa_dev[container].config_needed = CHANGE; + dev->fsa_dev[container].config_waiting_on = AifEnConfigChange; + scsi_device_put(device); + } + } + } + + /* + * If we are waiting on something and this happens to be + * that thing then set the re-configure flag. + */ + if (container != (u32)-1) { + if (container >= dev->maximum_num_containers) + break; + if (dev->fsa_dev[container].config_waiting_on == + le32_to_cpu(*(u32 *)aifcmd->data)) + dev->fsa_dev[container].config_waiting_on = 0; + } else for (container = 0; + container < dev->maximum_num_containers; ++container) { + if (dev->fsa_dev[container].config_waiting_on == + le32_to_cpu(*(u32 *)aifcmd->data)) + dev->fsa_dev[container].config_waiting_on = 0; + } + break; + + case AifCmdEventNotify: + switch (le32_to_cpu(((u32 *)aifcmd->data)[0])) { + /* + * Add an Array. + */ + case AifEnAddContainer: + container = le32_to_cpu(((u32 *)aifcmd->data)[1]); + if (container >= dev->maximum_num_containers) + break; + dev->fsa_dev[container].config_needed = ADD; + dev->fsa_dev[container].config_waiting_on = + AifEnConfigChange; + break; + + /* + * Delete an Array. + */ + case AifEnDeleteContainer: + container = le32_to_cpu(((u32 *)aifcmd->data)[1]); + if (container >= dev->maximum_num_containers) + break; + dev->fsa_dev[container].config_needed = DELETE; + dev->fsa_dev[container].config_waiting_on = + AifEnConfigChange; + break; + + /* + * Container change detected. If we currently are not + * waiting on something else, setup to wait on a Config Change. + */ + case AifEnContainerChange: + container = le32_to_cpu(((u32 *)aifcmd->data)[1]); + if (container >= dev->maximum_num_containers) + break; + if (dev->fsa_dev[container].config_waiting_on) + break; + dev->fsa_dev[container].config_needed = CHANGE; + dev->fsa_dev[container].config_waiting_on = + AifEnConfigChange; + break; + + case AifEnConfigChange: + break; + + } + + /* + * If we are waiting on something and this happens to be + * that thing then set the re-configure flag. + */ + if (container != (u32)-1) { + if (container >= dev->maximum_num_containers) + break; + if (dev->fsa_dev[container].config_waiting_on == + le32_to_cpu(*(u32 *)aifcmd->data)) + dev->fsa_dev[container].config_waiting_on = 0; + } else for (container = 0; + container < dev->maximum_num_containers; ++container) { + if (dev->fsa_dev[container].config_waiting_on == + le32_to_cpu(*(u32 *)aifcmd->data)) + dev->fsa_dev[container].config_waiting_on = 0; + } + break; + + case AifCmdJobProgress: + /* + * These are job progress AIF's. When a Clear is being + * done on a container it is initially created then hidden from + * the OS. When the clear completes we don't get a config + * change so we monitor the job status complete on a clear then + * wait for a container change. + */ + + if ((((u32 *)aifcmd->data)[1] == cpu_to_le32(AifJobCtrZero)) + && ((((u32 *)aifcmd->data)[6] == ((u32 *)aifcmd->data)[5]) + || (((u32 *)aifcmd->data)[4] == cpu_to_le32(AifJobStsSuccess)))) { + for (container = 0; + container < dev->maximum_num_containers; + ++container) { + /* + * Stomp on all config sequencing for all + * containers? + */ + dev->fsa_dev[container].config_waiting_on = + AifEnContainerChange; + dev->fsa_dev[container].config_needed = ADD; + } + } + if ((((u32 *)aifcmd->data)[1] == cpu_to_le32(AifJobCtrZero)) + && (((u32 *)aifcmd->data)[6] == 0) + && (((u32 *)aifcmd->data)[4] == cpu_to_le32(AifJobStsRunning))) { + for (container = 0; + container < dev->maximum_num_containers; + ++container) { + /* + * Stomp on all config sequencing for all + * containers? + */ + dev->fsa_dev[container].config_waiting_on = + AifEnContainerChange; + dev->fsa_dev[container].config_needed = DELETE; + } + } + break; + } + + device_config_needed = NOTHING; + for (container = 0; container < dev->maximum_num_containers; + ++container) { + if ((dev->fsa_dev[container].config_waiting_on == 0) + && (dev->fsa_dev[container].config_needed != NOTHING)) { + device_config_needed = + dev->fsa_dev[container].config_needed; + dev->fsa_dev[container].config_needed = NOTHING; + break; + } + } + if (device_config_needed == NOTHING) + return; + + /* + * If we decided that a re-configuration needs to be done, + * schedule it here on the way out the door, please close the door + * behind you. + */ + + busy = 0; + + + /* + * Find the Scsi_Device associated with the SCSI address, + * and mark it as changed, invalidating the cache. This deals + * with changes to existing device IDs. + */ + + if (!dev || !dev->scsi_host_ptr) + return; + /* + * force reload of disk info via probe_container + */ + if ((device_config_needed == CHANGE) + && (dev->fsa_dev[container].valid == 1)) + dev->fsa_dev[container].valid = 2; + if ((device_config_needed == CHANGE) || + (device_config_needed == ADD)) + probe_container(dev, container); + device = scsi_device_lookup(dev->scsi_host_ptr, + CONTAINER_TO_CHANNEL(container), + CONTAINER_TO_ID(container), + CONTAINER_TO_LUN(container)); + if (device) { + switch (device_config_needed) { + case DELETE: + scsi_remove_device(device); + break; + case CHANGE: + if (!dev->fsa_dev[container].valid) { + scsi_remove_device(device); + break; + } + scsi_rescan_device(&device->sdev_gendev); + + default: + break; + } + scsi_device_put(device); + } + if (device_config_needed == ADD) { + scsi_add_device(dev->scsi_host_ptr, + CONTAINER_TO_CHANNEL(container), + CONTAINER_TO_ID(container), + CONTAINER_TO_LUN(container)); + } + +} + /** * aac_command_thread - command processing thread * @dev: Adapter to monitor @@ -860,6 +1123,7 @@ int aac_command_thread(struct aac_dev * dev) aifcmd = (struct aac_aifcmd *) hw_fib->data; if (aifcmd->command == cpu_to_le32(AifCmdDriverNotify)) { /* Handle Driver Notify Events */ + aac_handle_aif(dev, fib); *(__le32 *)hw_fib->data = cpu_to_le32(ST_OK); fib_adapter_complete(fib, (u16)sizeof(u32)); } else { @@ -872,7 +1136,15 @@ int aac_command_thread(struct aac_dev * dev) unsigned num; struct hw_fib ** hw_fib_pool, ** hw_fib_p; struct fib ** fib_pool, ** fib_p; - + + /* Sniff events */ + if ((aifcmd->command == + cpu_to_le32(AifCmdEventNotify)) || + (aifcmd->command == + cpu_to_le32(AifCmdJobProgress))) { + aac_handle_aif(dev, fib); + } + time_now = jiffies/HZ; /* -- cgit v1.2.3 From 08efb7b6116927c8b6e0af5064448e3aa13300e6 Mon Sep 17 00:00:00 2001 From: Mark Haverkamp Date: Tue, 20 Sep 2005 12:56:36 -0700 Subject: [SCSI] aacraid: error return checking This patch adds some additional error return checking and error return value propagation during initialization. Also, the deprecation of pci_module_init with pci_register_driver along with the change in return values. Signed-off-by: Mark Haverkamp Signed-off-by: James Bottomley --- drivers/scsi/aacraid/linit.c | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/drivers/scsi/aacraid/linit.c b/drivers/scsi/aacraid/linit.c index 31d96b965ee..de8490a9283 100644 --- a/drivers/scsi/aacraid/linit.c +++ b/drivers/scsi/aacraid/linit.c @@ -748,7 +748,8 @@ static int __devinit aac_probe_one(struct pci_dev *pdev, unique_id++; } - if (pci_enable_device(pdev)) + error = pci_enable_device(pdev); + if (error) goto out; if (pci_set_dma_mask(pdev, 0xFFFFFFFFULL) || @@ -800,7 +801,9 @@ static int __devinit aac_probe_one(struct pci_dev *pdev, goto out_free_fibs; aac->maximum_num_channels = aac_drivers[index].channels; - aac_get_adapter_info(aac); + error = aac_get_adapter_info(aac); + if (error < 0) + goto out_deinit; /* * Lets override negotiations and drop the maximum SG limit to 34 @@ -928,8 +931,8 @@ static int __init aac_init(void) printk(KERN_INFO "Adaptec %s driver (%s)\n", AAC_DRIVERNAME, aac_driver_version); - error = pci_module_init(&aac_pci_driver); - if (error) + error = pci_register_driver(&aac_pci_driver); + if (error < 0) return error; aac_cfg_major = register_chrdev( 0, "aac", &aac_cfg_fops); -- cgit v1.2.3 From 9203344cb8ecc554a1d36eae6661235ed422cf59 Mon Sep 17 00:00:00 2001 From: Mark Haverkamp Date: Tue, 20 Sep 2005 12:56:50 -0700 Subject: [SCSI] aacraid: initialization timeout Received from Mark Salyzyn from Adaptec. In the rare instances where the adapter, or the motherboard, is misbehaving; driver initialization or shutdown becomes problematic. By introducing a 3 minute timeout on the first interrupt driven command during initialization, or the issuance of the adapter shutdown command during driver unload, we can resolve the lockup problems induced by common (but rare) hardware misbehaviors. The timeout during initialization, should it occur, is accompanied by a message presented to the console and the logs indicating that the user should inspect and resolve problems with interrupt routing. Signed-off-by: Mark Haverkamp Signed-off-by: James Bottomley --- drivers/scsi/aacraid/aachba.c | 2 +- drivers/scsi/aacraid/comminit.c | 2 +- drivers/scsi/aacraid/commsup.c | 30 +++++++++++++++++++++++++++++- 3 files changed, 31 insertions(+), 3 deletions(-) diff --git a/drivers/scsi/aacraid/aachba.c b/drivers/scsi/aacraid/aachba.c index 85d133c40bd..a0735a247e5 100644 --- a/drivers/scsi/aacraid/aachba.c +++ b/drivers/scsi/aacraid/aachba.c @@ -692,7 +692,7 @@ int aac_get_adapter_info(struct aac_dev* dev) fibptr, sizeof(*info), FsaNormal, - 1, 1, + -1, 1, /* First `interrupt' command uses special wait */ NULL, NULL); diff --git a/drivers/scsi/aacraid/comminit.c b/drivers/scsi/aacraid/comminit.c index 7f11c8540ea..9e054a509b4 100644 --- a/drivers/scsi/aacraid/comminit.c +++ b/drivers/scsi/aacraid/comminit.c @@ -195,7 +195,7 @@ int aac_send_shutdown(struct aac_dev * dev) fibctx, sizeof(struct aac_close), FsaNormal, - 1, 1, + -2 /* Timeout silently */, 1, NULL, NULL); if (status == 0) diff --git a/drivers/scsi/aacraid/commsup.c b/drivers/scsi/aacraid/commsup.c index 69985b08a27..3b983f3ed96 100644 --- a/drivers/scsi/aacraid/commsup.c +++ b/drivers/scsi/aacraid/commsup.c @@ -41,6 +41,7 @@ #include #include #include +#include #include "aacraid.h" @@ -541,7 +542,34 @@ int fib_send(u16 command, struct fib * fibptr, unsigned long size, int priority if (wait) { spin_unlock_irqrestore(&fibptr->event_lock, flags); - down(&fibptr->event_wait); + /* Only set for first known interruptable command */ + if (wait < 0) { + /* + * *VERY* Dangerous to time out a command, the + * assumption is made that we have no hope of + * functioning because an interrupt routing or other + * hardware failure has occurred. + */ + unsigned long count = 36000000L; /* 3 minutes */ + unsigned long qflags; + while (down_trylock(&fibptr->event_wait)) { + if (--count == 0) { + spin_lock_irqsave(q->lock, qflags); + q->numpending--; + list_del(&fibptr->queue); + spin_unlock_irqrestore(q->lock, qflags); + if (wait == -1) { + printk(KERN_ERR "aacraid: fib_send: first asynchronous command timed out.\n" + "Usually a result of a PCI interrupt routing problem;\n" + "update mother board BIOS or consider utilizing one of\n" + "the SAFE mode kernel options (acpi, apic etc)\n"); + } + return -ETIMEDOUT; + } + udelay(5); + } + } else + down(&fibptr->event_wait); if(fibptr->done == 0) BUG(); -- cgit v1.2.3 From 63a70eeaafe0e17e7f45cba495cb457d06070419 Mon Sep 17 00:00:00 2001 From: Mark Haverkamp Date: Tue, 20 Sep 2005 12:57:04 -0700 Subject: [SCSI] aacraid: fib size math fix Received from Mark Salyzyn from Adaptec. The size of the command packet's scatter gather list maximum size was miscalculated in the low range leading to the driver initialization limiting the maximum i/o size that could go to the Adapter. There were no negative operational side effects resulting from this bad math, only a subtle limit in performance of the Adapter at the top end of the range. Signed-off-by: Mark Haverkamp Signed-off-by: James Bottomley --- drivers/scsi/aacraid/aachba.c | 8 ++++---- drivers/scsi/aacraid/comminit.c | 8 ++++---- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/scsi/aacraid/aachba.c b/drivers/scsi/aacraid/aachba.c index a0735a247e5..93416f760e5 100644 --- a/drivers/scsi/aacraid/aachba.c +++ b/drivers/scsi/aacraid/aachba.c @@ -843,8 +843,8 @@ int aac_get_adapter_info(struct aac_dev* dev) if (!(dev->raw_io_interface)) { dev->scsi_host_ptr->sg_tablesize = (dev->max_fib_size - sizeof(struct aac_fibhdr) - - sizeof(struct aac_write) + sizeof(struct sgmap)) / - sizeof(struct sgmap); + sizeof(struct aac_write) + sizeof(struct sgentry)) / + sizeof(struct sgentry); if (dev->dac_support) { /* * 38 scatter gather elements @@ -853,8 +853,8 @@ int aac_get_adapter_info(struct aac_dev* dev) (dev->max_fib_size - sizeof(struct aac_fibhdr) - sizeof(struct aac_write64) + - sizeof(struct sgmap64)) / - sizeof(struct sgmap64); + sizeof(struct sgentry64)) / + sizeof(struct sgentry64); } dev->scsi_host_ptr->max_sectors = AAC_MAX_32BIT_SGBCOUNT; if(!(dev->adapter_info.options & AAC_OPT_NEW_COMM)) { diff --git a/drivers/scsi/aacraid/comminit.c b/drivers/scsi/aacraid/comminit.c index 9e054a509b4..59a341b2aed 100644 --- a/drivers/scsi/aacraid/comminit.c +++ b/drivers/scsi/aacraid/comminit.c @@ -313,8 +313,8 @@ struct aac_dev *aac_init_adapter(struct aac_dev *dev) dev->max_fib_size = sizeof(struct hw_fib); dev->sg_tablesize = host->sg_tablesize = (dev->max_fib_size - sizeof(struct aac_fibhdr) - - sizeof(struct aac_write) + sizeof(struct sgmap)) - / sizeof(struct sgmap); + - sizeof(struct aac_write) + sizeof(struct sgentry)) + / sizeof(struct sgentry); dev->raw_io_64 = 0; if ((!aac_adapter_sync_cmd(dev, GET_ADAPTER_PROPERTIES, 0, 0, 0, 0, 0, 0, status+0, status+1, status+2, NULL, NULL)) && @@ -349,8 +349,8 @@ struct aac_dev *aac_init_adapter(struct aac_dev *dev) dev->max_fib_size = 512; dev->sg_tablesize = host->sg_tablesize = (512 - sizeof(struct aac_fibhdr) - - sizeof(struct aac_write) + sizeof(struct sgmap)) - / sizeof(struct sgmap); + - sizeof(struct aac_write) + sizeof(struct sgentry)) + / sizeof(struct sgentry); host->can_queue = AAC_NUM_IO_FIB; } else if (acbsize == 2048) { host->max_sectors = 512; -- cgit v1.2.3 From 1640a2c385a860ef25be4a8d18a528c4b6f02bd6 Mon Sep 17 00:00:00 2001 From: Mark Haverkamp Date: Tue, 20 Sep 2005 12:57:11 -0700 Subject: [SCSI] aacraid: remove aac_insert_entry Received from Mark Salyzyn from Adaptec. High Priority Queues have *never* been used in the entire history of the aac based adapters. Associated with this, aac_insert_entry can be removed, SavedIrql can be removed & padding variable can be removed. With the movement of SavedIrql out & replaced with an automatic variable qflags, the locking can be refined somewhat. The sparse warnings did not catch the need for byte swapping in the 'dprintk' debugging print macros, so fixed this up when this code was moved outside of the now refined locking. Signed-off-by: Mark Haverkamp Signed-off-by: James Bottomley --- drivers/scsi/aacraid/aacraid.h | 3 - drivers/scsi/aacraid/commsup.c | 177 ++++++++++++----------------------------- 2 files changed, 50 insertions(+), 130 deletions(-) diff --git a/drivers/scsi/aacraid/aacraid.h b/drivers/scsi/aacraid/aacraid.h index 0880f4807fc..4a99d2f000f 100644 --- a/drivers/scsi/aacraid/aacraid.h +++ b/drivers/scsi/aacraid/aacraid.h @@ -306,7 +306,6 @@ enum aac_queue_types { */ #define FsaNormal 1 -#define FsaHigh 2 /* * Define the FIB. The FIB is the where all the requested data and @@ -550,8 +549,6 @@ struct aac_queue { /* This is only valid for adapter to host command queues. */ spinlock_t *lock; /* Spinlock for this queue must take this lock before accessing the lock */ spinlock_t lockdata; /* Actual lock (used only on one side of the lock) */ - unsigned long SavedIrql; /* Previous IRQL when the spin lock is taken */ - u32 padding; /* Padding - FIXME - can remove I believe */ struct list_head cmdq; /* A queue of FIBs which need to be prcessed by the FS thread. This is */ /* only valid for command queues which receive entries from the adapter. */ struct list_head pendingq; /* A queue of outstanding fib's to the adapter. */ diff --git a/drivers/scsi/aacraid/commsup.c b/drivers/scsi/aacraid/commsup.c index 3b983f3ed96..e4d543a474a 100644 --- a/drivers/scsi/aacraid/commsup.c +++ b/drivers/scsi/aacraid/commsup.c @@ -271,40 +271,22 @@ static int aac_get_entry (struct aac_dev * dev, u32 qid, struct aac_entry **entr /* Interrupt Moderation, only interrupt for first two entries */ if (idx != le32_to_cpu(*(q->headers.consumer))) { if (--idx == 0) { - if (qid == AdapHighCmdQueue) - idx = ADAP_HIGH_CMD_ENTRIES; - else if (qid == AdapNormCmdQueue) + if (qid == AdapNormCmdQueue) idx = ADAP_NORM_CMD_ENTRIES; - else if (qid == AdapHighRespQueue) - idx = ADAP_HIGH_RESP_ENTRIES; - else if (qid == AdapNormRespQueue) + else idx = ADAP_NORM_RESP_ENTRIES; } if (idx != le32_to_cpu(*(q->headers.consumer))) *nonotify = 1; } - if (qid == AdapHighCmdQueue) { - if (*index >= ADAP_HIGH_CMD_ENTRIES) - *index = 0; - } else if (qid == AdapNormCmdQueue) { + if (qid == AdapNormCmdQueue) { if (*index >= ADAP_NORM_CMD_ENTRIES) *index = 0; /* Wrap to front of the Producer Queue. */ - } - else if (qid == AdapHighRespQueue) - { - if (*index >= ADAP_HIGH_RESP_ENTRIES) - *index = 0; - } - else if (qid == AdapNormRespQueue) - { + } else { if (*index >= ADAP_NORM_RESP_ENTRIES) *index = 0; /* Wrap to front of the Producer Queue. */ } - else { - printk("aacraid: invalid qid\n"); - BUG(); - } if ((*index + 1) == le32_to_cpu(*(q->headers.consumer))) { /* Queue is full */ printk(KERN_WARNING "Queue %d full, %u outstanding.\n", @@ -336,12 +318,8 @@ static int aac_queue_get(struct aac_dev * dev, u32 * index, u32 qid, struct hw_f { struct aac_entry * entry = NULL; int map = 0; - struct aac_queue * q = &dev->queues->queue[qid]; - - spin_lock_irqsave(q->lock, q->SavedIrql); - if (qid == AdapHighCmdQueue || qid == AdapNormCmdQueue) - { + if (qid == AdapNormCmdQueue) { /* if no entries wait for some if caller wants to */ while (!aac_get_entry(dev, qid, &entry, index, nonotify)) { @@ -352,9 +330,7 @@ static int aac_queue_get(struct aac_dev * dev, u32 * index, u32 qid, struct hw_f */ entry->size = cpu_to_le32(le16_to_cpu(hw_fib->header.Size)); map = 1; - } - else if (qid == AdapHighRespQueue || qid == AdapNormRespQueue) - { + } else { while(!aac_get_entry(dev, qid, &entry, index, nonotify)) { /* if no entries wait for some if caller wants to */ @@ -377,42 +353,6 @@ static int aac_queue_get(struct aac_dev * dev, u32 * index, u32 qid, struct hw_f return 0; } - -/** - * aac_insert_entry - insert a queue entry - * @dev: Adapter - * @index: Index of entry to insert - * @qid: Queue number - * @nonotify: Suppress adapter notification - * - * Gets the next free QE off the requested priorty adapter command - * queue and associates the Fib with the QE. The QE represented by - * index is ready to insert on the queue when this routine returns - * success. - */ - -static int aac_insert_entry(struct aac_dev * dev, u32 index, u32 qid, unsigned long nonotify) -{ - struct aac_queue * q = &dev->queues->queue[qid]; - - if(q == NULL) - BUG(); - *(q->headers.producer) = cpu_to_le32(index + 1); - spin_unlock_irqrestore(q->lock, q->SavedIrql); - - if (qid == AdapHighCmdQueue || - qid == AdapNormCmdQueue || - qid == AdapHighRespQueue || - qid == AdapNormRespQueue) - { - if (!nonotify) - aac_adapter_notify(dev, qid); - } - else - printk("Suprise insert!\n"); - return 0; -} - /* * Define the highest level of host to adapter communication routines. * These routines will support host to adapter FS commuication. These @@ -441,12 +381,13 @@ static int aac_insert_entry(struct aac_dev * dev, u32 index, u32 qid, unsigned l int fib_send(u16 command, struct fib * fibptr, unsigned long size, int priority, int wait, int reply, fib_callback callback, void * callback_data) { u32 index; - u32 qid; struct aac_dev * dev = fibptr->dev; unsigned long nointr = 0; struct hw_fib * hw_fib = fibptr->hw_fib; struct aac_queue * q; unsigned long flags = 0; + unsigned long qflags; + if (!(hw_fib->header.XferState & cpu_to_le32(HostOwned))) return -EBUSY; /* @@ -499,26 +440,8 @@ int fib_send(u16 command, struct fib * fibptr, unsigned long size, int priority * Get a queue entry connect the FIB to it and send an notify * the adapter a command is ready. */ - if (priority == FsaHigh) { - hw_fib->header.XferState |= cpu_to_le32(HighPriority); - qid = AdapHighCmdQueue; - } else { - hw_fib->header.XferState |= cpu_to_le32(NormalPriority); - qid = AdapNormCmdQueue; - } - q = &dev->queues->queue[qid]; + hw_fib->header.XferState |= cpu_to_le32(NormalPriority); - if(wait) - spin_lock_irqsave(&fibptr->event_lock, flags); - if(aac_queue_get( dev, &index, qid, hw_fib, 1, fibptr, &nointr)<0) - return -EWOULDBLOCK; - dprintk((KERN_DEBUG "fib_send: inserting a queue entry at index %d.\n",index)); - dprintk((KERN_DEBUG "Fib contents:.\n")); - dprintk((KERN_DEBUG " Command = %d.\n", hw_fib->header.Command)); - dprintk((KERN_DEBUG " XferState = %x.\n", hw_fib->header.XferState)); - dprintk((KERN_DEBUG " hw_fib va being sent=%p\n",fibptr->hw_fib)); - dprintk((KERN_DEBUG " hw_fib pa being sent=%lx\n",(ulong)fibptr->hw_fib_pa)); - dprintk((KERN_DEBUG " fib being sent=%p\n",fibptr)); /* * Fill in the Callback and CallbackContext if we are not * going to wait. @@ -527,15 +450,33 @@ int fib_send(u16 command, struct fib * fibptr, unsigned long size, int priority fibptr->callback = callback; fibptr->callback_data = callback_data; } - FIB_COUNTER_INCREMENT(aac_config.FibsSent); - list_add_tail(&fibptr->queue, &q->pendingq); - q->numpending++; fibptr->done = 0; fibptr->flags = 0; - if(aac_insert_entry(dev, index, qid, (nointr & aac_config.irq_mod)) < 0) - return -EWOULDBLOCK; + FIB_COUNTER_INCREMENT(aac_config.FibsSent); + + dprintk((KERN_DEBUG "fib_send: inserting a queue entry at index %d.\n",index)); + dprintk((KERN_DEBUG "Fib contents:.\n")); + dprintk((KERN_DEBUG " Command = %d.\n", hw_fib->header.Command)); + dprintk((KERN_DEBUG " XferState = %x.\n", hw_fib->header.XferState)); + dprintk((KERN_DEBUG " hw_fib va being sent=%p\n",fibptr->hw_fib)); + dprintk((KERN_DEBUG " hw_fib pa being sent=%lx\n",(ulong)fibptr->hw_fib_pa)); + dprintk((KERN_DEBUG " fib being sent=%p\n",fibptr)); + + q = &dev->queues->queue[AdapNormCmdQueue]; + + if(wait) + spin_lock_irqsave(&fibptr->event_lock, flags); + spin_lock_irqsave(q->lock, qflags); + aac_queue_get( dev, &index, AdapNormCmdQueue, hw_fib, 1, fibptr, &nointr); + + list_add_tail(&fibptr->queue, &q->pendingq); + q->numpending++; + *(q->headers.producer) = cpu_to_le32(index + 1); + spin_unlock_irqrestore(q->lock, qflags); + if (!(nointr & aac_config.irq_mod)) + aac_adapter_notify(dev, AdapNormCmdQueue); /* * If the caller wanted us to wait for response wait now. */ @@ -651,15 +592,9 @@ void aac_consumer_free(struct aac_dev * dev, struct aac_queue *q, u32 qid) case HostNormCmdQueue: notify = HostNormCmdNotFull; break; - case HostHighCmdQueue: - notify = HostHighCmdNotFull; - break; case HostNormRespQueue: notify = HostNormRespNotFull; break; - case HostHighRespQueue: - notify = HostHighRespNotFull; - break; default: BUG(); return; @@ -681,9 +616,13 @@ int fib_adapter_complete(struct fib * fibptr, unsigned short size) { struct hw_fib * hw_fib = fibptr->hw_fib; struct aac_dev * dev = fibptr->dev; + struct aac_queue * q; unsigned long nointr = 0; - if (hw_fib->header.XferState == 0) + unsigned long qflags; + + if (hw_fib->header.XferState == 0) { return 0; + } /* * If we plan to do anything check the structure type first. */ @@ -698,37 +637,21 @@ int fib_adapter_complete(struct fib * fibptr, unsigned short size) * send the completed cdb to the adapter. */ if (hw_fib->header.XferState & cpu_to_le32(SentFromAdapter)) { + u32 index; hw_fib->header.XferState |= cpu_to_le32(HostProcessed); - if (hw_fib->header.XferState & cpu_to_le32(HighPriority)) { - u32 index; - if (size) - { - size += sizeof(struct aac_fibhdr); - if (size > le16_to_cpu(hw_fib->header.SenderSize)) - return -EMSGSIZE; - hw_fib->header.Size = cpu_to_le16(size); - } - if(aac_queue_get(dev, &index, AdapHighRespQueue, hw_fib, 1, NULL, &nointr) < 0) { - return -EWOULDBLOCK; - } - if (aac_insert_entry(dev, index, AdapHighRespQueue, (nointr & (int)aac_config.irq_mod)) != 0) { - } - } else if (hw_fib->header.XferState & - cpu_to_le32(NormalPriority)) { - u32 index; - - if (size) { - size += sizeof(struct aac_fibhdr); - if (size > le16_to_cpu(hw_fib->header.SenderSize)) - return -EMSGSIZE; - hw_fib->header.Size = cpu_to_le16(size); - } - if (aac_queue_get(dev, &index, AdapNormRespQueue, hw_fib, 1, NULL, &nointr) < 0) - return -EWOULDBLOCK; - if (aac_insert_entry(dev, index, AdapNormRespQueue, (nointr & (int)aac_config.irq_mod)) != 0) - { - } + if (size) { + size += sizeof(struct aac_fibhdr); + if (size > le16_to_cpu(hw_fib->header.SenderSize)) + return -EMSGSIZE; + hw_fib->header.Size = cpu_to_le16(size); } + q = &dev->queues->queue[AdapNormRespQueue]; + spin_lock_irqsave(q->lock, qflags); + aac_queue_get(dev, &index, AdapNormRespQueue, hw_fib, 1, NULL, &nointr); + *(q->headers.producer) = cpu_to_le32(index + 1); + spin_unlock_irqrestore(q->lock, qflags); + if (!(nointr & (int)aac_config.irq_mod)) + aac_adapter_notify(dev, AdapNormRespQueue); } else { -- cgit v1.2.3 From bc8dfcb93970ad7139c976356bfc99d7e251deaf Mon Sep 17 00:00:00 2001 From: Daniel Phillips Date: Tue, 27 Sep 2005 15:22:35 -0700 Subject: [NET]: Use non-recursive algorithm in skb_copy_datagram_iovec() Use iteration instead of recursion. Fraglists within fraglists should never occur, so we BUG check this. Signed-off-by: Daniel Phillips Signed-off-by: David S. Miller --- net/core/datagram.c | 81 +++++++++++++++++------------------------------------ 1 file changed, 26 insertions(+), 55 deletions(-) diff --git a/net/core/datagram.c b/net/core/datagram.c index da9bf71421a..81987df536e 100644 --- a/net/core/datagram.c +++ b/net/core/datagram.c @@ -211,74 +211,45 @@ void skb_free_datagram(struct sock *sk, struct sk_buff *skb) int skb_copy_datagram_iovec(const struct sk_buff *skb, int offset, struct iovec *to, int len) { - int start = skb_headlen(skb); - int i, copy = start - offset; - - /* Copy header. */ - if (copy > 0) { - if (copy > len) - copy = len; - if (memcpy_toiovec(to, skb->data + offset, copy)) - goto fault; - if ((len -= copy) == 0) - return 0; - offset += copy; - } + int i, err, fraglen, end = 0; + struct sk_buff *next = skb_shinfo(skb)->frag_list; +next_skb: + fraglen = skb_headlen(skb); + i = -1; - /* Copy paged appendix. Hmm... why does this look so complicated? */ - for (i = 0; i < skb_shinfo(skb)->nr_frags; i++) { - int end; - - BUG_TRAP(start <= offset + len); + while (1) { + int start = end; - end = start + skb_shinfo(skb)->frags[i].size; - if ((copy = end - offset) > 0) { - int err; - u8 *vaddr; - skb_frag_t *frag = &skb_shinfo(skb)->frags[i]; - struct page *page = frag->page; + if ((end += fraglen) > offset) { + int copy = end - offset, o = offset - start; if (copy > len) copy = len; - vaddr = kmap(page); - err = memcpy_toiovec(to, vaddr + frag->page_offset + - offset - start, copy); - kunmap(page); + if (i == -1) + err = memcpy_toiovec(to, skb->data + o, copy); + else { + skb_frag_t *frag = &skb_shinfo(skb)->frags[i]; + struct page *page = frag->page; + void *p = kmap(page) + frag->page_offset + o; + err = memcpy_toiovec(to, p, copy); + kunmap(page); + } if (err) goto fault; if (!(len -= copy)) return 0; offset += copy; } - start = end; + if (++i >= skb_shinfo(skb)->nr_frags) + break; + fraglen = skb_shinfo(skb)->frags[i].size; } - - if (skb_shinfo(skb)->frag_list) { - struct sk_buff *list = skb_shinfo(skb)->frag_list; - - for (; list; list = list->next) { - int end; - - BUG_TRAP(start <= offset + len); - - end = start + list->len; - if ((copy = end - offset) > 0) { - if (copy > len) - copy = len; - if (skb_copy_datagram_iovec(list, - offset - start, - to, copy)) - goto fault; - if ((len -= copy) == 0) - return 0; - offset += copy; - } - start = end; - } + if (next) { + skb = next; + BUG_ON(skb_shinfo(skb)->frag_list); + next = skb->next; + goto next_skb; } - if (!len) - return 0; - fault: return -EFAULT; } -- cgit v1.2.3 From 2d7ceece08ad940d0ceac98ab1b5a3b82dfc2a0a Mon Sep 17 00:00:00 2001 From: Eric Dumazet Date: Tue, 27 Sep 2005 15:22:58 -0700 Subject: [NET]: Prefetch dev->qdisc_lock in dev_queue_xmit() We know the lock is going to be taken. Signed-off-by: Eric Dumazet Signed-off-by: David S. Miller --- net/core/dev.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/net/core/dev.c b/net/core/dev.c index 37c88107096..9066c874e27 100644 --- a/net/core/dev.c +++ b/net/core/dev.c @@ -1259,6 +1259,8 @@ int dev_queue_xmit(struct sk_buff *skb) if (skb_checksum_help(skb, 0)) goto out_kfree_skb; + spin_lock_prefetch(&dev->queue_lock); + /* Disable soft irqs for various locks below. Also * stops preemption for RCU. */ -- cgit v1.2.3 From 9356b8fc07dc126cd91d2b12f314d760ab48996e Mon Sep 17 00:00:00 2001 From: Eric Dumazet Date: Tue, 27 Sep 2005 15:23:16 -0700 Subject: [NET]: Reorder some hot fields of struct net_device Place them on separate cache lines in SMP to lower memory bouncing between multiple CPU accessing the device. - One part is mostly used on receive path (including eth_type_trans()) (poll_list, poll, quota, weight, last_rx, dev_addr, broadcast) - One part is mostly used on queue transmit path (qdisc) (queue_lock, qdisc, qdisc_sleeping, qdisc_list, tx_queue_len) - One part is mostly used on xmit path (device) (xmit_lock, xmit_lock_owner, priv, hard_start_xmit, trans_start) 'features' is placed outside of these hot points, in a location that may be shared by all cpus (because mostly read) name_hlist is moved close to name[IFNAMSIZ] to speedup __dev_get_by_name() Signed-off-by: Eric Dumazet Signed-off-by: David S. Miller --- include/linux/netdevice.h | 89 +++++++++++++++++++++++++++++------------------ 1 file changed, 55 insertions(+), 34 deletions(-) diff --git a/include/linux/netdevice.h b/include/linux/netdevice.h index 7c717907896..368e4c825ff 100644 --- a/include/linux/netdevice.h +++ b/include/linux/netdevice.h @@ -265,6 +265,8 @@ struct net_device * the interface. */ char name[IFNAMSIZ]; + /* device name hash chain */ + struct hlist_node name_hlist; /* * I/O specific fields @@ -292,6 +294,21 @@ struct net_device /* ------- Fields preinitialized in Space.c finish here ------- */ + /* Net device features */ + unsigned long features; +#define NETIF_F_SG 1 /* Scatter/gather IO. */ +#define NETIF_F_IP_CSUM 2 /* Can checksum only TCP/UDP over IPv4. */ +#define NETIF_F_NO_CSUM 4 /* Does not require checksum. F.e. loopack. */ +#define NETIF_F_HW_CSUM 8 /* Can checksum all the packets. */ +#define NETIF_F_HIGHDMA 32 /* Can DMA to high memory. */ +#define NETIF_F_FRAGLIST 64 /* Scatter/gather IO. */ +#define NETIF_F_HW_VLAN_TX 128 /* Transmit VLAN hw acceleration */ +#define NETIF_F_HW_VLAN_RX 256 /* Receive VLAN hw acceleration */ +#define NETIF_F_HW_VLAN_FILTER 512 /* Receive filtering on VLAN */ +#define NETIF_F_VLAN_CHALLENGED 1024 /* Device cannot handle VLAN packets */ +#define NETIF_F_TSO 2048 /* Can offload TCP/IP segmentation */ +#define NETIF_F_LLTX 4096 /* LockLess TX */ + struct net_device *next_sched; /* Interface index. Unique device identifier */ @@ -316,9 +333,6 @@ struct net_device * will (read: may be cleaned up at will). */ - /* These may be needed for future network-power-down code. */ - unsigned long trans_start; /* Time (in jiffies) of last Tx */ - unsigned long last_rx; /* Time of last Rx */ unsigned short flags; /* interface flags (a la BSD) */ unsigned short gflags; @@ -328,15 +342,12 @@ struct net_device unsigned mtu; /* interface MTU value */ unsigned short type; /* interface hardware type */ unsigned short hard_header_len; /* hardware hdr length */ - void *priv; /* pointer to private data */ struct net_device *master; /* Pointer to master device of a group, * which this device is member of. */ /* Interface address info. */ - unsigned char broadcast[MAX_ADDR_LEN]; /* hw bcast add */ - unsigned char dev_addr[MAX_ADDR_LEN]; /* hw address */ unsigned char perm_addr[MAX_ADDR_LEN]; /* permanent hw address */ unsigned char addr_len; /* hardware address length */ unsigned short dev_id; /* for shared network cards */ @@ -346,8 +357,6 @@ struct net_device int promiscuity; int allmulti; - int watchdog_timeo; - struct timer_list watchdog_timer; /* Protocol specific pointers */ @@ -358,32 +367,62 @@ struct net_device void *ec_ptr; /* Econet specific data */ void *ax25_ptr; /* AX.25 specific data */ - struct list_head poll_list; /* Link to poll list */ +/* + * Cache line mostly used on receive path (including eth_type_trans()) + */ + struct list_head poll_list ____cacheline_aligned_in_smp; + /* Link to poll list */ + + int (*poll) (struct net_device *dev, int *quota); int quota; int weight; + unsigned long last_rx; /* Time of last Rx */ + /* Interface address info used in eth_type_trans() */ + unsigned char dev_addr[MAX_ADDR_LEN]; /* hw address, (before bcast + because most packets are unicast) */ + + unsigned char broadcast[MAX_ADDR_LEN]; /* hw bcast add */ +/* + * Cache line mostly used on queue transmit path (qdisc) + */ + /* device queue lock */ + spinlock_t queue_lock ____cacheline_aligned_in_smp; struct Qdisc *qdisc; struct Qdisc *qdisc_sleeping; - struct Qdisc *qdisc_ingress; struct list_head qdisc_list; unsigned long tx_queue_len; /* Max frames per queue allowed */ /* ingress path synchronizer */ spinlock_t ingress_lock; + struct Qdisc *qdisc_ingress; + +/* + * One part is mostly used on xmit path (device) + */ /* hard_start_xmit synchronizer */ - spinlock_t xmit_lock; + spinlock_t xmit_lock ____cacheline_aligned_in_smp; /* cpu id of processor entered to hard_start_xmit or -1, if nobody entered there. */ int xmit_lock_owner; - /* device queue lock */ - spinlock_t queue_lock; + void *priv; /* pointer to private data */ + int (*hard_start_xmit) (struct sk_buff *skb, + struct net_device *dev); + /* These may be needed for future network-power-down code. */ + unsigned long trans_start; /* Time (in jiffies) of last Tx */ + + int watchdog_timeo; /* used by dev_watchdog() */ + struct timer_list watchdog_timer; + +/* + * refcnt is a very hot point, so align it on SMP + */ /* Number of references to this device */ - atomic_t refcnt; + atomic_t refcnt ____cacheline_aligned_in_smp; + /* delayed register/unregister */ struct list_head todo_list; - /* device name hash chain */ - struct hlist_node name_hlist; /* device index hash chain */ struct hlist_node index_hlist; @@ -396,21 +435,6 @@ struct net_device NETREG_RELEASED, /* called free_netdev */ } reg_state; - /* Net device features */ - unsigned long features; -#define NETIF_F_SG 1 /* Scatter/gather IO. */ -#define NETIF_F_IP_CSUM 2 /* Can checksum only TCP/UDP over IPv4. */ -#define NETIF_F_NO_CSUM 4 /* Does not require checksum. F.e. loopack. */ -#define NETIF_F_HW_CSUM 8 /* Can checksum all the packets. */ -#define NETIF_F_HIGHDMA 32 /* Can DMA to high memory. */ -#define NETIF_F_FRAGLIST 64 /* Scatter/gather IO. */ -#define NETIF_F_HW_VLAN_TX 128 /* Transmit VLAN hw acceleration */ -#define NETIF_F_HW_VLAN_RX 256 /* Receive VLAN hw acceleration */ -#define NETIF_F_HW_VLAN_FILTER 512 /* Receive filtering on VLAN */ -#define NETIF_F_VLAN_CHALLENGED 1024 /* Device cannot handle VLAN packets */ -#define NETIF_F_TSO 2048 /* Can offload TCP/IP segmentation */ -#define NETIF_F_LLTX 4096 /* LockLess TX */ - /* Called after device is detached from network. */ void (*uninit)(struct net_device *dev); /* Called after last user reference disappears. */ @@ -419,10 +443,7 @@ struct net_device /* Pointers to interface service routines. */ int (*open)(struct net_device *dev); int (*stop)(struct net_device *dev); - int (*hard_start_xmit) (struct sk_buff *skb, - struct net_device *dev); #define HAVE_NETDEV_POLL - int (*poll) (struct net_device *dev, int *quota); int (*hard_header) (struct sk_buff *skb, struct net_device *dev, unsigned short type, -- cgit v1.2.3 From a79af59efd20990473d579b1d8d70bb120f0920c Mon Sep 17 00:00:00 2001 From: Frank Filz Date: Tue, 27 Sep 2005 15:23:38 -0700 Subject: [NET]: Fix module reference counts for loadable protocol modules I have been experimenting with loadable protocol modules, and ran into several issues with module reference counting. The first issue was that __module_get failed at the BUG_ON check at the top of the routine (checking that my module reference count was not zero) when I created the first socket. When sk_alloc() is called, my module reference count was still 0. When I looked at why sctp didn't have this problem, I discovered that sctp creates a control socket during module init (when the module ref count is not 0), which keeps the reference count non-zero. This section has been updated to address the point Stephen raised about checking the return value of try_module_get(). The next problem arose when my socket init routine returned an error. This resulted in my module reference count being decremented below 0. My socket ops->release routine was also being called. The issue here is that sock_release() calls the ops->release routine and decrements the ref count if sock->ops is not NULL. Since the socket probably didn't get correctly initialized, this should not be done, so we will set sock->ops to NULL because we will not call try_module_get(). While searching for another bug, I also noticed that sys_accept() has a possibility of doing a module_put() when it did not do an __module_get so I re-ordered the call to security_socket_accept(). Signed-off-by: Frank Filz Signed-off-by: David S. Miller --- net/core/sock.c | 20 ++++++++++++-------- net/socket.c | 13 ++++++++----- 2 files changed, 20 insertions(+), 13 deletions(-) diff --git a/net/core/sock.c b/net/core/sock.c index ac63b56e23b..928d2a1d6d8 100644 --- a/net/core/sock.c +++ b/net/core/sock.c @@ -660,16 +660,20 @@ struct sock *sk_alloc(int family, unsigned int __nocast priority, sock_lock_init(sk); } - if (security_sk_alloc(sk, family, priority)) { - if (slab != NULL) - kmem_cache_free(slab, sk); - else - kfree(sk); - sk = NULL; - } else - __module_get(prot->owner); + if (security_sk_alloc(sk, family, priority)) + goto out_free; + + if (!try_module_get(prot->owner)) + goto out_free; } return sk; + +out_free: + if (slab != NULL) + kmem_cache_free(slab, sk); + else + kfree(sk); + return NULL; } void sk_free(struct sock *sk) diff --git a/net/socket.c b/net/socket.c index dbd1a6851ed..3145103cdf5 100644 --- a/net/socket.c +++ b/net/socket.c @@ -1145,8 +1145,11 @@ static int __sock_create(int family, int type, int protocol, struct socket **res if (!try_module_get(net_families[family]->owner)) goto out_release; - if ((err = net_families[family]->create(sock, protocol)) < 0) + if ((err = net_families[family]->create(sock, protocol)) < 0) { + sock->ops = NULL; goto out_module_put; + } + /* * Now to bump the refcnt of the [loadable] module that owns this * socket at sock_release time we decrement its refcnt. @@ -1360,16 +1363,16 @@ asmlinkage long sys_accept(int fd, struct sockaddr __user *upeer_sockaddr, int _ newsock->type = sock->type; newsock->ops = sock->ops; - err = security_socket_accept(sock, newsock); - if (err) - goto out_release; - /* * We don't need try_module_get here, as the listening socket (sock) * has the protocol module (sock->ops->owner) held. */ __module_get(newsock->ops->owner); + err = security_socket_accept(sock, newsock); + if (err) + goto out_release; + err = sock->ops->accept(sock, newsock, sock->file->f_flags); if (err < 0) goto out_release; -- cgit v1.2.3 From 1f26dac32057baaf67d10b45c6b5277db862911d Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Tue, 27 Sep 2005 15:24:13 -0700 Subject: [NET]: Add Sun Cassini driver. Written by Adrian Sun (asun@darksunrising.com). Ported to 2.6.x by Tom 'spot' Callaway . Further cleaned up and integrated by David S. Miller Signed-off-by: David S. Miller --- drivers/net/Kconfig | 8 + drivers/net/Makefile | 1 + drivers/net/cassini.c | 5311 +++++++++++++++++++++++++++++++++++++++++++++++ drivers/net/cassini.h | 4425 +++++++++++++++++++++++++++++++++++++++ include/linux/pci_ids.h | 2 + 5 files changed, 9747 insertions(+) create mode 100644 drivers/net/cassini.c create mode 100644 drivers/net/cassini.h diff --git a/drivers/net/Kconfig b/drivers/net/Kconfig index 96f14ab1c1f..2a908c4690a 100644 --- a/drivers/net/Kconfig +++ b/drivers/net/Kconfig @@ -548,6 +548,14 @@ config SUNGEM Support for the Sun GEM chip, aka Sun GigabitEthernet/P 2.0. See also . +config CASSINI + tristate "Sun Cassini support" + depends on NET_ETHERNET && PCI + select CRC32 + help + Support for the Sun Cassini chip, aka Sun GigaSwift Ethernet. See also + + config NET_VENDOR_3COM bool "3COM cards" depends on NET_ETHERNET && (ISA || EISA || MCA || PCI) diff --git a/drivers/net/Makefile b/drivers/net/Makefile index 8645c843cf4..8aeec9f2495 100644 --- a/drivers/net/Makefile +++ b/drivers/net/Makefile @@ -28,6 +28,7 @@ obj-$(CONFIG_SUNQE) += sunqe.o obj-$(CONFIG_SUNBMAC) += sunbmac.o obj-$(CONFIG_MYRI_SBUS) += myri_sbus.o obj-$(CONFIG_SUNGEM) += sungem.o sungem_phy.o +obj-$(CONFIG_CASSINI) += cassini.o obj-$(CONFIG_MACE) += mace.o obj-$(CONFIG_BMAC) += bmac.o diff --git a/drivers/net/cassini.c b/drivers/net/cassini.c new file mode 100644 index 00000000000..69cb368247e --- /dev/null +++ b/drivers/net/cassini.c @@ -0,0 +1,5311 @@ +/* cassini.c: Sun Microsystems Cassini(+) ethernet driver. + * + * Copyright (C) 2004 Sun Microsystems Inc. + * Copyright (C) 2003 Adrian Sun (asun@darksunrising.com) + * + * 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. + * + * This driver uses the sungem driver (c) David Miller + * (davem@redhat.com) as its basis. + * + * The cassini chip has a number of features that distinguish it from + * the gem chip: + * 4 transmit descriptor rings that are used for either QoS (VLAN) or + * load balancing (non-VLAN mode) + * batching of multiple packets + * multiple CPU dispatching + * page-based RX descriptor engine with separate completion rings + * Gigabit support (GMII and PCS interface) + * MIF link up/down detection works + * + * RX is handled by page sized buffers that are attached as fragments to + * the skb. here's what's done: + * -- driver allocates pages at a time and keeps reference counts + * on them. + * -- the upper protocol layers assume that the header is in the skb + * itself. as a result, cassini will copy a small amount (64 bytes) + * to make them happy. + * -- driver appends the rest of the data pages as frags to skbuffs + * and increments the reference count + * -- on page reclamation, the driver swaps the page with a spare page. + * if that page is still in use, it frees its reference to that page, + * and allocates a new page for use. otherwise, it just recycles the + * the page. + * + * NOTE: cassini can parse the header. however, it's not worth it + * as long as the network stack requires a header copy. + * + * TX has 4 queues. currently these queues are used in a round-robin + * fashion for load balancing. They can also be used for QoS. for that + * to work, however, QoS information needs to be exposed down to the driver + * level so that subqueues get targetted to particular transmit rings. + * alternatively, the queues can be configured via use of the all-purpose + * ioctl. + * + * RX DATA: the rx completion ring has all the info, but the rx desc + * ring has all of the data. RX can conceivably come in under multiple + * interrupts, but the INT# assignment needs to be set up properly by + * the BIOS and conveyed to the driver. PCI BIOSes don't know how to do + * that. also, the two descriptor rings are designed to distinguish between + * encrypted and non-encrypted packets, but we use them for buffering + * instead. + * + * by default, the selective clear mask is set up to process rx packets. + */ + +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +#include +#include +#include +#include +#include + +#define cas_page_map(x) kmap_atomic((x), KM_SKB_DATA_SOFTIRQ) +#define cas_page_unmap(x) kunmap_atomic((x), KM_SKB_DATA_SOFTIRQ) +#define CAS_NCPUS num_online_cpus() + +#if defined(CONFIG_CASSINI_NAPI) && defined(HAVE_NETDEV_POLL) +#define USE_NAPI +#define cas_skb_release(x) netif_receive_skb(x) +#else +#define cas_skb_release(x) netif_rx(x) +#endif + +/* select which firmware to use */ +#define USE_HP_WORKAROUND +#define HP_WORKAROUND_DEFAULT /* select which firmware to use as default */ +#define CAS_HP_ALT_FIRMWARE cas_prog_null /* alternate firmware */ + +#include "cassini.h" + +#define USE_TX_COMPWB /* use completion writeback registers */ +#define USE_CSMA_CD_PROTO /* standard CSMA/CD */ +#define USE_RX_BLANK /* hw interrupt mitigation */ +#undef USE_ENTROPY_DEV /* don't test for entropy device */ + +/* NOTE: these aren't useable unless PCI interrupts can be assigned. + * also, we need to make cp->lock finer-grained. + */ +#undef USE_PCI_INTB +#undef USE_PCI_INTC +#undef USE_PCI_INTD +#undef USE_QOS + +#undef USE_VPD_DEBUG /* debug vpd information if defined */ + +/* rx processing options */ +#define USE_PAGE_ORDER /* specify to allocate large rx pages */ +#define RX_DONT_BATCH 0 /* if 1, don't batch flows */ +#define RX_COPY_ALWAYS 0 /* if 0, use frags */ +#define RX_COPY_MIN 64 /* copy a little to make upper layers happy */ +#undef RX_COUNT_BUFFERS /* define to calculate RX buffer stats */ + +#define DRV_MODULE_NAME "cassini" +#define PFX DRV_MODULE_NAME ": " +#define DRV_MODULE_VERSION "1.4" +#define DRV_MODULE_RELDATE "1 July 2004" + +#define CAS_DEF_MSG_ENABLE \ + (NETIF_MSG_DRV | \ + NETIF_MSG_PROBE | \ + NETIF_MSG_LINK | \ + NETIF_MSG_TIMER | \ + NETIF_MSG_IFDOWN | \ + NETIF_MSG_IFUP | \ + NETIF_MSG_RX_ERR | \ + NETIF_MSG_TX_ERR) + +/* length of time before we decide the hardware is borked, + * and dev->tx_timeout() should be called to fix the problem + */ +#define CAS_TX_TIMEOUT (HZ) +#define CAS_LINK_TIMEOUT (22*HZ/10) +#define CAS_LINK_FAST_TIMEOUT (1) + +/* timeout values for state changing. these specify the number + * of 10us delays to be used before giving up. + */ +#define STOP_TRIES_PHY 1000 +#define STOP_TRIES 5000 + +/* specify a minimum frame size to deal with some fifo issues + * max mtu == 2 * page size - ethernet header - 64 - swivel = + * 2 * page_size - 0x50 + */ +#define CAS_MIN_FRAME 97 +#define CAS_1000MB_MIN_FRAME 255 +#define CAS_MIN_MTU 60 +#define CAS_MAX_MTU min(((cp->page_size << 1) - 0x50), 9000) + +#if 1 +/* + * Eliminate these and use separate atomic counters for each, to + * avoid a race condition. + */ +#else +#define CAS_RESET_MTU 1 +#define CAS_RESET_ALL 2 +#define CAS_RESET_SPARE 3 +#endif + +static char version[] __devinitdata = + DRV_MODULE_NAME ".c:v" DRV_MODULE_VERSION " (" DRV_MODULE_RELDATE ")\n"; + +MODULE_AUTHOR("Adrian Sun (asun@darksunrising.com)"); +MODULE_DESCRIPTION("Sun Cassini(+) ethernet driver"); +MODULE_LICENSE("GPL"); +MODULE_PARM(cassini_debug, "i"); +MODULE_PARM_DESC(cassini_debug, "Cassini bitmapped debugging message enable value"); +MODULE_PARM(link_mode, "i"); +MODULE_PARM_DESC(link_mode, "default link mode"); + +/* + * Work around for a PCS bug in which the link goes down due to the chip + * being confused and never showing a link status of "up." + */ +#define DEFAULT_LINKDOWN_TIMEOUT 5 +/* + * Value in seconds, for user input. + */ +static int linkdown_timeout = DEFAULT_LINKDOWN_TIMEOUT; +MODULE_PARM(linkdown_timeout, "i"); +MODULE_PARM_DESC(linkdown_timeout, +"min reset interval in sec. for PCS linkdown issue; disabled if not positive"); + +/* + * value in 'ticks' (units used by jiffies). Set when we init the + * module because 'HZ' in actually a function call on some flavors of + * Linux. This will default to DEFAULT_LINKDOWN_TIMEOUT * HZ. + */ +static int link_transition_timeout; + + +static int cassini_debug = -1; /* -1 == use CAS_DEF_MSG_ENABLE as value */ +static int link_mode; + +static u16 link_modes[] __devinitdata = { + BMCR_ANENABLE, /* 0 : autoneg */ + 0, /* 1 : 10bt half duplex */ + BMCR_SPEED100, /* 2 : 100bt half duplex */ + BMCR_FULLDPLX, /* 3 : 10bt full duplex */ + BMCR_SPEED100|BMCR_FULLDPLX, /* 4 : 100bt full duplex */ + CAS_BMCR_SPEED1000|BMCR_FULLDPLX /* 5 : 1000bt full duplex */ +}; + +static struct pci_device_id cas_pci_tbl[] __devinitdata = { + { PCI_VENDOR_ID_SUN, PCI_DEVICE_ID_SUN_CASSINI, + PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0UL }, + { PCI_VENDOR_ID_NS, PCI_DEVICE_ID_NS_SATURN, + PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0UL }, + { 0, } +}; + +MODULE_DEVICE_TABLE(pci, cas_pci_tbl); + +static void cas_set_link_modes(struct cas *cp); + +static inline void cas_lock_tx(struct cas *cp) +{ + int i; + + for (i = 0; i < N_TX_RINGS; i++) + spin_lock(&cp->tx_lock[i]); +} + +static inline void cas_lock_all(struct cas *cp) +{ + spin_lock_irq(&cp->lock); + cas_lock_tx(cp); +} + +/* WTZ: QA was finding deadlock problems with the previous + * versions after long test runs with multiple cards per machine. + * See if replacing cas_lock_all with safer versions helps. The + * symptoms QA is reporting match those we'd expect if interrupts + * aren't being properly restored, and we fixed a previous deadlock + * with similar symptoms by using save/restore versions in other + * places. + */ +#define cas_lock_all_save(cp, flags) \ +do { \ + struct cas *xxxcp = (cp); \ + spin_lock_irqsave(&xxxcp->lock, flags); \ + cas_lock_tx(xxxcp); \ +} while (0) + +static inline void cas_unlock_tx(struct cas *cp) +{ + int i; + + for (i = N_TX_RINGS; i > 0; i--) + spin_unlock(&cp->tx_lock[i - 1]); +} + +static inline void cas_unlock_all(struct cas *cp) +{ + cas_unlock_tx(cp); + spin_unlock_irq(&cp->lock); +} + +#define cas_unlock_all_restore(cp, flags) \ +do { \ + struct cas *xxxcp = (cp); \ + cas_unlock_tx(xxxcp); \ + spin_unlock_irqrestore(&xxxcp->lock, flags); \ +} while (0) + +static void cas_disable_irq(struct cas *cp, const int ring) +{ + /* Make sure we won't get any more interrupts */ + if (ring == 0) { + writel(0xFFFFFFFF, cp->regs + REG_INTR_MASK); + return; + } + + /* disable completion interrupts and selectively mask */ + if (cp->cas_flags & CAS_FLAG_REG_PLUS) { + switch (ring) { +#if defined (USE_PCI_INTB) || defined(USE_PCI_INTC) || defined(USE_PCI_INTD) +#ifdef USE_PCI_INTB + case 1: +#endif +#ifdef USE_PCI_INTC + case 2: +#endif +#ifdef USE_PCI_INTD + case 3: +#endif + writel(INTRN_MASK_CLEAR_ALL | INTRN_MASK_RX_EN, + cp->regs + REG_PLUS_INTRN_MASK(ring)); + break; +#endif + default: + writel(INTRN_MASK_CLEAR_ALL, cp->regs + + REG_PLUS_INTRN_MASK(ring)); + break; + } + } +} + +static inline void cas_mask_intr(struct cas *cp) +{ + int i; + + for (i = 0; i < N_RX_COMP_RINGS; i++) + cas_disable_irq(cp, i); +} + +static void cas_enable_irq(struct cas *cp, const int ring) +{ + if (ring == 0) { /* all but TX_DONE */ + writel(INTR_TX_DONE, cp->regs + REG_INTR_MASK); + return; + } + + if (cp->cas_flags & CAS_FLAG_REG_PLUS) { + switch (ring) { +#if defined (USE_PCI_INTB) || defined(USE_PCI_INTC) || defined(USE_PCI_INTD) +#ifdef USE_PCI_INTB + case 1: +#endif +#ifdef USE_PCI_INTC + case 2: +#endif +#ifdef USE_PCI_INTD + case 3: +#endif + writel(INTRN_MASK_RX_EN, cp->regs + + REG_PLUS_INTRN_MASK(ring)); + break; +#endif + default: + break; + } + } +} + +static inline void cas_unmask_intr(struct cas *cp) +{ + int i; + + for (i = 0; i < N_RX_COMP_RINGS; i++) + cas_enable_irq(cp, i); +} + +static inline void cas_entropy_gather(struct cas *cp) +{ +#ifdef USE_ENTROPY_DEV + if ((cp->cas_flags & CAS_FLAG_ENTROPY_DEV) == 0) + return; + + batch_entropy_store(readl(cp->regs + REG_ENTROPY_IV), + readl(cp->regs + REG_ENTROPY_IV), + sizeof(uint64_t)*8); +#endif +} + +static inline void cas_entropy_reset(struct cas *cp) +{ +#ifdef USE_ENTROPY_DEV + if ((cp->cas_flags & CAS_FLAG_ENTROPY_DEV) == 0) + return; + + writel(BIM_LOCAL_DEV_PAD | BIM_LOCAL_DEV_PROM | BIM_LOCAL_DEV_EXT, + cp->regs + REG_BIM_LOCAL_DEV_EN); + writeb(ENTROPY_RESET_STC_MODE, cp->regs + REG_ENTROPY_RESET); + writeb(0x55, cp->regs + REG_ENTROPY_RAND_REG); + + /* if we read back 0x0, we don't have an entropy device */ + if (readb(cp->regs + REG_ENTROPY_RAND_REG) == 0) + cp->cas_flags &= ~CAS_FLAG_ENTROPY_DEV; +#endif +} + +/* access to the phy. the following assumes that we've initialized the MIF to + * be in frame rather than bit-bang mode + */ +static u16 cas_phy_read(struct cas *cp, int reg) +{ + u32 cmd; + int limit = STOP_TRIES_PHY; + + cmd = MIF_FRAME_ST | MIF_FRAME_OP_READ; + cmd |= CAS_BASE(MIF_FRAME_PHY_ADDR, cp->phy_addr); + cmd |= CAS_BASE(MIF_FRAME_REG_ADDR, reg); + cmd |= MIF_FRAME_TURN_AROUND_MSB; + writel(cmd, cp->regs + REG_MIF_FRAME); + + /* poll for completion */ + while (limit-- > 0) { + udelay(10); + cmd = readl(cp->regs + REG_MIF_FRAME); + if (cmd & MIF_FRAME_TURN_AROUND_LSB) + return (cmd & MIF_FRAME_DATA_MASK); + } + return 0xFFFF; /* -1 */ +} + +static int cas_phy_write(struct cas *cp, int reg, u16 val) +{ + int limit = STOP_TRIES_PHY; + u32 cmd; + + cmd = MIF_FRAME_ST | MIF_FRAME_OP_WRITE; + cmd |= CAS_BASE(MIF_FRAME_PHY_ADDR, cp->phy_addr); + cmd |= CAS_BASE(MIF_FRAME_REG_ADDR, reg); + cmd |= MIF_FRAME_TURN_AROUND_MSB; + cmd |= val & MIF_FRAME_DATA_MASK; + writel(cmd, cp->regs + REG_MIF_FRAME); + + /* poll for completion */ + while (limit-- > 0) { + udelay(10); + cmd = readl(cp->regs + REG_MIF_FRAME); + if (cmd & MIF_FRAME_TURN_AROUND_LSB) + return 0; + } + return -1; +} + +static void cas_phy_powerup(struct cas *cp) +{ + u16 ctl = cas_phy_read(cp, MII_BMCR); + + if ((ctl & BMCR_PDOWN) == 0) + return; + ctl &= ~BMCR_PDOWN; + cas_phy_write(cp, MII_BMCR, ctl); +} + +static void cas_phy_powerdown(struct cas *cp) +{ + u16 ctl = cas_phy_read(cp, MII_BMCR); + + if (ctl & BMCR_PDOWN) + return; + ctl |= BMCR_PDOWN; + cas_phy_write(cp, MII_BMCR, ctl); +} + +/* cp->lock held. note: the last put_page will free the buffer */ +static int cas_page_free(struct cas *cp, cas_page_t *page) +{ + pci_unmap_page(cp->pdev, page->dma_addr, cp->page_size, + PCI_DMA_FROMDEVICE); + __free_pages(page->buffer, cp->page_order); + kfree(page); + return 0; +} + +#ifdef RX_COUNT_BUFFERS +#define RX_USED_ADD(x, y) ((x)->used += (y)) +#define RX_USED_SET(x, y) ((x)->used = (y)) +#else +#define RX_USED_ADD(x, y) +#define RX_USED_SET(x, y) +#endif + +/* local page allocation routines for the receive buffers. jumbo pages + * require at least 8K contiguous and 8K aligned buffers. + */ +static cas_page_t *cas_page_alloc(struct cas *cp, const int flags) +{ + cas_page_t *page; + + page = kmalloc(sizeof(cas_page_t), flags); + if (!page) + return NULL; + + INIT_LIST_HEAD(&page->list); + RX_USED_SET(page, 0); + page->buffer = alloc_pages(flags, cp->page_order); + if (!page->buffer) + goto page_err; + page->dma_addr = pci_map_page(cp->pdev, page->buffer, 0, + cp->page_size, PCI_DMA_FROMDEVICE); + return page; + +page_err: + kfree(page); + return NULL; +} + +/* initialize spare pool of rx buffers, but allocate during the open */ +static void cas_spare_init(struct cas *cp) +{ + spin_lock(&cp->rx_inuse_lock); + INIT_LIST_HEAD(&cp->rx_inuse_list); + spin_unlock(&cp->rx_inuse_lock); + + spin_lock(&cp->rx_spare_lock); + INIT_LIST_HEAD(&cp->rx_spare_list); + cp->rx_spares_needed = RX_SPARE_COUNT; + spin_unlock(&cp->rx_spare_lock); +} + +/* used on close. free all the spare buffers. */ +static void cas_spare_free(struct cas *cp) +{ + struct list_head list, *elem, *tmp; + + /* free spare buffers */ + INIT_LIST_HEAD(&list); + spin_lock(&cp->rx_spare_lock); + list_splice(&cp->rx_spare_list, &list); + INIT_LIST_HEAD(&cp->rx_spare_list); + spin_unlock(&cp->rx_spare_lock); + list_for_each_safe(elem, tmp, &list) { + cas_page_free(cp, list_entry(elem, cas_page_t, list)); + } + + INIT_LIST_HEAD(&list); +#if 1 + /* + * Looks like Adrian had protected this with a different + * lock than used everywhere else to manipulate this list. + */ + spin_lock(&cp->rx_inuse_lock); + list_splice(&cp->rx_inuse_list, &list); + INIT_LIST_HEAD(&cp->rx_inuse_list); + spin_unlock(&cp->rx_inuse_lock); +#else + spin_lock(&cp->rx_spare_lock); + list_splice(&cp->rx_inuse_list, &list); + INIT_LIST_HEAD(&cp->rx_inuse_list); + spin_unlock(&cp->rx_spare_lock); +#endif + list_for_each_safe(elem, tmp, &list) { + cas_page_free(cp, list_entry(elem, cas_page_t, list)); + } +} + +/* replenish spares if needed */ +static void cas_spare_recover(struct cas *cp, const int flags) +{ + struct list_head list, *elem, *tmp; + int needed, i; + + /* check inuse list. if we don't need any more free buffers, + * just free it + */ + + /* make a local copy of the list */ + INIT_LIST_HEAD(&list); + spin_lock(&cp->rx_inuse_lock); + list_splice(&cp->rx_inuse_list, &list); + INIT_LIST_HEAD(&cp->rx_inuse_list); + spin_unlock(&cp->rx_inuse_lock); + + list_for_each_safe(elem, tmp, &list) { + cas_page_t *page = list_entry(elem, cas_page_t, list); + + if (page_count(page->buffer) > 1) + continue; + + list_del(elem); + spin_lock(&cp->rx_spare_lock); + if (cp->rx_spares_needed > 0) { + list_add(elem, &cp->rx_spare_list); + cp->rx_spares_needed--; + spin_unlock(&cp->rx_spare_lock); + } else { + spin_unlock(&cp->rx_spare_lock); + cas_page_free(cp, page); + } + } + + /* put any inuse buffers back on the list */ + if (!list_empty(&list)) { + spin_lock(&cp->rx_inuse_lock); + list_splice(&list, &cp->rx_inuse_list); + spin_unlock(&cp->rx_inuse_lock); + } + + spin_lock(&cp->rx_spare_lock); + needed = cp->rx_spares_needed; + spin_unlock(&cp->rx_spare_lock); + if (!needed) + return; + + /* we still need spares, so try to allocate some */ + INIT_LIST_HEAD(&list); + i = 0; + while (i < needed) { + cas_page_t *spare = cas_page_alloc(cp, flags); + if (!spare) + break; + list_add(&spare->list, &list); + i++; + } + + spin_lock(&cp->rx_spare_lock); + list_splice(&list, &cp->rx_spare_list); + cp->rx_spares_needed -= i; + spin_unlock(&cp->rx_spare_lock); +} + +/* pull a page from the list. */ +static cas_page_t *cas_page_dequeue(struct cas *cp) +{ + struct list_head *entry; + int recover; + + spin_lock(&cp->rx_spare_lock); + if (list_empty(&cp->rx_spare_list)) { + /* try to do a quick recovery */ + spin_unlock(&cp->rx_spare_lock); + cas_spare_recover(cp, GFP_ATOMIC); + spin_lock(&cp->rx_spare_lock); + if (list_empty(&cp->rx_spare_list)) { + if (netif_msg_rx_err(cp)) + printk(KERN_ERR "%s: no spare buffers " + "available.\n", cp->dev->name); + spin_unlock(&cp->rx_spare_lock); + return NULL; + } + } + + entry = cp->rx_spare_list.next; + list_del(entry); + recover = ++cp->rx_spares_needed; + spin_unlock(&cp->rx_spare_lock); + + /* trigger the timer to do the recovery */ + if ((recover & (RX_SPARE_RECOVER_VAL - 1)) == 0) { +#if 1 + atomic_inc(&cp->reset_task_pending); + atomic_inc(&cp->reset_task_pending_spare); + schedule_work(&cp->reset_task); +#else + atomic_set(&cp->reset_task_pending, CAS_RESET_SPARE); + schedule_work(&cp->reset_task); +#endif + } + return list_entry(entry, cas_page_t, list); +} + + +static void cas_mif_poll(struct cas *cp, const int enable) +{ + u32 cfg; + + cfg = readl(cp->regs + REG_MIF_CFG); + cfg &= (MIF_CFG_MDIO_0 | MIF_CFG_MDIO_1); + + if (cp->phy_type & CAS_PHY_MII_MDIO1) + cfg |= MIF_CFG_PHY_SELECT; + + /* poll and interrupt on link status change. */ + if (enable) { + cfg |= MIF_CFG_POLL_EN; + cfg |= CAS_BASE(MIF_CFG_POLL_REG, MII_BMSR); + cfg |= CAS_BASE(MIF_CFG_POLL_PHY, cp->phy_addr); + } + writel((enable) ? ~(BMSR_LSTATUS | BMSR_ANEGCOMPLETE) : 0xFFFF, + cp->regs + REG_MIF_MASK); + writel(cfg, cp->regs + REG_MIF_CFG); +} + +/* Must be invoked under cp->lock */ +static void cas_begin_auto_negotiation(struct cas *cp, struct ethtool_cmd *ep) +{ + u16 ctl; +#if 1 + int lcntl; + int changed = 0; + int oldstate = cp->lstate; + int link_was_not_down = !(oldstate == link_down); +#endif + /* Setup link parameters */ + if (!ep) + goto start_aneg; + lcntl = cp->link_cntl; + if (ep->autoneg == AUTONEG_ENABLE) + cp->link_cntl = BMCR_ANENABLE; + else { + cp->link_cntl = 0; + if (ep->speed == SPEED_100) + cp->link_cntl |= BMCR_SPEED100; + else if (ep->speed == SPEED_1000) + cp->link_cntl |= CAS_BMCR_SPEED1000; + if (ep->duplex == DUPLEX_FULL) + cp->link_cntl |= BMCR_FULLDPLX; + } +#if 1 + changed = (lcntl != cp->link_cntl); +#endif +start_aneg: + if (cp->lstate == link_up) { + printk(KERN_INFO "%s: PCS link down.\n", + cp->dev->name); + } else { + if (changed) { + printk(KERN_INFO "%s: link configuration changed\n", + cp->dev->name); + } + } + cp->lstate = link_down; + cp->link_transition = LINK_TRANSITION_LINK_DOWN; + if (!cp->hw_running) + return; +#if 1 + /* + * WTZ: If the old state was link_up, we turn off the carrier + * to replicate everything we do elsewhere on a link-down + * event when we were already in a link-up state.. + */ + if (oldstate == link_up) + netif_carrier_off(cp->dev); + if (changed && link_was_not_down) { + /* + * WTZ: This branch will simply schedule a full reset after + * we explicitly changed link modes in an ioctl. See if this + * fixes the link-problems we were having for forced mode. + */ + atomic_inc(&cp->reset_task_pending); + atomic_inc(&cp->reset_task_pending_all); + schedule_work(&cp->reset_task); + cp->timer_ticks = 0; + mod_timer(&cp->link_timer, jiffies + CAS_LINK_TIMEOUT); + return; + } +#endif + if (cp->phy_type & CAS_PHY_SERDES) { + u32 val = readl(cp->regs + REG_PCS_MII_CTRL); + + if (cp->link_cntl & BMCR_ANENABLE) { + val |= (PCS_MII_RESTART_AUTONEG | PCS_MII_AUTONEG_EN); + cp->lstate = link_aneg; + } else { + if (cp->link_cntl & BMCR_FULLDPLX) + val |= PCS_MII_CTRL_DUPLEX; + val &= ~PCS_MII_AUTONEG_EN; + cp->lstate = link_force_ok; + } + cp->link_transition = LINK_TRANSITION_LINK_CONFIG; + writel(val, cp->regs + REG_PCS_MII_CTRL); + + } else { + cas_mif_poll(cp, 0); + ctl = cas_phy_read(cp, MII_BMCR); + ctl &= ~(BMCR_FULLDPLX | BMCR_SPEED100 | + CAS_BMCR_SPEED1000 | BMCR_ANENABLE); + ctl |= cp->link_cntl; + if (ctl & BMCR_ANENABLE) { + ctl |= BMCR_ANRESTART; + cp->lstate = link_aneg; + } else { + cp->lstate = link_force_ok; + } + cp->link_transition = LINK_TRANSITION_LINK_CONFIG; + cas_phy_write(cp, MII_BMCR, ctl); + cas_mif_poll(cp, 1); + } + + cp->timer_ticks = 0; + mod_timer(&cp->link_timer, jiffies + CAS_LINK_TIMEOUT); +} + +/* Must be invoked under cp->lock. */ +static int cas_reset_mii_phy(struct cas *cp) +{ + int limit = STOP_TRIES_PHY; + u16 val; + + cas_phy_write(cp, MII_BMCR, BMCR_RESET); + udelay(100); + while (limit--) { + val = cas_phy_read(cp, MII_BMCR); + if ((val & BMCR_RESET) == 0) + break; + udelay(10); + } + return (limit <= 0); +} + +static void cas_saturn_firmware_load(struct cas *cp) +{ + cas_saturn_patch_t *patch = cas_saturn_patch; + + cas_phy_powerdown(cp); + + /* expanded memory access mode */ + cas_phy_write(cp, DP83065_MII_MEM, 0x0); + + /* pointer configuration for new firmware */ + cas_phy_write(cp, DP83065_MII_REGE, 0x8ff9); + cas_phy_write(cp, DP83065_MII_REGD, 0xbd); + cas_phy_write(cp, DP83065_MII_REGE, 0x8ffa); + cas_phy_write(cp, DP83065_MII_REGD, 0x82); + cas_phy_write(cp, DP83065_MII_REGE, 0x8ffb); + cas_phy_write(cp, DP83065_MII_REGD, 0x0); + cas_phy_write(cp, DP83065_MII_REGE, 0x8ffc); + cas_phy_write(cp, DP83065_MII_REGD, 0x39); + + /* download new firmware */ + cas_phy_write(cp, DP83065_MII_MEM, 0x1); + cas_phy_write(cp, DP83065_MII_REGE, patch->addr); + while (patch->addr) { + cas_phy_write(cp, DP83065_MII_REGD, patch->val); + patch++; + } + + /* enable firmware */ + cas_phy_write(cp, DP83065_MII_REGE, 0x8ff8); + cas_phy_write(cp, DP83065_MII_REGD, 0x1); +} + + +/* phy initialization */ +static void cas_phy_init(struct cas *cp) +{ + u16 val; + + /* if we're in MII/GMII mode, set up phy */ + if (CAS_PHY_MII(cp->phy_type)) { + writel(PCS_DATAPATH_MODE_MII, + cp->regs + REG_PCS_DATAPATH_MODE); + + cas_mif_poll(cp, 0); + cas_reset_mii_phy(cp); /* take out of isolate mode */ + + if (PHY_LUCENT_B0 == cp->phy_id) { + /* workaround link up/down issue with lucent */ + cas_phy_write(cp, LUCENT_MII_REG, 0x8000); + cas_phy_write(cp, MII_BMCR, 0x00f1); + cas_phy_write(cp, LUCENT_MII_REG, 0x0); + + } else if (PHY_BROADCOM_B0 == (cp->phy_id & 0xFFFFFFFC)) { + /* workarounds for broadcom phy */ + cas_phy_write(cp, BROADCOM_MII_REG8, 0x0C20); + cas_phy_write(cp, BROADCOM_MII_REG7, 0x0012); + cas_phy_write(cp, BROADCOM_MII_REG5, 0x1804); + cas_phy_write(cp, BROADCOM_MII_REG7, 0x0013); + cas_phy_write(cp, BROADCOM_MII_REG5, 0x1204); + cas_phy_write(cp, BROADCOM_MII_REG7, 0x8006); + cas_phy_write(cp, BROADCOM_MII_REG5, 0x0132); + cas_phy_write(cp, BROADCOM_MII_REG7, 0x8006); + cas_phy_write(cp, BROADCOM_MII_REG5, 0x0232); + cas_phy_write(cp, BROADCOM_MII_REG7, 0x201F); + cas_phy_write(cp, BROADCOM_MII_REG5, 0x0A20); + + } else if (PHY_BROADCOM_5411 == cp->phy_id) { + val = cas_phy_read(cp, BROADCOM_MII_REG4); + val = cas_phy_read(cp, BROADCOM_MII_REG4); + if (val & 0x0080) { + /* link workaround */ + cas_phy_write(cp, BROADCOM_MII_REG4, + val & ~0x0080); + } + + } else if (cp->cas_flags & CAS_FLAG_SATURN) { + writel((cp->phy_type & CAS_PHY_MII_MDIO0) ? + SATURN_PCFG_FSI : 0x0, + cp->regs + REG_SATURN_PCFG); + + /* load firmware to address 10Mbps auto-negotiation + * issue. NOTE: this will need to be changed if the + * default firmware gets fixed. + */ + if (PHY_NS_DP83065 == cp->phy_id) { + cas_saturn_firmware_load(cp); + } + cas_phy_powerup(cp); + } + + /* advertise capabilities */ + val = cas_phy_read(cp, MII_BMCR); + val &= ~BMCR_ANENABLE; + cas_phy_write(cp, MII_BMCR, val); + udelay(10); + + cas_phy_write(cp, MII_ADVERTISE, + cas_phy_read(cp, MII_ADVERTISE) | + (ADVERTISE_10HALF | ADVERTISE_10FULL | + ADVERTISE_100HALF | ADVERTISE_100FULL | + CAS_ADVERTISE_PAUSE | + CAS_ADVERTISE_ASYM_PAUSE)); + + if (cp->cas_flags & CAS_FLAG_1000MB_CAP) { + /* make sure that we don't advertise half + * duplex to avoid a chip issue + */ + val = cas_phy_read(cp, CAS_MII_1000_CTRL); + val &= ~CAS_ADVERTISE_1000HALF; + val |= CAS_ADVERTISE_1000FULL; + cas_phy_write(cp, CAS_MII_1000_CTRL, val); + } + + } else { + /* reset pcs for serdes */ + u32 val; + int limit; + + writel(PCS_DATAPATH_MODE_SERDES, + cp->regs + REG_PCS_DATAPATH_MODE); + + /* enable serdes pins on saturn */ + if (cp->cas_flags & CAS_FLAG_SATURN) + writel(0, cp->regs + REG_SATURN_PCFG); + + /* Reset PCS unit. */ + val = readl(cp->regs + REG_PCS_MII_CTRL); + val |= PCS_MII_RESET; + writel(val, cp->regs + REG_PCS_MII_CTRL); + + limit = STOP_TRIES; + while (limit-- > 0) { + udelay(10); + if ((readl(cp->regs + REG_PCS_MII_CTRL) & + PCS_MII_RESET) == 0) + break; + } + if (limit <= 0) + printk(KERN_WARNING "%s: PCS reset bit would not " + "clear [%08x].\n", cp->dev->name, + readl(cp->regs + REG_PCS_STATE_MACHINE)); + + /* Make sure PCS is disabled while changing advertisement + * configuration. + */ + writel(0x0, cp->regs + REG_PCS_CFG); + + /* Advertise all capabilities except half-duplex. */ + val = readl(cp->regs + REG_PCS_MII_ADVERT); + val &= ~PCS_MII_ADVERT_HD; + val |= (PCS_MII_ADVERT_FD | PCS_MII_ADVERT_SYM_PAUSE | + PCS_MII_ADVERT_ASYM_PAUSE); + writel(val, cp->regs + REG_PCS_MII_ADVERT); + + /* enable PCS */ + writel(PCS_CFG_EN, cp->regs + REG_PCS_CFG); + + /* pcs workaround: enable sync detect */ + writel(PCS_SERDES_CTRL_SYNCD_EN, + cp->regs + REG_PCS_SERDES_CTRL); + } +} + + +static int cas_pcs_link_check(struct cas *cp) +{ + u32 stat, state_machine; + int retval = 0; + + /* The link status bit latches on zero, so you must + * read it twice in such a case to see a transition + * to the link being up. + */ + stat = readl(cp->regs + REG_PCS_MII_STATUS); + if ((stat & PCS_MII_STATUS_LINK_STATUS) == 0) + stat = readl(cp->regs + REG_PCS_MII_STATUS); + + /* The remote-fault indication is only valid + * when autoneg has completed. + */ + if ((stat & (PCS_MII_STATUS_AUTONEG_COMP | + PCS_MII_STATUS_REMOTE_FAULT)) == + (PCS_MII_STATUS_AUTONEG_COMP | PCS_MII_STATUS_REMOTE_FAULT)) { + if (netif_msg_link(cp)) + printk(KERN_INFO "%s: PCS RemoteFault\n", + cp->dev->name); + } + + /* work around link detection issue by querying the PCS state + * machine directly. + */ + state_machine = readl(cp->regs + REG_PCS_STATE_MACHINE); + if ((state_machine & PCS_SM_LINK_STATE_MASK) != SM_LINK_STATE_UP) { + stat &= ~PCS_MII_STATUS_LINK_STATUS; + } else if (state_machine & PCS_SM_WORD_SYNC_STATE_MASK) { + stat |= PCS_MII_STATUS_LINK_STATUS; + } + + if (stat & PCS_MII_STATUS_LINK_STATUS) { + if (cp->lstate != link_up) { + if (cp->opened) { + cp->lstate = link_up; + cp->link_transition = LINK_TRANSITION_LINK_UP; + + cas_set_link_modes(cp); + netif_carrier_on(cp->dev); + } + } + } else if (cp->lstate == link_up) { + cp->lstate = link_down; + if (link_transition_timeout != 0 && + cp->link_transition != LINK_TRANSITION_REQUESTED_RESET && + !cp->link_transition_jiffies_valid) { + /* + * force a reset, as a workaround for the + * link-failure problem. May want to move this to a + * point a bit earlier in the sequence. If we had + * generated a reset a short time ago, we'll wait for + * the link timer to check the status until a + * timer expires (link_transistion_jiffies_valid is + * true when the timer is running.) Instead of using + * a system timer, we just do a check whenever the + * link timer is running - this clears the flag after + * a suitable delay. + */ + retval = 1; + cp->link_transition = LINK_TRANSITION_REQUESTED_RESET; + cp->link_transition_jiffies = jiffies; + cp->link_transition_jiffies_valid = 1; + } else { + cp->link_transition = LINK_TRANSITION_ON_FAILURE; + } + netif_carrier_off(cp->dev); + if (cp->opened && netif_msg_link(cp)) { + printk(KERN_INFO "%s: PCS link down.\n", + cp->dev->name); + } + + /* Cassini only: if you force a mode, there can be + * sync problems on link down. to fix that, the following + * things need to be checked: + * 1) read serialink state register + * 2) read pcs status register to verify link down. + * 3) if link down and serial link == 0x03, then you need + * to global reset the chip. + */ + if ((cp->cas_flags & CAS_FLAG_REG_PLUS) == 0) { + /* should check to see if we're in a forced mode */ + stat = readl(cp->regs + REG_PCS_SERDES_STATE); + if (stat == 0x03) + return 1; + } + } else if (cp->lstate == link_down) { + if (link_transition_timeout != 0 && + cp->link_transition != LINK_TRANSITION_REQUESTED_RESET && + !cp->link_transition_jiffies_valid) { + /* force a reset, as a workaround for the + * link-failure problem. May want to move + * this to a point a bit earlier in the + * sequence. + */ + retval = 1; + cp->link_transition = LINK_TRANSITION_REQUESTED_RESET; + cp->link_transition_jiffies = jiffies; + cp->link_transition_jiffies_valid = 1; + } else { + cp->link_transition = LINK_TRANSITION_STILL_FAILED; + } + } + + return retval; +} + +static int cas_pcs_interrupt(struct net_device *dev, + struct cas *cp, u32 status) +{ + u32 stat = readl(cp->regs + REG_PCS_INTR_STATUS); + + if ((stat & PCS_INTR_STATUS_LINK_CHANGE) == 0) + return 0; + return cas_pcs_link_check(cp); +} + +static int cas_txmac_interrupt(struct net_device *dev, + struct cas *cp, u32 status) +{ + u32 txmac_stat = readl(cp->regs + REG_MAC_TX_STATUS); + + if (!txmac_stat) + return 0; + + if (netif_msg_intr(cp)) + printk(KERN_DEBUG "%s: txmac interrupt, txmac_stat: 0x%x\n", + cp->dev->name, txmac_stat); + + /* Defer timer expiration is quite normal, + * don't even log the event. + */ + if ((txmac_stat & MAC_TX_DEFER_TIMER) && + !(txmac_stat & ~MAC_TX_DEFER_TIMER)) + return 0; + + spin_lock(&cp->stat_lock[0]); + if (txmac_stat & MAC_TX_UNDERRUN) { + printk(KERN_ERR "%s: TX MAC xmit underrun.\n", + dev->name); + cp->net_stats[0].tx_fifo_errors++; + } + + if (txmac_stat & MAC_TX_MAX_PACKET_ERR) { + printk(KERN_ERR "%s: TX MAC max packet size error.\n", + dev->name); + cp->net_stats[0].tx_errors++; + } + + /* The rest are all cases of one of the 16-bit TX + * counters expiring. + */ + if (txmac_stat & MAC_TX_COLL_NORMAL) + cp->net_stats[0].collisions += 0x10000; + + if (txmac_stat & MAC_TX_COLL_EXCESS) { + cp->net_stats[0].tx_aborted_errors += 0x10000; + cp->net_stats[0].collisions += 0x10000; + } + + if (txmac_stat & MAC_TX_COLL_LATE) { + cp->net_stats[0].tx_aborted_errors += 0x10000; + cp->net_stats[0].collisions += 0x10000; + } + spin_unlock(&cp->stat_lock[0]); + + /* We do not keep track of MAC_TX_COLL_FIRST and + * MAC_TX_PEAK_ATTEMPTS events. + */ + return 0; +} + +static void cas_load_firmware(struct cas *cp, cas_hp_inst_t *firmware) +{ + cas_hp_inst_t *inst; + u32 val; + int i; + + i = 0; + while ((inst = firmware) && inst->note) { + writel(i, cp->regs + REG_HP_INSTR_RAM_ADDR); + + val = CAS_BASE(HP_INSTR_RAM_HI_VAL, inst->val); + val |= CAS_BASE(HP_INSTR_RAM_HI_MASK, inst->mask); + writel(val, cp->regs + REG_HP_INSTR_RAM_DATA_HI); + + val = CAS_BASE(HP_INSTR_RAM_MID_OUTARG, inst->outarg >> 10); + val |= CAS_BASE(HP_INSTR_RAM_MID_OUTOP, inst->outop); + val |= CAS_BASE(HP_INSTR_RAM_MID_FNEXT, inst->fnext); + val |= CAS_BASE(HP_INSTR_RAM_MID_FOFF, inst->foff); + val |= CAS_BASE(HP_INSTR_RAM_MID_SNEXT, inst->snext); + val |= CAS_BASE(HP_INSTR_RAM_MID_SOFF, inst->soff); + val |= CAS_BASE(HP_INSTR_RAM_MID_OP, inst->op); + writel(val, cp->regs + REG_HP_INSTR_RAM_DATA_MID); + + val = CAS_BASE(HP_INSTR_RAM_LOW_OUTMASK, inst->outmask); + val |= CAS_BASE(HP_INSTR_RAM_LOW_OUTSHIFT, inst->outshift); + val |= CAS_BASE(HP_INSTR_RAM_LOW_OUTEN, inst->outenab); + val |= CAS_BASE(HP_INSTR_RAM_LOW_OUTARG, inst->outarg); + writel(val, cp->regs + REG_HP_INSTR_RAM_DATA_LOW); + ++firmware; + ++i; + } +} + +static void cas_init_rx_dma(struct cas *cp) +{ + u64 desc_dma = cp->block_dvma; + u32 val; + int i, size; + + /* rx free descriptors */ + val = CAS_BASE(RX_CFG_SWIVEL, RX_SWIVEL_OFF_VAL); + val |= CAS_BASE(RX_CFG_DESC_RING, RX_DESC_RINGN_INDEX(0)); + val |= CAS_BASE(RX_CFG_COMP_RING, RX_COMP_RINGN_INDEX(0)); + if ((N_RX_DESC_RINGS > 1) && + (cp->cas_flags & CAS_FLAG_REG_PLUS)) /* do desc 2 */ + val |= CAS_BASE(RX_CFG_DESC_RING1, RX_DESC_RINGN_INDEX(1)); + writel(val, cp->regs + REG_RX_CFG); + + val = (unsigned long) cp->init_rxds[0] - + (unsigned long) cp->init_block; + writel((desc_dma + val) >> 32, cp->regs + REG_RX_DB_HI); + writel((desc_dma + val) & 0xffffffff, cp->regs + REG_RX_DB_LOW); + writel(RX_DESC_RINGN_SIZE(0) - 4, cp->regs + REG_RX_KICK); + + if (cp->cas_flags & CAS_FLAG_REG_PLUS) { + /* rx desc 2 is for IPSEC packets. however, + * we don't it that for that purpose. + */ + val = (unsigned long) cp->init_rxds[1] - + (unsigned long) cp->init_block; + writel((desc_dma + val) >> 32, cp->regs + REG_PLUS_RX_DB1_HI); + writel((desc_dma + val) & 0xffffffff, cp->regs + + REG_PLUS_RX_DB1_LOW); + writel(RX_DESC_RINGN_SIZE(1) - 4, cp->regs + + REG_PLUS_RX_KICK1); + } + + /* rx completion registers */ + val = (unsigned long) cp->init_rxcs[0] - + (unsigned long) cp->init_block; + writel((desc_dma + val) >> 32, cp->regs + REG_RX_CB_HI); + writel((desc_dma + val) & 0xffffffff, cp->regs + REG_RX_CB_LOW); + + if (cp->cas_flags & CAS_FLAG_REG_PLUS) { + /* rx comp 2-4 */ + for (i = 1; i < MAX_RX_COMP_RINGS; i++) { + val = (unsigned long) cp->init_rxcs[i] - + (unsigned long) cp->init_block; + writel((desc_dma + val) >> 32, cp->regs + + REG_PLUS_RX_CBN_HI(i)); + writel((desc_dma + val) & 0xffffffff, cp->regs + + REG_PLUS_RX_CBN_LOW(i)); + } + } + + /* read selective clear regs to prevent spurious interrupts + * on reset because complete == kick. + * selective clear set up to prevent interrupts on resets + */ + readl(cp->regs + REG_INTR_STATUS_ALIAS); + writel(INTR_RX_DONE | INTR_RX_BUF_UNAVAIL, cp->regs + REG_ALIAS_CLEAR); + if (cp->cas_flags & CAS_FLAG_REG_PLUS) { + for (i = 1; i < N_RX_COMP_RINGS; i++) + readl(cp->regs + REG_PLUS_INTRN_STATUS_ALIAS(i)); + + /* 2 is different from 3 and 4 */ + if (N_RX_COMP_RINGS > 1) + writel(INTR_RX_DONE_ALT | INTR_RX_BUF_UNAVAIL_1, + cp->regs + REG_PLUS_ALIASN_CLEAR(1)); + + for (i = 2; i < N_RX_COMP_RINGS; i++) + writel(INTR_RX_DONE_ALT, + cp->regs + REG_PLUS_ALIASN_CLEAR(i)); + } + + /* set up pause thresholds */ + val = CAS_BASE(RX_PAUSE_THRESH_OFF, + cp->rx_pause_off / RX_PAUSE_THRESH_QUANTUM); + val |= CAS_BASE(RX_PAUSE_THRESH_ON, + cp->rx_pause_on / RX_PAUSE_THRESH_QUANTUM); + writel(val, cp->regs + REG_RX_PAUSE_THRESH); + + /* zero out dma reassembly buffers */ + for (i = 0; i < 64; i++) { + writel(i, cp->regs + REG_RX_TABLE_ADDR); + writel(0x0, cp->regs + REG_RX_TABLE_DATA_LOW); + writel(0x0, cp->regs + REG_RX_TABLE_DATA_MID); + writel(0x0, cp->regs + REG_RX_TABLE_DATA_HI); + } + + /* make sure address register is 0 for normal operation */ + writel(0x0, cp->regs + REG_RX_CTRL_FIFO_ADDR); + writel(0x0, cp->regs + REG_RX_IPP_FIFO_ADDR); + + /* interrupt mitigation */ +#ifdef USE_RX_BLANK + val = CAS_BASE(RX_BLANK_INTR_TIME, RX_BLANK_INTR_TIME_VAL); + val |= CAS_BASE(RX_BLANK_INTR_PKT, RX_BLANK_INTR_PKT_VAL); + writel(val, cp->regs + REG_RX_BLANK); +#else + writel(0x0, cp->regs + REG_RX_BLANK); +#endif + + /* interrupt generation as a function of low water marks for + * free desc and completion entries. these are used to trigger + * housekeeping for rx descs. we don't use the free interrupt + * as it's not very useful + */ + /* val = CAS_BASE(RX_AE_THRESH_FREE, RX_AE_FREEN_VAL(0)); */ + val = CAS_BASE(RX_AE_THRESH_COMP, RX_AE_COMP_VAL); + writel(val, cp->regs + REG_RX_AE_THRESH); + if (cp->cas_flags & CAS_FLAG_REG_PLUS) { + val = CAS_BASE(RX_AE1_THRESH_FREE, RX_AE_FREEN_VAL(1)); + writel(val, cp->regs + REG_PLUS_RX_AE1_THRESH); + } + + /* Random early detect registers. useful for congestion avoidance. + * this should be tunable. + */ + writel(0x0, cp->regs + REG_RX_RED); + + /* receive page sizes. default == 2K (0x800) */ + val = 0; + if (cp->page_size == 0x1000) + val = 0x1; + else if (cp->page_size == 0x2000) + val = 0x2; + else if (cp->page_size == 0x4000) + val = 0x3; + + /* round mtu + offset. constrain to page size. */ + size = cp->dev->mtu + 64; + if (size > cp->page_size) + size = cp->page_size; + + if (size <= 0x400) + i = 0x0; + else if (size <= 0x800) + i = 0x1; + else if (size <= 0x1000) + i = 0x2; + else + i = 0x3; + + cp->mtu_stride = 1 << (i + 10); + val = CAS_BASE(RX_PAGE_SIZE, val); + val |= CAS_BASE(RX_PAGE_SIZE_MTU_STRIDE, i); + val |= CAS_BASE(RX_PAGE_SIZE_MTU_COUNT, cp->page_size >> (i + 10)); + val |= CAS_BASE(RX_PAGE_SIZE_MTU_OFF, 0x1); + writel(val, cp->regs + REG_RX_PAGE_SIZE); + + /* enable the header parser if desired */ + if (CAS_HP_FIRMWARE == cas_prog_null) + return; + + val = CAS_BASE(HP_CFG_NUM_CPU, CAS_NCPUS > 63 ? 0 : CAS_NCPUS); + val |= HP_CFG_PARSE_EN | HP_CFG_SYN_INC_MASK; + val |= CAS_BASE(HP_CFG_TCP_THRESH, HP_TCP_THRESH_VAL); + writel(val, cp->regs + REG_HP_CFG); +} + +static inline void cas_rxc_init(struct cas_rx_comp *rxc) +{ + memset(rxc, 0, sizeof(*rxc)); + rxc->word4 = cpu_to_le64(RX_COMP4_ZERO); +} + +/* NOTE: we use the ENC RX DESC ring for spares. the rx_page[0,1] + * flipping is protected by the fact that the chip will not + * hand back the same page index while it's being processed. + */ +static inline cas_page_t *cas_page_spare(struct cas *cp, const int index) +{ + cas_page_t *page = cp->rx_pages[1][index]; + cas_page_t *new; + + if (page_count(page->buffer) == 1) + return page; + + new = cas_page_dequeue(cp); + if (new) { + spin_lock(&cp->rx_inuse_lock); + list_add(&page->list, &cp->rx_inuse_list); + spin_unlock(&cp->rx_inuse_lock); + } + return new; +} + +/* this needs to be changed if we actually use the ENC RX DESC ring */ +static cas_page_t *cas_page_swap(struct cas *cp, const int ring, + const int index) +{ + cas_page_t **page0 = cp->rx_pages[0]; + cas_page_t **page1 = cp->rx_pages[1]; + + /* swap if buffer is in use */ + if (page_count(page0[index]->buffer) > 1) { + cas_page_t *new = cas_page_spare(cp, index); + if (new) { + page1[index] = page0[index]; + page0[index] = new; + } + } + RX_USED_SET(page0[index], 0); + return page0[index]; +} + +static void cas_clean_rxds(struct cas *cp) +{ + /* only clean ring 0 as ring 1 is used for spare buffers */ + struct cas_rx_desc *rxd = cp->init_rxds[0]; + int i, size; + + /* release all rx flows */ + for (i = 0; i < N_RX_FLOWS; i++) { + struct sk_buff *skb; + while ((skb = __skb_dequeue(&cp->rx_flows[i]))) { + cas_skb_release(skb); + } + } + + /* initialize descriptors */ + size = RX_DESC_RINGN_SIZE(0); + for (i = 0; i < size; i++) { + cas_page_t *page = cas_page_swap(cp, 0, i); + rxd[i].buffer = cpu_to_le64(page->dma_addr); + rxd[i].index = cpu_to_le64(CAS_BASE(RX_INDEX_NUM, i) | + CAS_BASE(RX_INDEX_RING, 0)); + } + + cp->rx_old[0] = RX_DESC_RINGN_SIZE(0) - 4; + cp->rx_last[0] = 0; + cp->cas_flags &= ~CAS_FLAG_RXD_POST(0); +} + +static void cas_clean_rxcs(struct cas *cp) +{ + int i, j; + + /* take ownership of rx comp descriptors */ + memset(cp->rx_cur, 0, sizeof(*cp->rx_cur)*N_RX_COMP_RINGS); + memset(cp->rx_new, 0, sizeof(*cp->rx_new)*N_RX_COMP_RINGS); + for (i = 0; i < N_RX_COMP_RINGS; i++) { + struct cas_rx_comp *rxc = cp->init_rxcs[i]; + for (j = 0; j < RX_COMP_RINGN_SIZE(i); j++) { + cas_rxc_init(rxc + j); + } + } +} + +#if 0 +/* When we get a RX fifo overflow, the RX unit is probably hung + * so we do the following. + * + * If any part of the reset goes wrong, we return 1 and that causes the + * whole chip to be reset. + */ +static int cas_rxmac_reset(struct cas *cp) +{ + struct net_device *dev = cp->dev; + int limit; + u32 val; + + /* First, reset MAC RX. */ + writel(cp->mac_rx_cfg & ~MAC_RX_CFG_EN, cp->regs + REG_MAC_RX_CFG); + for (limit = 0; limit < STOP_TRIES; limit++) { + if (!(readl(cp->regs + REG_MAC_RX_CFG) & MAC_RX_CFG_EN)) + break; + udelay(10); + } + if (limit == STOP_TRIES) { + printk(KERN_ERR "%s: RX MAC will not disable, resetting whole " + "chip.\n", dev->name); + return 1; + } + + /* Second, disable RX DMA. */ + writel(0, cp->regs + REG_RX_CFG); + for (limit = 0; limit < STOP_TRIES; limit++) { + if (!(readl(cp->regs + REG_RX_CFG) & RX_CFG_DMA_EN)) + break; + udelay(10); + } + if (limit == STOP_TRIES) { + printk(KERN_ERR "%s: RX DMA will not disable, resetting whole " + "chip.\n", dev->name); + return 1; + } + + mdelay(5); + + /* Execute RX reset command. */ + writel(SW_RESET_RX, cp->regs + REG_SW_RESET); + for (limit = 0; limit < STOP_TRIES; limit++) { + if (!(readl(cp->regs + REG_SW_RESET) & SW_RESET_RX)) + break; + udelay(10); + } + if (limit == STOP_TRIES) { + printk(KERN_ERR "%s: RX reset command will not execute, " + "resetting whole chip.\n", dev->name); + return 1; + } + + /* reset driver rx state */ + cas_clean_rxds(cp); + cas_clean_rxcs(cp); + + /* Now, reprogram the rest of RX unit. */ + cas_init_rx_dma(cp); + + /* re-enable */ + val = readl(cp->regs + REG_RX_CFG); + writel(val | RX_CFG_DMA_EN, cp->regs + REG_RX_CFG); + writel(MAC_RX_FRAME_RECV, cp->regs + REG_MAC_RX_MASK); + val = readl(cp->regs + REG_MAC_RX_CFG); + writel(val | MAC_RX_CFG_EN, cp->regs + REG_MAC_RX_CFG); + return 0; +} +#endif + +static int cas_rxmac_interrupt(struct net_device *dev, struct cas *cp, + u32 status) +{ + u32 stat = readl(cp->regs + REG_MAC_RX_STATUS); + + if (!stat) + return 0; + + if (netif_msg_intr(cp)) + printk(KERN_DEBUG "%s: rxmac interrupt, stat: 0x%x\n", + cp->dev->name, stat); + + /* these are all rollovers */ + spin_lock(&cp->stat_lock[0]); + if (stat & MAC_RX_ALIGN_ERR) + cp->net_stats[0].rx_frame_errors += 0x10000; + + if (stat & MAC_RX_CRC_ERR) + cp->net_stats[0].rx_crc_errors += 0x10000; + + if (stat & MAC_RX_LEN_ERR) + cp->net_stats[0].rx_length_errors += 0x10000; + + if (stat & MAC_RX_OVERFLOW) { + cp->net_stats[0].rx_over_errors++; + cp->net_stats[0].rx_fifo_errors++; + } + + /* We do not track MAC_RX_FRAME_COUNT and MAC_RX_VIOL_ERR + * events. + */ + spin_unlock(&cp->stat_lock[0]); + return 0; +} + +static int cas_mac_interrupt(struct net_device *dev, struct cas *cp, + u32 status) +{ + u32 stat = readl(cp->regs + REG_MAC_CTRL_STATUS); + + if (!stat) + return 0; + + if (netif_msg_intr(cp)) + printk(KERN_DEBUG "%s: mac interrupt, stat: 0x%x\n", + cp->dev->name, stat); + + /* This interrupt is just for pause frame and pause + * tracking. It is useful for diagnostics and debug + * but probably by default we will mask these events. + */ + if (stat & MAC_CTRL_PAUSE_STATE) + cp->pause_entered++; + + if (stat & MAC_CTRL_PAUSE_RECEIVED) + cp->pause_last_time_recvd = (stat >> 16); + + return 0; +} + + +/* Must be invoked under cp->lock. */ +static inline int cas_mdio_link_not_up(struct cas *cp) +{ + u16 val; + + switch (cp->lstate) { + case link_force_ret: + if (netif_msg_link(cp)) + printk(KERN_INFO "%s: Autoneg failed again, keeping" + " forced mode\n", cp->dev->name); + cas_phy_write(cp, MII_BMCR, cp->link_fcntl); + cp->timer_ticks = 5; + cp->lstate = link_force_ok; + cp->link_transition = LINK_TRANSITION_LINK_CONFIG; + break; + + case link_aneg: + val = cas_phy_read(cp, MII_BMCR); + + /* Try forced modes. we try things in the following order: + * 1000 full -> 100 full/half -> 10 half + */ + val &= ~(BMCR_ANRESTART | BMCR_ANENABLE); + val |= BMCR_FULLDPLX; + val |= (cp->cas_flags & CAS_FLAG_1000MB_CAP) ? + CAS_BMCR_SPEED1000 : BMCR_SPEED100; + cas_phy_write(cp, MII_BMCR, val); + cp->timer_ticks = 5; + cp->lstate = link_force_try; + cp->link_transition = LINK_TRANSITION_LINK_CONFIG; + break; + + case link_force_try: + /* Downgrade from 1000 to 100 to 10 Mbps if necessary. */ + val = cas_phy_read(cp, MII_BMCR); + cp->timer_ticks = 5; + if (val & CAS_BMCR_SPEED1000) { /* gigabit */ + val &= ~CAS_BMCR_SPEED1000; + val |= (BMCR_SPEED100 | BMCR_FULLDPLX); + cas_phy_write(cp, MII_BMCR, val); + break; + } + + if (val & BMCR_SPEED100) { + if (val & BMCR_FULLDPLX) /* fd failed */ + val &= ~BMCR_FULLDPLX; + else { /* 100Mbps failed */ + val &= ~BMCR_SPEED100; + } + cas_phy_write(cp, MII_BMCR, val); + break; + } + default: + break; + } + return 0; +} + + +/* must be invoked with cp->lock held */ +static int cas_mii_link_check(struct cas *cp, const u16 bmsr) +{ + int restart; + + if (bmsr & BMSR_LSTATUS) { + /* Ok, here we got a link. If we had it due to a forced + * fallback, and we were configured for autoneg, we + * retry a short autoneg pass. If you know your hub is + * broken, use ethtool ;) + */ + if ((cp->lstate == link_force_try) && + (cp->link_cntl & BMCR_ANENABLE)) { + cp->lstate = link_force_ret; + cp->link_transition = LINK_TRANSITION_LINK_CONFIG; + cas_mif_poll(cp, 0); + cp->link_fcntl = cas_phy_read(cp, MII_BMCR); + cp->timer_ticks = 5; + if (cp->opened && netif_msg_link(cp)) + printk(KERN_INFO "%s: Got link after fallback, retrying" + " autoneg once...\n", cp->dev->name); + cas_phy_write(cp, MII_BMCR, + cp->link_fcntl | BMCR_ANENABLE | + BMCR_ANRESTART); + cas_mif_poll(cp, 1); + + } else if (cp->lstate != link_up) { + cp->lstate = link_up; + cp->link_transition = LINK_TRANSITION_LINK_UP; + + if (cp->opened) { + cas_set_link_modes(cp); + netif_carrier_on(cp->dev); + } + } + return 0; + } + + /* link not up. if the link was previously up, we restart the + * whole process + */ + restart = 0; + if (cp->lstate == link_up) { + cp->lstate = link_down; + cp->link_transition = LINK_TRANSITION_LINK_DOWN; + + netif_carrier_off(cp->dev); + if (cp->opened && netif_msg_link(cp)) + printk(KERN_INFO "%s: Link down\n", + cp->dev->name); + restart = 1; + + } else if (++cp->timer_ticks > 10) + cas_mdio_link_not_up(cp); + + return restart; +} + +static int cas_mif_interrupt(struct net_device *dev, struct cas *cp, + u32 status) +{ + u32 stat = readl(cp->regs + REG_MIF_STATUS); + u16 bmsr; + + /* check for a link change */ + if (CAS_VAL(MIF_STATUS_POLL_STATUS, stat) == 0) + return 0; + + bmsr = CAS_VAL(MIF_STATUS_POLL_DATA, stat); + return cas_mii_link_check(cp, bmsr); +} + +static int cas_pci_interrupt(struct net_device *dev, struct cas *cp, + u32 status) +{ + u32 stat = readl(cp->regs + REG_PCI_ERR_STATUS); + + if (!stat) + return 0; + + printk(KERN_ERR "%s: PCI error [%04x:%04x] ", dev->name, stat, + readl(cp->regs + REG_BIM_DIAG)); + + /* cassini+ has this reserved */ + if ((stat & PCI_ERR_BADACK) && + ((cp->cas_flags & CAS_FLAG_REG_PLUS) == 0)) + printk(" "); + + if (stat & PCI_ERR_DTRTO) + printk(" "); + if (stat & PCI_ERR_OTHER) + printk(" "); + if (stat & PCI_ERR_BIM_DMA_WRITE) + printk(" "); + if (stat & PCI_ERR_BIM_DMA_READ) + printk(" "); + printk("\n"); + + if (stat & PCI_ERR_OTHER) { + u16 cfg; + + /* Interrogate PCI config space for the + * true cause. + */ + pci_read_config_word(cp->pdev, PCI_STATUS, &cfg); + printk(KERN_ERR "%s: Read PCI cfg space status [%04x]\n", + dev->name, cfg); + if (cfg & PCI_STATUS_PARITY) + printk(KERN_ERR "%s: PCI parity error detected.\n", + dev->name); + if (cfg & PCI_STATUS_SIG_TARGET_ABORT) + printk(KERN_ERR "%s: PCI target abort.\n", + dev->name); + if (cfg & PCI_STATUS_REC_TARGET_ABORT) + printk(KERN_ERR "%s: PCI master acks target abort.\n", + dev->name); + if (cfg & PCI_STATUS_REC_MASTER_ABORT) + printk(KERN_ERR "%s: PCI master abort.\n", dev->name); + if (cfg & PCI_STATUS_SIG_SYSTEM_ERROR) + printk(KERN_ERR "%s: PCI system error SERR#.\n", + dev->name); + if (cfg & PCI_STATUS_DETECTED_PARITY) + printk(KERN_ERR "%s: PCI parity error.\n", + dev->name); + + /* Write the error bits back to clear them. */ + cfg &= (PCI_STATUS_PARITY | + PCI_STATUS_SIG_TARGET_ABORT | + PCI_STATUS_REC_TARGET_ABORT | + PCI_STATUS_REC_MASTER_ABORT | + PCI_STATUS_SIG_SYSTEM_ERROR | + PCI_STATUS_DETECTED_PARITY); + pci_write_config_word(cp->pdev, PCI_STATUS, cfg); + } + + /* For all PCI errors, we should reset the chip. */ + return 1; +} + +/* All non-normal interrupt conditions get serviced here. + * Returns non-zero if we should just exit the interrupt + * handler right now (ie. if we reset the card which invalidates + * all of the other original irq status bits). + */ +static int cas_abnormal_irq(struct net_device *dev, struct cas *cp, + u32 status) +{ + if (status & INTR_RX_TAG_ERROR) { + /* corrupt RX tag framing */ + if (netif_msg_rx_err(cp)) + printk(KERN_DEBUG "%s: corrupt rx tag framing\n", + cp->dev->name); + spin_lock(&cp->stat_lock[0]); + cp->net_stats[0].rx_errors++; + spin_unlock(&cp->stat_lock[0]); + goto do_reset; + } + + if (status & INTR_RX_LEN_MISMATCH) { + /* length mismatch. */ + if (netif_msg_rx_err(cp)) + printk(KERN_DEBUG "%s: length mismatch for rx frame\n", + cp->dev->name); + spin_lock(&cp->stat_lock[0]); + cp->net_stats[0].rx_errors++; + spin_unlock(&cp->stat_lock[0]); + goto do_reset; + } + + if (status & INTR_PCS_STATUS) { + if (cas_pcs_interrupt(dev, cp, status)) + goto do_reset; + } + + if (status & INTR_TX_MAC_STATUS) { + if (cas_txmac_interrupt(dev, cp, status)) + goto do_reset; + } + + if (status & INTR_RX_MAC_STATUS) { + if (cas_rxmac_interrupt(dev, cp, status)) + goto do_reset; + } + + if (status & INTR_MAC_CTRL_STATUS) { + if (cas_mac_interrupt(dev, cp, status)) + goto do_reset; + } + + if (status & INTR_MIF_STATUS) { + if (cas_mif_interrupt(dev, cp, status)) + goto do_reset; + } + + if (status & INTR_PCI_ERROR_STATUS) { + if (cas_pci_interrupt(dev, cp, status)) + goto do_reset; + } + return 0; + +do_reset: +#if 1 + atomic_inc(&cp->reset_task_pending); + atomic_inc(&cp->reset_task_pending_all); + printk(KERN_ERR "%s:reset called in cas_abnormal_irq [0x%x]\n", + dev->name, status); + schedule_work(&cp->reset_task); +#else + atomic_set(&cp->reset_task_pending, CAS_RESET_ALL); + printk(KERN_ERR "reset called in cas_abnormal_irq\n"); + schedule_work(&cp->reset_task); +#endif + return 1; +} + +/* NOTE: CAS_TABORT returns 1 or 2 so that it can be used when + * determining whether to do a netif_stop/wakeup + */ +#define CAS_TABORT(x) (((x)->cas_flags & CAS_FLAG_TARGET_ABORT) ? 2 : 1) +#define CAS_ROUND_PAGE(x) (((x) + PAGE_SIZE - 1) & PAGE_MASK) +static inline int cas_calc_tabort(struct cas *cp, const unsigned long addr, + const int len) +{ + unsigned long off = addr + len; + + if (CAS_TABORT(cp) == 1) + return 0; + if ((CAS_ROUND_PAGE(off) - off) > TX_TARGET_ABORT_LEN) + return 0; + return TX_TARGET_ABORT_LEN; +} + +static inline void cas_tx_ringN(struct cas *cp, int ring, int limit) +{ + struct cas_tx_desc *txds; + struct sk_buff **skbs; + struct net_device *dev = cp->dev; + int entry, count; + + spin_lock(&cp->tx_lock[ring]); + txds = cp->init_txds[ring]; + skbs = cp->tx_skbs[ring]; + entry = cp->tx_old[ring]; + + count = TX_BUFF_COUNT(ring, entry, limit); + while (entry != limit) { + struct sk_buff *skb = skbs[entry]; + dma_addr_t daddr; + u32 dlen; + int frag; + + if (!skb) { + /* this should never occur */ + entry = TX_DESC_NEXT(ring, entry); + continue; + } + + /* however, we might get only a partial skb release. */ + count -= skb_shinfo(skb)->nr_frags + + + cp->tx_tiny_use[ring][entry].nbufs + 1; + if (count < 0) + break; + + if (netif_msg_tx_done(cp)) + printk(KERN_DEBUG "%s: tx[%d] done, slot %d\n", + cp->dev->name, ring, entry); + + skbs[entry] = NULL; + cp->tx_tiny_use[ring][entry].nbufs = 0; + + for (frag = 0; frag <= skb_shinfo(skb)->nr_frags; frag++) { + struct cas_tx_desc *txd = txds + entry; + + daddr = le64_to_cpu(txd->buffer); + dlen = CAS_VAL(TX_DESC_BUFLEN, + le64_to_cpu(txd->control)); + pci_unmap_page(cp->pdev, daddr, dlen, + PCI_DMA_TODEVICE); + entry = TX_DESC_NEXT(ring, entry); + + /* tiny buffer may follow */ + if (cp->tx_tiny_use[ring][entry].used) { + cp->tx_tiny_use[ring][entry].used = 0; + entry = TX_DESC_NEXT(ring, entry); + } + } + + spin_lock(&cp->stat_lock[ring]); + cp->net_stats[ring].tx_packets++; + cp->net_stats[ring].tx_bytes += skb->len; + spin_unlock(&cp->stat_lock[ring]); + dev_kfree_skb_irq(skb); + } + cp->tx_old[ring] = entry; + + /* this is wrong for multiple tx rings. the net device needs + * multiple queues for this to do the right thing. we wait + * for 2*packets to be available when using tiny buffers + */ + if (netif_queue_stopped(dev) && + (TX_BUFFS_AVAIL(cp, ring) > CAS_TABORT(cp)*(MAX_SKB_FRAGS + 1))) + netif_wake_queue(dev); + spin_unlock(&cp->tx_lock[ring]); +} + +static void cas_tx(struct net_device *dev, struct cas *cp, + u32 status) +{ + int limit, ring; +#ifdef USE_TX_COMPWB + u64 compwb = le64_to_cpu(cp->init_block->tx_compwb); +#endif + if (netif_msg_intr(cp)) + printk(KERN_DEBUG "%s: tx interrupt, status: 0x%x, %lx\n", + cp->dev->name, status, compwb); + /* process all the rings */ + for (ring = 0; ring < N_TX_RINGS; ring++) { +#ifdef USE_TX_COMPWB + /* use the completion writeback registers */ + limit = (CAS_VAL(TX_COMPWB_MSB, compwb) << 8) | + CAS_VAL(TX_COMPWB_LSB, compwb); + compwb = TX_COMPWB_NEXT(compwb); +#else + limit = readl(cp->regs + REG_TX_COMPN(ring)); +#endif + if (cp->tx_old[ring] != limit) + cas_tx_ringN(cp, ring, limit); + } +} + + +static int cas_rx_process_pkt(struct cas *cp, struct cas_rx_comp *rxc, + int entry, const u64 *words, + struct sk_buff **skbref) +{ + int dlen, hlen, len, i, alloclen; + int off, swivel = RX_SWIVEL_OFF_VAL; + struct cas_page *page; + struct sk_buff *skb; + void *addr, *crcaddr; + char *p; + + hlen = CAS_VAL(RX_COMP2_HDR_SIZE, words[1]); + dlen = CAS_VAL(RX_COMP1_DATA_SIZE, words[0]); + len = hlen + dlen; + + if (RX_COPY_ALWAYS || (words[2] & RX_COMP3_SMALL_PKT)) + alloclen = len; + else + alloclen = max(hlen, RX_COPY_MIN); + + skb = dev_alloc_skb(alloclen + swivel + cp->crc_size); + if (skb == NULL) + return -1; + + *skbref = skb; + skb->dev = cp->dev; + skb_reserve(skb, swivel); + + p = skb->data; + addr = crcaddr = NULL; + if (hlen) { /* always copy header pages */ + i = CAS_VAL(RX_COMP2_HDR_INDEX, words[1]); + page = cp->rx_pages[CAS_VAL(RX_INDEX_RING, i)][CAS_VAL(RX_INDEX_NUM, i)]; + off = CAS_VAL(RX_COMP2_HDR_OFF, words[1]) * 0x100 + + swivel; + + i = hlen; + if (!dlen) /* attach FCS */ + i += cp->crc_size; + pci_dma_sync_single_for_cpu(cp->pdev, page->dma_addr + off, i, + PCI_DMA_FROMDEVICE); + addr = cas_page_map(page->buffer); + memcpy(p, addr + off, i); + pci_dma_sync_single_for_device(cp->pdev, page->dma_addr + off, i, + PCI_DMA_FROMDEVICE); + cas_page_unmap(addr); + RX_USED_ADD(page, 0x100); + p += hlen; + swivel = 0; + } + + + if (alloclen < (hlen + dlen)) { + skb_frag_t *frag = skb_shinfo(skb)->frags; + + /* normal or jumbo packets. we use frags */ + i = CAS_VAL(RX_COMP1_DATA_INDEX, words[0]); + page = cp->rx_pages[CAS_VAL(RX_INDEX_RING, i)][CAS_VAL(RX_INDEX_NUM, i)]; + off = CAS_VAL(RX_COMP1_DATA_OFF, words[0]) + swivel; + + hlen = min(cp->page_size - off, dlen); + if (hlen < 0) { + if (netif_msg_rx_err(cp)) { + printk(KERN_DEBUG "%s: rx page overflow: " + "%d\n", cp->dev->name, hlen); + } + dev_kfree_skb_irq(skb); + return -1; + } + i = hlen; + if (i == dlen) /* attach FCS */ + i += cp->crc_size; + pci_dma_sync_single_for_cpu(cp->pdev, page->dma_addr + off, i, + PCI_DMA_FROMDEVICE); + + /* make sure we always copy a header */ + swivel = 0; + if (p == (char *) skb->data) { /* not split */ + addr = cas_page_map(page->buffer); + memcpy(p, addr + off, RX_COPY_MIN); + pci_dma_sync_single_for_device(cp->pdev, page->dma_addr + off, i, + PCI_DMA_FROMDEVICE); + cas_page_unmap(addr); + off += RX_COPY_MIN; + swivel = RX_COPY_MIN; + RX_USED_ADD(page, cp->mtu_stride); + } else { + RX_USED_ADD(page, hlen); + } + skb_put(skb, alloclen); + + skb_shinfo(skb)->nr_frags++; + skb->data_len += hlen - swivel; + skb->len += hlen - swivel; + + get_page(page->buffer); + frag->page = page->buffer; + frag->page_offset = off; + frag->size = hlen - swivel; + + /* any more data? */ + if ((words[0] & RX_COMP1_SPLIT_PKT) && ((dlen -= hlen) > 0)) { + hlen = dlen; + off = 0; + + i = CAS_VAL(RX_COMP2_NEXT_INDEX, words[1]); + page = cp->rx_pages[CAS_VAL(RX_INDEX_RING, i)][CAS_VAL(RX_INDEX_NUM, i)]; + pci_dma_sync_single_for_cpu(cp->pdev, page->dma_addr, + hlen + cp->crc_size, + PCI_DMA_FROMDEVICE); + pci_dma_sync_single_for_device(cp->pdev, page->dma_addr, + hlen + cp->crc_size, + PCI_DMA_FROMDEVICE); + + skb_shinfo(skb)->nr_frags++; + skb->data_len += hlen; + skb->len += hlen; + frag++; + + get_page(page->buffer); + frag->page = page->buffer; + frag->page_offset = 0; + frag->size = hlen; + RX_USED_ADD(page, hlen + cp->crc_size); + } + + if (cp->crc_size) { + addr = cas_page_map(page->buffer); + crcaddr = addr + off + hlen; + } + + } else { + /* copying packet */ + if (!dlen) + goto end_copy_pkt; + + i = CAS_VAL(RX_COMP1_DATA_INDEX, words[0]); + page = cp->rx_pages[CAS_VAL(RX_INDEX_RING, i)][CAS_VAL(RX_INDEX_NUM, i)]; + off = CAS_VAL(RX_COMP1_DATA_OFF, words[0]) + swivel; + hlen = min(cp->page_size - off, dlen); + if (hlen < 0) { + if (netif_msg_rx_err(cp)) { + printk(KERN_DEBUG "%s: rx page overflow: " + "%d\n", cp->dev->name, hlen); + } + dev_kfree_skb_irq(skb); + return -1; + } + i = hlen; + if (i == dlen) /* attach FCS */ + i += cp->crc_size; + pci_dma_sync_single_for_cpu(cp->pdev, page->dma_addr + off, i, + PCI_DMA_FROMDEVICE); + addr = cas_page_map(page->buffer); + memcpy(p, addr + off, i); + pci_dma_sync_single_for_device(cp->pdev, page->dma_addr + off, i, + PCI_DMA_FROMDEVICE); + cas_page_unmap(addr); + if (p == (char *) skb->data) /* not split */ + RX_USED_ADD(page, cp->mtu_stride); + else + RX_USED_ADD(page, i); + + /* any more data? */ + if ((words[0] & RX_COMP1_SPLIT_PKT) && ((dlen -= hlen) > 0)) { + p += hlen; + i = CAS_VAL(RX_COMP2_NEXT_INDEX, words[1]); + page = cp->rx_pages[CAS_VAL(RX_INDEX_RING, i)][CAS_VAL(RX_INDEX_NUM, i)]; + pci_dma_sync_single_for_cpu(cp->pdev, page->dma_addr, + dlen + cp->crc_size, + PCI_DMA_FROMDEVICE); + addr = cas_page_map(page->buffer); + memcpy(p, addr, dlen + cp->crc_size); + pci_dma_sync_single_for_device(cp->pdev, page->dma_addr, + dlen + cp->crc_size, + PCI_DMA_FROMDEVICE); + cas_page_unmap(addr); + RX_USED_ADD(page, dlen + cp->crc_size); + } +end_copy_pkt: + if (cp->crc_size) { + addr = NULL; + crcaddr = skb->data + alloclen; + } + skb_put(skb, alloclen); + } + + i = CAS_VAL(RX_COMP4_TCP_CSUM, words[3]); + if (cp->crc_size) { + /* checksum includes FCS. strip it out. */ + i = csum_fold(csum_partial(crcaddr, cp->crc_size, i)); + if (addr) + cas_page_unmap(addr); + } + skb->csum = ntohs(i ^ 0xffff); + skb->ip_summed = CHECKSUM_HW; + skb->protocol = eth_type_trans(skb, cp->dev); + return len; +} + + +/* we can handle up to 64 rx flows at a time. we do the same thing + * as nonreassm except that we batch up the buffers. + * NOTE: we currently just treat each flow as a bunch of packets that + * we pass up. a better way would be to coalesce the packets + * into a jumbo packet. to do that, we need to do the following: + * 1) the first packet will have a clean split between header and + * data. save both. + * 2) each time the next flow packet comes in, extend the + * data length and merge the checksums. + * 3) on flow release, fix up the header. + * 4) make sure the higher layer doesn't care. + * because packets get coalesced, we shouldn't run into fragment count + * issues. + */ +static inline void cas_rx_flow_pkt(struct cas *cp, const u64 *words, + struct sk_buff *skb) +{ + int flowid = CAS_VAL(RX_COMP3_FLOWID, words[2]) & (N_RX_FLOWS - 1); + struct sk_buff_head *flow = &cp->rx_flows[flowid]; + + /* this is protected at a higher layer, so no need to + * do any additional locking here. stick the buffer + * at the end. + */ + __skb_insert(skb, flow->prev, (struct sk_buff *) flow, flow); + if (words[0] & RX_COMP1_RELEASE_FLOW) { + while ((skb = __skb_dequeue(flow))) { + cas_skb_release(skb); + } + } +} + +/* put rx descriptor back on ring. if a buffer is in use by a higher + * layer, this will need to put in a replacement. + */ +static void cas_post_page(struct cas *cp, const int ring, const int index) +{ + cas_page_t *new; + int entry; + + entry = cp->rx_old[ring]; + + new = cas_page_swap(cp, ring, index); + cp->init_rxds[ring][entry].buffer = cpu_to_le64(new->dma_addr); + cp->init_rxds[ring][entry].index = + cpu_to_le64(CAS_BASE(RX_INDEX_NUM, index) | + CAS_BASE(RX_INDEX_RING, ring)); + + entry = RX_DESC_ENTRY(ring, entry + 1); + cp->rx_old[ring] = entry; + + if (entry % 4) + return; + + if (ring == 0) + writel(entry, cp->regs + REG_RX_KICK); + else if ((N_RX_DESC_RINGS > 1) && + (cp->cas_flags & CAS_FLAG_REG_PLUS)) + writel(entry, cp->regs + REG_PLUS_RX_KICK1); +} + + +/* only when things are bad */ +static int cas_post_rxds_ringN(struct cas *cp, int ring, int num) +{ + unsigned int entry, last, count, released; + int cluster; + cas_page_t **page = cp->rx_pages[ring]; + + entry = cp->rx_old[ring]; + + if (netif_msg_intr(cp)) + printk(KERN_DEBUG "%s: rxd[%d] interrupt, done: %d\n", + cp->dev->name, ring, entry); + + cluster = -1; + count = entry & 0x3; + last = RX_DESC_ENTRY(ring, num ? entry + num - 4: entry - 4); + released = 0; + while (entry != last) { + /* make a new buffer if it's still in use */ + if (page_count(page[entry]->buffer) > 1) { + cas_page_t *new = cas_page_dequeue(cp); + if (!new) { + /* let the timer know that we need to + * do this again + */ + cp->cas_flags |= CAS_FLAG_RXD_POST(ring); + if (!timer_pending(&cp->link_timer)) + mod_timer(&cp->link_timer, jiffies + + CAS_LINK_FAST_TIMEOUT); + cp->rx_old[ring] = entry; + cp->rx_last[ring] = num ? num - released : 0; + return -ENOMEM; + } + spin_lock(&cp->rx_inuse_lock); + list_add(&page[entry]->list, &cp->rx_inuse_list); + spin_unlock(&cp->rx_inuse_lock); + cp->init_rxds[ring][entry].buffer = + cpu_to_le64(new->dma_addr); + page[entry] = new; + + } + + if (++count == 4) { + cluster = entry; + count = 0; + } + released++; + entry = RX_DESC_ENTRY(ring, entry + 1); + } + cp->rx_old[ring] = entry; + + if (cluster < 0) + return 0; + + if (ring == 0) + writel(cluster, cp->regs + REG_RX_KICK); + else if ((N_RX_DESC_RINGS > 1) && + (cp->cas_flags & CAS_FLAG_REG_PLUS)) + writel(cluster, cp->regs + REG_PLUS_RX_KICK1); + return 0; +} + + +/* process a completion ring. packets are set up in three basic ways: + * small packets: should be copied header + data in single buffer. + * large packets: header and data in a single buffer. + * split packets: header in a separate buffer from data. + * data may be in multiple pages. data may be > 256 + * bytes but in a single page. + * + * NOTE: RX page posting is done in this routine as well. while there's + * the capability of using multiple RX completion rings, it isn't + * really worthwhile due to the fact that the page posting will + * force serialization on the single descriptor ring. + */ +static int cas_rx_ringN(struct cas *cp, int ring, int budget) +{ + struct cas_rx_comp *rxcs = cp->init_rxcs[ring]; + int entry, drops; + int npackets = 0; + + if (netif_msg_intr(cp)) + printk(KERN_DEBUG "%s: rx[%d] interrupt, done: %d/%d\n", + cp->dev->name, ring, + readl(cp->regs + REG_RX_COMP_HEAD), + cp->rx_new[ring]); + + entry = cp->rx_new[ring]; + drops = 0; + while (1) { + struct cas_rx_comp *rxc = rxcs + entry; + struct sk_buff *skb; + int type, len; + u64 words[4]; + int i, dring; + + words[0] = le64_to_cpu(rxc->word1); + words[1] = le64_to_cpu(rxc->word2); + words[2] = le64_to_cpu(rxc->word3); + words[3] = le64_to_cpu(rxc->word4); + + /* don't touch if still owned by hw */ + type = CAS_VAL(RX_COMP1_TYPE, words[0]); + if (type == 0) + break; + + /* hw hasn't cleared the zero bit yet */ + if (words[3] & RX_COMP4_ZERO) { + break; + } + + /* get info on the packet */ + if (words[3] & (RX_COMP4_LEN_MISMATCH | RX_COMP4_BAD)) { + spin_lock(&cp->stat_lock[ring]); + cp->net_stats[ring].rx_errors++; + if (words[3] & RX_COMP4_LEN_MISMATCH) + cp->net_stats[ring].rx_length_errors++; + if (words[3] & RX_COMP4_BAD) + cp->net_stats[ring].rx_crc_errors++; + spin_unlock(&cp->stat_lock[ring]); + + /* We'll just return it to Cassini. */ + drop_it: + spin_lock(&cp->stat_lock[ring]); + ++cp->net_stats[ring].rx_dropped; + spin_unlock(&cp->stat_lock[ring]); + goto next; + } + + len = cas_rx_process_pkt(cp, rxc, entry, words, &skb); + if (len < 0) { + ++drops; + goto drop_it; + } + + /* see if it's a flow re-assembly or not. the driver + * itself handles release back up. + */ + if (RX_DONT_BATCH || (type == 0x2)) { + /* non-reassm: these always get released */ + cas_skb_release(skb); + } else { + cas_rx_flow_pkt(cp, words, skb); + } + + spin_lock(&cp->stat_lock[ring]); + cp->net_stats[ring].rx_packets++; + cp->net_stats[ring].rx_bytes += len; + spin_unlock(&cp->stat_lock[ring]); + cp->dev->last_rx = jiffies; + + next: + npackets++; + + /* should it be released? */ + if (words[0] & RX_COMP1_RELEASE_HDR) { + i = CAS_VAL(RX_COMP2_HDR_INDEX, words[1]); + dring = CAS_VAL(RX_INDEX_RING, i); + i = CAS_VAL(RX_INDEX_NUM, i); + cas_post_page(cp, dring, i); + } + + if (words[0] & RX_COMP1_RELEASE_DATA) { + i = CAS_VAL(RX_COMP1_DATA_INDEX, words[0]); + dring = CAS_VAL(RX_INDEX_RING, i); + i = CAS_VAL(RX_INDEX_NUM, i); + cas_post_page(cp, dring, i); + } + + if (words[0] & RX_COMP1_RELEASE_NEXT) { + i = CAS_VAL(RX_COMP2_NEXT_INDEX, words[1]); + dring = CAS_VAL(RX_INDEX_RING, i); + i = CAS_VAL(RX_INDEX_NUM, i); + cas_post_page(cp, dring, i); + } + + /* skip to the next entry */ + entry = RX_COMP_ENTRY(ring, entry + 1 + + CAS_VAL(RX_COMP1_SKIP, words[0])); +#ifdef USE_NAPI + if (budget && (npackets >= budget)) + break; +#endif + } + cp->rx_new[ring] = entry; + + if (drops) + printk(KERN_INFO "%s: Memory squeeze, deferring packet.\n", + cp->dev->name); + return npackets; +} + + +/* put completion entries back on the ring */ +static void cas_post_rxcs_ringN(struct net_device *dev, + struct cas *cp, int ring) +{ + struct cas_rx_comp *rxc = cp->init_rxcs[ring]; + int last, entry; + + last = cp->rx_cur[ring]; + entry = cp->rx_new[ring]; + if (netif_msg_intr(cp)) + printk(KERN_DEBUG "%s: rxc[%d] interrupt, done: %d/%d\n", + dev->name, ring, readl(cp->regs + REG_RX_COMP_HEAD), + entry); + + /* zero and re-mark descriptors */ + while (last != entry) { + cas_rxc_init(rxc + last); + last = RX_COMP_ENTRY(ring, last + 1); + } + cp->rx_cur[ring] = last; + + if (ring == 0) + writel(last, cp->regs + REG_RX_COMP_TAIL); + else if (cp->cas_flags & CAS_FLAG_REG_PLUS) + writel(last, cp->regs + REG_PLUS_RX_COMPN_TAIL(ring)); +} + + + +/* cassini can use all four PCI interrupts for the completion ring. + * rings 3 and 4 are identical + */ +#if defined(USE_PCI_INTC) || defined(USE_PCI_INTD) +static inline void cas_handle_irqN(struct net_device *dev, + struct cas *cp, const u32 status, + const int ring) +{ + if (status & (INTR_RX_COMP_FULL_ALT | INTR_RX_COMP_AF_ALT)) + cas_post_rxcs_ringN(dev, cp, ring); +} + +static irqreturn_t cas_interruptN(int irq, void *dev_id, struct pt_regs *regs) +{ + struct net_device *dev = dev_id; + struct cas *cp = netdev_priv(dev); + unsigned long flags; + int ring; + u32 status = readl(cp->regs + REG_PLUS_INTRN_STATUS(ring)); + + /* check for shared irq */ + if (status == 0) + return IRQ_NONE; + + ring = (irq == cp->pci_irq_INTC) ? 2 : 3; + spin_lock_irqsave(&cp->lock, flags); + if (status & INTR_RX_DONE_ALT) { /* handle rx separately */ +#ifdef USE_NAPI + cas_mask_intr(cp); + netif_rx_schedule(dev); +#else + cas_rx_ringN(cp, ring, 0); +#endif + status &= ~INTR_RX_DONE_ALT; + } + + if (status) + cas_handle_irqN(dev, cp, status, ring); + spin_unlock_irqrestore(&cp->lock, flags); + return IRQ_HANDLED; +} +#endif + +#ifdef USE_PCI_INTB +/* everything but rx packets */ +static inline void cas_handle_irq1(struct cas *cp, const u32 status) +{ + if (status & INTR_RX_BUF_UNAVAIL_1) { + /* Frame arrived, no free RX buffers available. + * NOTE: we can get this on a link transition. */ + cas_post_rxds_ringN(cp, 1, 0); + spin_lock(&cp->stat_lock[1]); + cp->net_stats[1].rx_dropped++; + spin_unlock(&cp->stat_lock[1]); + } + + if (status & INTR_RX_BUF_AE_1) + cas_post_rxds_ringN(cp, 1, RX_DESC_RINGN_SIZE(1) - + RX_AE_FREEN_VAL(1)); + + if (status & (INTR_RX_COMP_AF | INTR_RX_COMP_FULL)) + cas_post_rxcs_ringN(cp, 1); +} + +/* ring 2 handles a few more events than 3 and 4 */ +static irqreturn_t cas_interrupt1(int irq, void *dev_id, struct pt_regs *regs) +{ + struct net_device *dev = dev_id; + struct cas *cp = netdev_priv(dev); + unsigned long flags; + u32 status = readl(cp->regs + REG_PLUS_INTRN_STATUS(1)); + + /* check for shared interrupt */ + if (status == 0) + return IRQ_NONE; + + spin_lock_irqsave(&cp->lock, flags); + if (status & INTR_RX_DONE_ALT) { /* handle rx separately */ +#ifdef USE_NAPI + cas_mask_intr(cp); + netif_rx_schedule(dev); +#else + cas_rx_ringN(cp, 1, 0); +#endif + status &= ~INTR_RX_DONE_ALT; + } + if (status) + cas_handle_irq1(cp, status); + spin_unlock_irqrestore(&cp->lock, flags); + return IRQ_HANDLED; +} +#endif + +static inline void cas_handle_irq(struct net_device *dev, + struct cas *cp, const u32 status) +{ + /* housekeeping interrupts */ + if (status & INTR_ERROR_MASK) + cas_abnormal_irq(dev, cp, status); + + if (status & INTR_RX_BUF_UNAVAIL) { + /* Frame arrived, no free RX buffers available. + * NOTE: we can get this on a link transition. + */ + cas_post_rxds_ringN(cp, 0, 0); + spin_lock(&cp->stat_lock[0]); + cp->net_stats[0].rx_dropped++; + spin_unlock(&cp->stat_lock[0]); + } else if (status & INTR_RX_BUF_AE) { + cas_post_rxds_ringN(cp, 0, RX_DESC_RINGN_SIZE(0) - + RX_AE_FREEN_VAL(0)); + } + + if (status & (INTR_RX_COMP_AF | INTR_RX_COMP_FULL)) + cas_post_rxcs_ringN(dev, cp, 0); +} + +static irqreturn_t cas_interrupt(int irq, void *dev_id, struct pt_regs *regs) +{ + struct net_device *dev = dev_id; + struct cas *cp = netdev_priv(dev); + unsigned long flags; + u32 status = readl(cp->regs + REG_INTR_STATUS); + + if (status == 0) + return IRQ_NONE; + + spin_lock_irqsave(&cp->lock, flags); + if (status & (INTR_TX_ALL | INTR_TX_INTME)) { + cas_tx(dev, cp, status); + status &= ~(INTR_TX_ALL | INTR_TX_INTME); + } + + if (status & INTR_RX_DONE) { +#ifdef USE_NAPI + cas_mask_intr(cp); + netif_rx_schedule(dev); +#else + cas_rx_ringN(cp, 0, 0); +#endif + status &= ~INTR_RX_DONE; + } + + if (status) + cas_handle_irq(dev, cp, status); + spin_unlock_irqrestore(&cp->lock, flags); + return IRQ_HANDLED; +} + + +#ifdef USE_NAPI +static int cas_poll(struct net_device *dev, int *budget) +{ + struct cas *cp = netdev_priv(dev); + int i, enable_intr, todo, credits; + u32 status = readl(cp->regs + REG_INTR_STATUS); + unsigned long flags; + + spin_lock_irqsave(&cp->lock, flags); + cas_tx(dev, cp, status); + spin_unlock_irqrestore(&cp->lock, flags); + + /* NAPI rx packets. we spread the credits across all of the + * rxc rings + */ + todo = min(*budget, dev->quota); + + /* to make sure we're fair with the work we loop through each + * ring N_RX_COMP_RING times with a request of + * todo / N_RX_COMP_RINGS + */ + enable_intr = 1; + credits = 0; + for (i = 0; i < N_RX_COMP_RINGS; i++) { + int j; + for (j = 0; j < N_RX_COMP_RINGS; j++) { + credits += cas_rx_ringN(cp, j, todo / N_RX_COMP_RINGS); + if (credits >= todo) { + enable_intr = 0; + goto rx_comp; + } + } + } + +rx_comp: + *budget -= credits; + dev->quota -= credits; + + /* final rx completion */ + spin_lock_irqsave(&cp->lock, flags); + if (status) + cas_handle_irq(dev, cp, status); + +#ifdef USE_PCI_INTB + if (N_RX_COMP_RINGS > 1) { + status = readl(cp->regs + REG_PLUS_INTRN_STATUS(1)); + if (status) + cas_handle_irq1(dev, cp, status); + } +#endif + +#ifdef USE_PCI_INTC + if (N_RX_COMP_RINGS > 2) { + status = readl(cp->regs + REG_PLUS_INTRN_STATUS(2)); + if (status) + cas_handle_irqN(dev, cp, status, 2); + } +#endif + +#ifdef USE_PCI_INTD + if (N_RX_COMP_RINGS > 3) { + status = readl(cp->regs + REG_PLUS_INTRN_STATUS(3)); + if (status) + cas_handle_irqN(dev, cp, status, 3); + } +#endif + spin_unlock_irqrestore(&cp->lock, flags); + if (enable_intr) { + netif_rx_complete(dev); + cas_unmask_intr(cp); + return 0; + } + return 1; +} +#endif + +#ifdef CONFIG_NET_POLL_CONTROLLER +static void cas_netpoll(struct net_device *dev) +{ + struct cas *cp = netdev_priv(dev); + + cas_disable_irq(cp, 0); + cas_interrupt(cp->pdev->irq, dev, NULL); + cas_enable_irq(cp, 0); + +#ifdef USE_PCI_INTB + if (N_RX_COMP_RINGS > 1) { + /* cas_interrupt1(); */ + } +#endif +#ifdef USE_PCI_INTC + if (N_RX_COMP_RINGS > 2) { + /* cas_interruptN(); */ + } +#endif +#ifdef USE_PCI_INTD + if (N_RX_COMP_RINGS > 3) { + /* cas_interruptN(); */ + } +#endif +} +#endif + +static void cas_tx_timeout(struct net_device *dev) +{ + struct cas *cp = netdev_priv(dev); + + printk(KERN_ERR "%s: transmit timed out, resetting\n", dev->name); + if (!cp->hw_running) { + printk("%s: hrm.. hw not running!\n", dev->name); + return; + } + + printk(KERN_ERR "%s: MIF_STATE[%08x]\n", + dev->name, readl(cp->regs + REG_MIF_STATE_MACHINE)); + + printk(KERN_ERR "%s: MAC_STATE[%08x]\n", + dev->name, readl(cp->regs + REG_MAC_STATE_MACHINE)); + + printk(KERN_ERR "%s: TX_STATE[%08x:%08x:%08x] " + "FIFO[%08x:%08x:%08x] SM1[%08x] SM2[%08x]\n", + dev->name, + readl(cp->regs + REG_TX_CFG), + readl(cp->regs + REG_MAC_TX_STATUS), + readl(cp->regs + REG_MAC_TX_CFG), + readl(cp->regs + REG_TX_FIFO_PKT_CNT), + readl(cp->regs + REG_TX_FIFO_WRITE_PTR), + readl(cp->regs + REG_TX_FIFO_READ_PTR), + readl(cp->regs + REG_TX_SM_1), + readl(cp->regs + REG_TX_SM_2)); + + printk(KERN_ERR "%s: RX_STATE[%08x:%08x:%08x]\n", + dev->name, + readl(cp->regs + REG_RX_CFG), + readl(cp->regs + REG_MAC_RX_STATUS), + readl(cp->regs + REG_MAC_RX_CFG)); + + printk(KERN_ERR "%s: HP_STATE[%08x:%08x:%08x:%08x]\n", + dev->name, + readl(cp->regs + REG_HP_STATE_MACHINE), + readl(cp->regs + REG_HP_STATUS0), + readl(cp->regs + REG_HP_STATUS1), + readl(cp->regs + REG_HP_STATUS2)); + +#if 1 + atomic_inc(&cp->reset_task_pending); + atomic_inc(&cp->reset_task_pending_all); + schedule_work(&cp->reset_task); +#else + atomic_set(&cp->reset_task_pending, CAS_RESET_ALL); + schedule_work(&cp->reset_task); +#endif +} + +static inline int cas_intme(int ring, int entry) +{ + /* Algorithm: IRQ every 1/2 of descriptors. */ + if (!(entry & ((TX_DESC_RINGN_SIZE(ring) >> 1) - 1))) + return 1; + return 0; +} + + +static void cas_write_txd(struct cas *cp, int ring, int entry, + dma_addr_t mapping, int len, u64 ctrl, int last) +{ + struct cas_tx_desc *txd = cp->init_txds[ring] + entry; + + ctrl |= CAS_BASE(TX_DESC_BUFLEN, len); + if (cas_intme(ring, entry)) + ctrl |= TX_DESC_INTME; + if (last) + ctrl |= TX_DESC_EOF; + txd->control = cpu_to_le64(ctrl); + txd->buffer = cpu_to_le64(mapping); +} + +static inline void *tx_tiny_buf(struct cas *cp, const int ring, + const int entry) +{ + return cp->tx_tiny_bufs[ring] + TX_TINY_BUF_LEN*entry; +} + +static inline dma_addr_t tx_tiny_map(struct cas *cp, const int ring, + const int entry, const int tentry) +{ + cp->tx_tiny_use[ring][tentry].nbufs++; + cp->tx_tiny_use[ring][entry].used = 1; + return cp->tx_tiny_dvma[ring] + TX_TINY_BUF_LEN*entry; +} + +static inline int cas_xmit_tx_ringN(struct cas *cp, int ring, + struct sk_buff *skb) +{ + struct net_device *dev = cp->dev; + int entry, nr_frags, frag, tabort, tentry; + dma_addr_t mapping; + unsigned long flags; + u64 ctrl; + u32 len; + + spin_lock_irqsave(&cp->tx_lock[ring], flags); + + /* This is a hard error, log it. */ + if (TX_BUFFS_AVAIL(cp, ring) <= + CAS_TABORT(cp)*(skb_shinfo(skb)->nr_frags + 1)) { + netif_stop_queue(dev); + spin_unlock_irqrestore(&cp->tx_lock[ring], flags); + printk(KERN_ERR PFX "%s: BUG! Tx Ring full when " + "queue awake!\n", dev->name); + return 1; + } + + ctrl = 0; + if (skb->ip_summed == CHECKSUM_HW) { + u64 csum_start_off, csum_stuff_off; + + csum_start_off = (u64) (skb->h.raw - skb->data); + csum_stuff_off = (u64) ((skb->h.raw + skb->csum) - skb->data); + + ctrl = TX_DESC_CSUM_EN | + CAS_BASE(TX_DESC_CSUM_START, csum_start_off) | + CAS_BASE(TX_DESC_CSUM_STUFF, csum_stuff_off); + } + + entry = cp->tx_new[ring]; + cp->tx_skbs[ring][entry] = skb; + + nr_frags = skb_shinfo(skb)->nr_frags; + len = skb_headlen(skb); + mapping = pci_map_page(cp->pdev, virt_to_page(skb->data), + offset_in_page(skb->data), len, + PCI_DMA_TODEVICE); + + tentry = entry; + tabort = cas_calc_tabort(cp, (unsigned long) skb->data, len); + if (unlikely(tabort)) { + /* NOTE: len is always > tabort */ + cas_write_txd(cp, ring, entry, mapping, len - tabort, + ctrl | TX_DESC_SOF, 0); + entry = TX_DESC_NEXT(ring, entry); + + memcpy(tx_tiny_buf(cp, ring, entry), skb->data + + len - tabort, tabort); + mapping = tx_tiny_map(cp, ring, entry, tentry); + cas_write_txd(cp, ring, entry, mapping, tabort, ctrl, + (nr_frags == 0)); + } else { + cas_write_txd(cp, ring, entry, mapping, len, ctrl | + TX_DESC_SOF, (nr_frags == 0)); + } + entry = TX_DESC_NEXT(ring, entry); + + for (frag = 0; frag < nr_frags; frag++) { + skb_frag_t *fragp = &skb_shinfo(skb)->frags[frag]; + + len = fragp->size; + mapping = pci_map_page(cp->pdev, fragp->page, + fragp->page_offset, len, + PCI_DMA_TODEVICE); + + tabort = cas_calc_tabort(cp, fragp->page_offset, len); + if (unlikely(tabort)) { + void *addr; + + /* NOTE: len is always > tabort */ + cas_write_txd(cp, ring, entry, mapping, len - tabort, + ctrl, 0); + entry = TX_DESC_NEXT(ring, entry); + + addr = cas_page_map(fragp->page); + memcpy(tx_tiny_buf(cp, ring, entry), + addr + fragp->page_offset + len - tabort, + tabort); + cas_page_unmap(addr); + mapping = tx_tiny_map(cp, ring, entry, tentry); + len = tabort; + } + + cas_write_txd(cp, ring, entry, mapping, len, ctrl, + (frag + 1 == nr_frags)); + entry = TX_DESC_NEXT(ring, entry); + } + + cp->tx_new[ring] = entry; + if (TX_BUFFS_AVAIL(cp, ring) <= CAS_TABORT(cp)*(MAX_SKB_FRAGS + 1)) + netif_stop_queue(dev); + + if (netif_msg_tx_queued(cp)) + printk(KERN_DEBUG "%s: tx[%d] queued, slot %d, skblen %d, " + "avail %d\n", + dev->name, ring, entry, skb->len, + TX_BUFFS_AVAIL(cp, ring)); + writel(entry, cp->regs + REG_TX_KICKN(ring)); + spin_unlock_irqrestore(&cp->tx_lock[ring], flags); + return 0; +} + +static int cas_start_xmit(struct sk_buff *skb, struct net_device *dev) +{ + struct cas *cp = netdev_priv(dev); + + /* this is only used as a load-balancing hint, so it doesn't + * need to be SMP safe + */ + static int ring; + + skb = skb_padto(skb, cp->min_frame_size); + if (!skb) + return 0; + + /* XXX: we need some higher-level QoS hooks to steer packets to + * individual queues. + */ + if (cas_xmit_tx_ringN(cp, ring++ & N_TX_RINGS_MASK, skb)) + return 1; + dev->trans_start = jiffies; + return 0; +} + +static void cas_init_tx_dma(struct cas *cp) +{ + u64 desc_dma = cp->block_dvma; + unsigned long off; + u32 val; + int i; + + /* set up tx completion writeback registers. must be 8-byte aligned */ +#ifdef USE_TX_COMPWB + off = offsetof(struct cas_init_block, tx_compwb); + writel((desc_dma + off) >> 32, cp->regs + REG_TX_COMPWB_DB_HI); + writel((desc_dma + off) & 0xffffffff, cp->regs + REG_TX_COMPWB_DB_LOW); +#endif + + /* enable completion writebacks, enable paced mode, + * disable read pipe, and disable pre-interrupt compwbs + */ + val = TX_CFG_COMPWB_Q1 | TX_CFG_COMPWB_Q2 | + TX_CFG_COMPWB_Q3 | TX_CFG_COMPWB_Q4 | + TX_CFG_DMA_RDPIPE_DIS | TX_CFG_PACED_MODE | + TX_CFG_INTR_COMPWB_DIS; + + /* write out tx ring info and tx desc bases */ + for (i = 0; i < MAX_TX_RINGS; i++) { + off = (unsigned long) cp->init_txds[i] - + (unsigned long) cp->init_block; + + val |= CAS_TX_RINGN_BASE(i); + writel((desc_dma + off) >> 32, cp->regs + REG_TX_DBN_HI(i)); + writel((desc_dma + off) & 0xffffffff, cp->regs + + REG_TX_DBN_LOW(i)); + /* don't zero out the kick register here as the system + * will wedge + */ + } + writel(val, cp->regs + REG_TX_CFG); + + /* program max burst sizes. these numbers should be different + * if doing QoS. + */ +#ifdef USE_QOS + writel(0x800, cp->regs + REG_TX_MAXBURST_0); + writel(0x1600, cp->regs + REG_TX_MAXBURST_1); + writel(0x2400, cp->regs + REG_TX_MAXBURST_2); + writel(0x4800, cp->regs + REG_TX_MAXBURST_3); +#else + writel(0x800, cp->regs + REG_TX_MAXBURST_0); + writel(0x800, cp->regs + REG_TX_MAXBURST_1); + writel(0x800, cp->regs + REG_TX_MAXBURST_2); + writel(0x800, cp->regs + REG_TX_MAXBURST_3); +#endif +} + +/* Must be invoked under cp->lock. */ +static inline void cas_init_dma(struct cas *cp) +{ + cas_init_tx_dma(cp); + cas_init_rx_dma(cp); +} + +/* Must be invoked under cp->lock. */ +static u32 cas_setup_multicast(struct cas *cp) +{ + u32 rxcfg = 0; + int i; + + if (cp->dev->flags & IFF_PROMISC) { + rxcfg |= MAC_RX_CFG_PROMISC_EN; + + } else if (cp->dev->flags & IFF_ALLMULTI) { + for (i=0; i < 16; i++) + writel(0xFFFF, cp->regs + REG_MAC_HASH_TABLEN(i)); + rxcfg |= MAC_RX_CFG_HASH_FILTER_EN; + + } else { + u16 hash_table[16]; + u32 crc; + struct dev_mc_list *dmi = cp->dev->mc_list; + int i; + + /* use the alternate mac address registers for the + * first 15 multicast addresses + */ + for (i = 1; i <= CAS_MC_EXACT_MATCH_SIZE; i++) { + if (!dmi) { + writel(0x0, cp->regs + REG_MAC_ADDRN(i*3 + 0)); + writel(0x0, cp->regs + REG_MAC_ADDRN(i*3 + 1)); + writel(0x0, cp->regs + REG_MAC_ADDRN(i*3 + 2)); + continue; + } + writel((dmi->dmi_addr[4] << 8) | dmi->dmi_addr[5], + cp->regs + REG_MAC_ADDRN(i*3 + 0)); + writel((dmi->dmi_addr[2] << 8) | dmi->dmi_addr[3], + cp->regs + REG_MAC_ADDRN(i*3 + 1)); + writel((dmi->dmi_addr[0] << 8) | dmi->dmi_addr[1], + cp->regs + REG_MAC_ADDRN(i*3 + 2)); + dmi = dmi->next; + } + + /* use hw hash table for the next series of + * multicast addresses + */ + memset(hash_table, 0, sizeof(hash_table)); + while (dmi) { + crc = ether_crc_le(ETH_ALEN, dmi->dmi_addr); + crc >>= 24; + hash_table[crc >> 4] |= 1 << (15 - (crc & 0xf)); + dmi = dmi->next; + } + for (i=0; i < 16; i++) + writel(hash_table[i], cp->regs + + REG_MAC_HASH_TABLEN(i)); + rxcfg |= MAC_RX_CFG_HASH_FILTER_EN; + } + + return rxcfg; +} + +/* must be invoked under cp->stat_lock[N_TX_RINGS] */ +static void cas_clear_mac_err(struct cas *cp) +{ + writel(0, cp->regs + REG_MAC_COLL_NORMAL); + writel(0, cp->regs + REG_MAC_COLL_FIRST); + writel(0, cp->regs + REG_MAC_COLL_EXCESS); + writel(0, cp->regs + REG_MAC_COLL_LATE); + writel(0, cp->regs + REG_MAC_TIMER_DEFER); + writel(0, cp->regs + REG_MAC_ATTEMPTS_PEAK); + writel(0, cp->regs + REG_MAC_RECV_FRAME); + writel(0, cp->regs + REG_MAC_LEN_ERR); + writel(0, cp->regs + REG_MAC_ALIGN_ERR); + writel(0, cp->regs + REG_MAC_FCS_ERR); + writel(0, cp->regs + REG_MAC_RX_CODE_ERR); +} + + +static void cas_mac_reset(struct cas *cp) +{ + int i; + + /* do both TX and RX reset */ + writel(0x1, cp->regs + REG_MAC_TX_RESET); + writel(0x1, cp->regs + REG_MAC_RX_RESET); + + /* wait for TX */ + i = STOP_TRIES; + while (i-- > 0) { + if (readl(cp->regs + REG_MAC_TX_RESET) == 0) + break; + udelay(10); + } + + /* wait for RX */ + i = STOP_TRIES; + while (i-- > 0) { + if (readl(cp->regs + REG_MAC_RX_RESET) == 0) + break; + udelay(10); + } + + if (readl(cp->regs + REG_MAC_TX_RESET) | + readl(cp->regs + REG_MAC_RX_RESET)) + printk(KERN_ERR "%s: mac tx[%d]/rx[%d] reset failed [%08x]\n", + cp->dev->name, readl(cp->regs + REG_MAC_TX_RESET), + readl(cp->regs + REG_MAC_RX_RESET), + readl(cp->regs + REG_MAC_STATE_MACHINE)); +} + + +/* Must be invoked under cp->lock. */ +static void cas_init_mac(struct cas *cp) +{ + unsigned char *e = &cp->dev->dev_addr[0]; + int i; +#ifdef CONFIG_CASSINI_MULTICAST_REG_WRITE + u32 rxcfg; +#endif + cas_mac_reset(cp); + + /* setup core arbitration weight register */ + writel(CAWR_RR_DIS, cp->regs + REG_CAWR); + + /* XXX Use pci_dma_burst_advice() */ +#if !defined(CONFIG_SPARC64) && !defined(CONFIG_ALPHA) + /* set the infinite burst register for chips that don't have + * pci issues. + */ + if ((cp->cas_flags & CAS_FLAG_TARGET_ABORT) == 0) + writel(INF_BURST_EN, cp->regs + REG_INF_BURST); +#endif + + writel(0x1BF0, cp->regs + REG_MAC_SEND_PAUSE); + + writel(0x00, cp->regs + REG_MAC_IPG0); + writel(0x08, cp->regs + REG_MAC_IPG1); + writel(0x04, cp->regs + REG_MAC_IPG2); + + /* change later for 802.3z */ + writel(0x40, cp->regs + REG_MAC_SLOT_TIME); + + /* min frame + FCS */ + writel(ETH_ZLEN + 4, cp->regs + REG_MAC_FRAMESIZE_MIN); + + /* Ethernet payload + header + FCS + optional VLAN tag. NOTE: we + * specify the maximum frame size to prevent RX tag errors on + * oversized frames. + */ + writel(CAS_BASE(MAC_FRAMESIZE_MAX_BURST, 0x2000) | + CAS_BASE(MAC_FRAMESIZE_MAX_FRAME, + (CAS_MAX_MTU + ETH_HLEN + 4 + 4)), + cp->regs + REG_MAC_FRAMESIZE_MAX); + + /* NOTE: crc_size is used as a surrogate for half-duplex. + * workaround saturn half-duplex issue by increasing preamble + * size to 65 bytes. + */ + if ((cp->cas_flags & CAS_FLAG_SATURN) && cp->crc_size) + writel(0x41, cp->regs + REG_MAC_PA_SIZE); + else + writel(0x07, cp->regs + REG_MAC_PA_SIZE); + writel(0x04, cp->regs + REG_MAC_JAM_SIZE); + writel(0x10, cp->regs + REG_MAC_ATTEMPT_LIMIT); + writel(0x8808, cp->regs + REG_MAC_CTRL_TYPE); + + writel((e[5] | (e[4] << 8)) & 0x3ff, cp->regs + REG_MAC_RANDOM_SEED); + + writel(0, cp->regs + REG_MAC_ADDR_FILTER0); + writel(0, cp->regs + REG_MAC_ADDR_FILTER1); + writel(0, cp->regs + REG_MAC_ADDR_FILTER2); + writel(0, cp->regs + REG_MAC_ADDR_FILTER2_1_MASK); + writel(0, cp->regs + REG_MAC_ADDR_FILTER0_MASK); + + /* setup mac address in perfect filter array */ + for (i = 0; i < 45; i++) + writel(0x0, cp->regs + REG_MAC_ADDRN(i)); + + writel((e[4] << 8) | e[5], cp->regs + REG_MAC_ADDRN(0)); + writel((e[2] << 8) | e[3], cp->regs + REG_MAC_ADDRN(1)); + writel((e[0] << 8) | e[1], cp->regs + REG_MAC_ADDRN(2)); + + writel(0x0001, cp->regs + REG_MAC_ADDRN(42)); + writel(0xc200, cp->regs + REG_MAC_ADDRN(43)); + writel(0x0180, cp->regs + REG_MAC_ADDRN(44)); + +#ifndef CONFIG_CASSINI_MULTICAST_REG_WRITE + cp->mac_rx_cfg = cas_setup_multicast(cp); +#else + /* WTZ: Do what Adrian did in cas_set_multicast. Doing + * a writel does not seem to be necessary because Cassini + * seems to preserve the configuration when we do the reset. + * If the chip is in trouble, though, it is not clear if we + * can really count on this behavior. cas_set_multicast uses + * spin_lock_irqsave, but we are called only in cas_init_hw and + * cas_init_hw is protected by cas_lock_all, which calls + * spin_lock_irq (so it doesn't need to save the flags, and + * we should be OK for the writel, as that is the only + * difference). + */ + cp->mac_rx_cfg = rxcfg = cas_setup_multicast(cp); + writel(rxcfg, cp->regs + REG_MAC_RX_CFG); +#endif + spin_lock(&cp->stat_lock[N_TX_RINGS]); + cas_clear_mac_err(cp); + spin_unlock(&cp->stat_lock[N_TX_RINGS]); + + /* Setup MAC interrupts. We want to get all of the interesting + * counter expiration events, but we do not want to hear about + * normal rx/tx as the DMA engine tells us that. + */ + writel(MAC_TX_FRAME_XMIT, cp->regs + REG_MAC_TX_MASK); + writel(MAC_RX_FRAME_RECV, cp->regs + REG_MAC_RX_MASK); + + /* Don't enable even the PAUSE interrupts for now, we + * make no use of those events other than to record them. + */ + writel(0xffffffff, cp->regs + REG_MAC_CTRL_MASK); +} + +/* Must be invoked under cp->lock. */ +static void cas_init_pause_thresholds(struct cas *cp) +{ + /* Calculate pause thresholds. Setting the OFF threshold to the + * full RX fifo size effectively disables PAUSE generation + */ + if (cp->rx_fifo_size <= (2 * 1024)) { + cp->rx_pause_off = cp->rx_pause_on = cp->rx_fifo_size; + } else { + int max_frame = (cp->dev->mtu + ETH_HLEN + 4 + 4 + 64) & ~63; + if (max_frame * 3 > cp->rx_fifo_size) { + cp->rx_pause_off = 7104; + cp->rx_pause_on = 960; + } else { + int off = (cp->rx_fifo_size - (max_frame * 2)); + int on = off - max_frame; + cp->rx_pause_off = off; + cp->rx_pause_on = on; + } + } +} + +static int cas_vpd_match(const void __iomem *p, const char *str) +{ + int len = strlen(str) + 1; + int i; + + for (i = 0; i < len; i++) { + if (readb(p + i) != str[i]) + return 0; + } + return 1; +} + + +/* get the mac address by reading the vpd information in the rom. + * also get the phy type and determine if there's an entropy generator. + * NOTE: this is a bit convoluted for the following reasons: + * 1) vpd info has order-dependent mac addresses for multinic cards + * 2) the only way to determine the nic order is to use the slot + * number. + * 3) fiber cards don't have bridges, so their slot numbers don't + * mean anything. + * 4) we don't actually know we have a fiber card until after + * the mac addresses are parsed. + */ +static int cas_get_vpd_info(struct cas *cp, unsigned char *dev_addr, + const int offset) +{ + void __iomem *p = cp->regs + REG_EXPANSION_ROM_RUN_START; + void __iomem *base, *kstart; + int i, len; + int found = 0; +#define VPD_FOUND_MAC 0x01 +#define VPD_FOUND_PHY 0x02 + + int phy_type = CAS_PHY_MII_MDIO0; /* default phy type */ + int mac_off = 0; + + /* give us access to the PROM */ + writel(BIM_LOCAL_DEV_PROM | BIM_LOCAL_DEV_PAD, + cp->regs + REG_BIM_LOCAL_DEV_EN); + + /* check for an expansion rom */ + if (readb(p) != 0x55 || readb(p + 1) != 0xaa) + goto use_random_mac_addr; + + /* search for beginning of vpd */ + base = 0; + for (i = 2; i < EXPANSION_ROM_SIZE; i++) { + /* check for PCIR */ + if ((readb(p + i + 0) == 0x50) && + (readb(p + i + 1) == 0x43) && + (readb(p + i + 2) == 0x49) && + (readb(p + i + 3) == 0x52)) { + base = p + (readb(p + i + 8) | + (readb(p + i + 9) << 8)); + break; + } + } + + if (!base || (readb(base) != 0x82)) + goto use_random_mac_addr; + + i = (readb(base + 1) | (readb(base + 2) << 8)) + 3; + while (i < EXPANSION_ROM_SIZE) { + if (readb(base + i) != 0x90) /* no vpd found */ + goto use_random_mac_addr; + + /* found a vpd field */ + len = readb(base + i + 1) | (readb(base + i + 2) << 8); + + /* extract keywords */ + kstart = base + i + 3; + p = kstart; + while ((p - kstart) < len) { + int klen = readb(p + 2); + int j; + char type; + + p += 3; + + /* look for the following things: + * -- correct length == 29 + * 3 (type) + 2 (size) + + * 18 (strlen("local-mac-address") + 1) + + * 6 (mac addr) + * -- VPD Instance 'I' + * -- VPD Type Bytes 'B' + * -- VPD data length == 6 + * -- property string == local-mac-address + * + * -- correct length == 24 + * 3 (type) + 2 (size) + + * 12 (strlen("entropy-dev") + 1) + + * 7 (strlen("vms110") + 1) + * -- VPD Instance 'I' + * -- VPD Type String 'B' + * -- VPD data length == 7 + * -- property string == entropy-dev + * + * -- correct length == 18 + * 3 (type) + 2 (size) + + * 9 (strlen("phy-type") + 1) + + * 4 (strlen("pcs") + 1) + * -- VPD Instance 'I' + * -- VPD Type String 'S' + * -- VPD data length == 4 + * -- property string == phy-type + * + * -- correct length == 23 + * 3 (type) + 2 (size) + + * 14 (strlen("phy-interface") + 1) + + * 4 (strlen("pcs") + 1) + * -- VPD Instance 'I' + * -- VPD Type String 'S' + * -- VPD data length == 4 + * -- property string == phy-interface + */ + if (readb(p) != 'I') + goto next; + + /* finally, check string and length */ + type = readb(p + 3); + if (type == 'B') { + if ((klen == 29) && readb(p + 4) == 6 && + cas_vpd_match(p + 5, + "local-mac-address")) { + if (mac_off++ > offset) + goto next; + + /* set mac address */ + for (j = 0; j < 6; j++) + dev_addr[j] = + readb(p + 23 + j); + goto found_mac; + } + } + + if (type != 'S') + goto next; + +#ifdef USE_ENTROPY_DEV + if ((klen == 24) && + cas_vpd_match(p + 5, "entropy-dev") && + cas_vpd_match(p + 17, "vms110")) { + cp->cas_flags |= CAS_FLAG_ENTROPY_DEV; + goto next; + } +#endif + + if (found & VPD_FOUND_PHY) + goto next; + + if ((klen == 18) && readb(p + 4) == 4 && + cas_vpd_match(p + 5, "phy-type")) { + if (cas_vpd_match(p + 14, "pcs")) { + phy_type = CAS_PHY_SERDES; + goto found_phy; + } + } + + if ((klen == 23) && readb(p + 4) == 4 && + cas_vpd_match(p + 5, "phy-interface")) { + if (cas_vpd_match(p + 19, "pcs")) { + phy_type = CAS_PHY_SERDES; + goto found_phy; + } + } +found_mac: + found |= VPD_FOUND_MAC; + goto next; + +found_phy: + found |= VPD_FOUND_PHY; + +next: + p += klen; + } + i += len + 3; + } + +use_random_mac_addr: + if (found & VPD_FOUND_MAC) + goto done; + + /* Sun MAC prefix then 3 random bytes. */ + printk(PFX "MAC address not found in ROM VPD\n"); + dev_addr[0] = 0x08; + dev_addr[1] = 0x00; + dev_addr[2] = 0x20; + get_random_bytes(dev_addr + 3, 3); + +done: + writel(0, cp->regs + REG_BIM_LOCAL_DEV_EN); + return phy_type; +} + +/* check pci invariants */ +static void cas_check_pci_invariants(struct cas *cp) +{ + struct pci_dev *pdev = cp->pdev; + u8 rev; + + cp->cas_flags = 0; + pci_read_config_byte(pdev, PCI_REVISION_ID, &rev); + if ((pdev->vendor == PCI_VENDOR_ID_SUN) && + (pdev->device == PCI_DEVICE_ID_SUN_CASSINI)) { + if (rev >= CAS_ID_REVPLUS) + cp->cas_flags |= CAS_FLAG_REG_PLUS; + if (rev < CAS_ID_REVPLUS02u) + cp->cas_flags |= CAS_FLAG_TARGET_ABORT; + + /* Original Cassini supports HW CSUM, but it's not + * enabled by default as it can trigger TX hangs. + */ + if (rev < CAS_ID_REV2) + cp->cas_flags |= CAS_FLAG_NO_HW_CSUM; + } else { + /* Only sun has original cassini chips. */ + cp->cas_flags |= CAS_FLAG_REG_PLUS; + + /* We use a flag because the same phy might be externally + * connected. + */ + if ((pdev->vendor == PCI_VENDOR_ID_NS) && + (pdev->device == PCI_DEVICE_ID_NS_SATURN)) + cp->cas_flags |= CAS_FLAG_SATURN; + } +} + + +static int cas_check_invariants(struct cas *cp) +{ + struct pci_dev *pdev = cp->pdev; + u32 cfg; + int i; + + /* get page size for rx buffers. */ + cp->page_order = 0; +#ifdef USE_PAGE_ORDER + if (PAGE_SHIFT < CAS_JUMBO_PAGE_SHIFT) { + /* see if we can allocate larger pages */ + struct page *page = alloc_pages(GFP_ATOMIC, + CAS_JUMBO_PAGE_SHIFT - + PAGE_SHIFT); + if (page) { + __free_pages(page, CAS_JUMBO_PAGE_SHIFT - PAGE_SHIFT); + cp->page_order = CAS_JUMBO_PAGE_SHIFT - PAGE_SHIFT; + } else { + printk(PFX "MTU limited to %d bytes\n", CAS_MAX_MTU); + } + } +#endif + cp->page_size = (PAGE_SIZE << cp->page_order); + + /* Fetch the FIFO configurations. */ + cp->tx_fifo_size = readl(cp->regs + REG_TX_FIFO_SIZE) * 64; + cp->rx_fifo_size = RX_FIFO_SIZE; + + /* finish phy determination. MDIO1 takes precedence over MDIO0 if + * they're both connected. + */ + cp->phy_type = cas_get_vpd_info(cp, cp->dev->dev_addr, + PCI_SLOT(pdev->devfn)); + if (cp->phy_type & CAS_PHY_SERDES) { + cp->cas_flags |= CAS_FLAG_1000MB_CAP; + return 0; /* no more checking needed */ + } + + /* MII */ + cfg = readl(cp->regs + REG_MIF_CFG); + if (cfg & MIF_CFG_MDIO_1) { + cp->phy_type = CAS_PHY_MII_MDIO1; + } else if (cfg & MIF_CFG_MDIO_0) { + cp->phy_type = CAS_PHY_MII_MDIO0; + } + + cas_mif_poll(cp, 0); + writel(PCS_DATAPATH_MODE_MII, cp->regs + REG_PCS_DATAPATH_MODE); + + for (i = 0; i < 32; i++) { + u32 phy_id; + int j; + + for (j = 0; j < 3; j++) { + cp->phy_addr = i; + phy_id = cas_phy_read(cp, MII_PHYSID1) << 16; + phy_id |= cas_phy_read(cp, MII_PHYSID2); + if (phy_id && (phy_id != 0xFFFFFFFF)) { + cp->phy_id = phy_id; + goto done; + } + } + } + printk(KERN_ERR PFX "MII phy did not respond [%08x]\n", + readl(cp->regs + REG_MIF_STATE_MACHINE)); + return -1; + +done: + /* see if we can do gigabit */ + cfg = cas_phy_read(cp, MII_BMSR); + if ((cfg & CAS_BMSR_1000_EXTEND) && + cas_phy_read(cp, CAS_MII_1000_EXTEND)) + cp->cas_flags |= CAS_FLAG_1000MB_CAP; + return 0; +} + +/* Must be invoked under cp->lock. */ +static inline void cas_start_dma(struct cas *cp) +{ + int i; + u32 val; + int txfailed = 0; + + /* enable dma */ + val = readl(cp->regs + REG_TX_CFG) | TX_CFG_DMA_EN; + writel(val, cp->regs + REG_TX_CFG); + val = readl(cp->regs + REG_RX_CFG) | RX_CFG_DMA_EN; + writel(val, cp->regs + REG_RX_CFG); + + /* enable the mac */ + val = readl(cp->regs + REG_MAC_TX_CFG) | MAC_TX_CFG_EN; + writel(val, cp->regs + REG_MAC_TX_CFG); + val = readl(cp->regs + REG_MAC_RX_CFG) | MAC_RX_CFG_EN; + writel(val, cp->regs + REG_MAC_RX_CFG); + + i = STOP_TRIES; + while (i-- > 0) { + val = readl(cp->regs + REG_MAC_TX_CFG); + if ((val & MAC_TX_CFG_EN)) + break; + udelay(10); + } + if (i < 0) txfailed = 1; + i = STOP_TRIES; + while (i-- > 0) { + val = readl(cp->regs + REG_MAC_RX_CFG); + if ((val & MAC_RX_CFG_EN)) { + if (txfailed) { + printk(KERN_ERR + "%s: enabling mac failed [tx:%08x:%08x].\n", + cp->dev->name, + readl(cp->regs + REG_MIF_STATE_MACHINE), + readl(cp->regs + REG_MAC_STATE_MACHINE)); + } + goto enable_rx_done; + } + udelay(10); + } + printk(KERN_ERR "%s: enabling mac failed [%s:%08x:%08x].\n", + cp->dev->name, + (txfailed? "tx,rx":"rx"), + readl(cp->regs + REG_MIF_STATE_MACHINE), + readl(cp->regs + REG_MAC_STATE_MACHINE)); + +enable_rx_done: + cas_unmask_intr(cp); /* enable interrupts */ + writel(RX_DESC_RINGN_SIZE(0) - 4, cp->regs + REG_RX_KICK); + writel(0, cp->regs + REG_RX_COMP_TAIL); + + if (cp->cas_flags & CAS_FLAG_REG_PLUS) { + if (N_RX_DESC_RINGS > 1) + writel(RX_DESC_RINGN_SIZE(1) - 4, + cp->regs + REG_PLUS_RX_KICK1); + + for (i = 1; i < N_RX_COMP_RINGS; i++) + writel(0, cp->regs + REG_PLUS_RX_COMPN_TAIL(i)); + } +} + +/* Must be invoked under cp->lock. */ +static void cas_read_pcs_link_mode(struct cas *cp, int *fd, int *spd, + int *pause) +{ + u32 val = readl(cp->regs + REG_PCS_MII_LPA); + *fd = (val & PCS_MII_LPA_FD) ? 1 : 0; + *pause = (val & PCS_MII_LPA_SYM_PAUSE) ? 0x01 : 0x00; + if (val & PCS_MII_LPA_ASYM_PAUSE) + *pause |= 0x10; + *spd = 1000; +} + +/* Must be invoked under cp->lock. */ +static void cas_read_mii_link_mode(struct cas *cp, int *fd, int *spd, + int *pause) +{ + u32 val; + + *fd = 0; + *spd = 10; + *pause = 0; + + /* use GMII registers */ + val = cas_phy_read(cp, MII_LPA); + if (val & CAS_LPA_PAUSE) + *pause = 0x01; + + if (val & CAS_LPA_ASYM_PAUSE) + *pause |= 0x10; + + if (val & LPA_DUPLEX) + *fd = 1; + if (val & LPA_100) + *spd = 100; + + if (cp->cas_flags & CAS_FLAG_1000MB_CAP) { + val = cas_phy_read(cp, CAS_MII_1000_STATUS); + if (val & (CAS_LPA_1000FULL | CAS_LPA_1000HALF)) + *spd = 1000; + if (val & CAS_LPA_1000FULL) + *fd = 1; + } +} + +/* A link-up condition has occurred, initialize and enable the + * rest of the chip. + * + * Must be invoked under cp->lock. + */ +static void cas_set_link_modes(struct cas *cp) +{ + u32 val; + int full_duplex, speed, pause; + + full_duplex = 0; + speed = 10; + pause = 0; + + if (CAS_PHY_MII(cp->phy_type)) { + cas_mif_poll(cp, 0); + val = cas_phy_read(cp, MII_BMCR); + if (val & BMCR_ANENABLE) { + cas_read_mii_link_mode(cp, &full_duplex, &speed, + &pause); + } else { + if (val & BMCR_FULLDPLX) + full_duplex = 1; + + if (val & BMCR_SPEED100) + speed = 100; + else if (val & CAS_BMCR_SPEED1000) + speed = (cp->cas_flags & CAS_FLAG_1000MB_CAP) ? + 1000 : 100; + } + cas_mif_poll(cp, 1); + + } else { + val = readl(cp->regs + REG_PCS_MII_CTRL); + cas_read_pcs_link_mode(cp, &full_duplex, &speed, &pause); + if ((val & PCS_MII_AUTONEG_EN) == 0) { + if (val & PCS_MII_CTRL_DUPLEX) + full_duplex = 1; + } + } + + if (netif_msg_link(cp)) + printk(KERN_INFO "%s: Link up at %d Mbps, %s-duplex.\n", + cp->dev->name, speed, (full_duplex ? "full" : "half")); + + val = MAC_XIF_TX_MII_OUTPUT_EN | MAC_XIF_LINK_LED; + if (CAS_PHY_MII(cp->phy_type)) { + val |= MAC_XIF_MII_BUFFER_OUTPUT_EN; + if (!full_duplex) + val |= MAC_XIF_DISABLE_ECHO; + } + if (full_duplex) + val |= MAC_XIF_FDPLX_LED; + if (speed == 1000) + val |= MAC_XIF_GMII_MODE; + writel(val, cp->regs + REG_MAC_XIF_CFG); + + /* deal with carrier and collision detect. */ + val = MAC_TX_CFG_IPG_EN; + if (full_duplex) { + val |= MAC_TX_CFG_IGNORE_CARRIER; + val |= MAC_TX_CFG_IGNORE_COLL; + } else { +#ifndef USE_CSMA_CD_PROTO + val |= MAC_TX_CFG_NEVER_GIVE_UP_EN; + val |= MAC_TX_CFG_NEVER_GIVE_UP_LIM; +#endif + } + /* val now set up for REG_MAC_TX_CFG */ + + /* If gigabit and half-duplex, enable carrier extension + * mode. increase slot time to 512 bytes as well. + * else, disable it and make sure slot time is 64 bytes. + * also activate checksum bug workaround + */ + if ((speed == 1000) && !full_duplex) { + writel(val | MAC_TX_CFG_CARRIER_EXTEND, + cp->regs + REG_MAC_TX_CFG); + + val = readl(cp->regs + REG_MAC_RX_CFG); + val &= ~MAC_RX_CFG_STRIP_FCS; /* checksum workaround */ + writel(val | MAC_RX_CFG_CARRIER_EXTEND, + cp->regs + REG_MAC_RX_CFG); + + writel(0x200, cp->regs + REG_MAC_SLOT_TIME); + + cp->crc_size = 4; + /* minimum size gigabit frame at half duplex */ + cp->min_frame_size = CAS_1000MB_MIN_FRAME; + + } else { + writel(val, cp->regs + REG_MAC_TX_CFG); + + /* checksum bug workaround. don't strip FCS when in + * half-duplex mode + */ + val = readl(cp->regs + REG_MAC_RX_CFG); + if (full_duplex) { + val |= MAC_RX_CFG_STRIP_FCS; + cp->crc_size = 0; + cp->min_frame_size = CAS_MIN_MTU; + } else { + val &= ~MAC_RX_CFG_STRIP_FCS; + cp->crc_size = 4; + cp->min_frame_size = CAS_MIN_FRAME; + } + writel(val & ~MAC_RX_CFG_CARRIER_EXTEND, + cp->regs + REG_MAC_RX_CFG); + writel(0x40, cp->regs + REG_MAC_SLOT_TIME); + } + + if (netif_msg_link(cp)) { + if (pause & 0x01) { + printk(KERN_INFO "%s: Pause is enabled " + "(rxfifo: %d off: %d on: %d)\n", + cp->dev->name, + cp->rx_fifo_size, + cp->rx_pause_off, + cp->rx_pause_on); + } else if (pause & 0x10) { + printk(KERN_INFO "%s: TX pause enabled\n", + cp->dev->name); + } else { + printk(KERN_INFO "%s: Pause is disabled\n", + cp->dev->name); + } + } + + val = readl(cp->regs + REG_MAC_CTRL_CFG); + val &= ~(MAC_CTRL_CFG_SEND_PAUSE_EN | MAC_CTRL_CFG_RECV_PAUSE_EN); + if (pause) { /* symmetric or asymmetric pause */ + val |= MAC_CTRL_CFG_SEND_PAUSE_EN; + if (pause & 0x01) { /* symmetric pause */ + val |= MAC_CTRL_CFG_RECV_PAUSE_EN; + } + } + writel(val, cp->regs + REG_MAC_CTRL_CFG); + cas_start_dma(cp); +} + +/* Must be invoked under cp->lock. */ +static void cas_init_hw(struct cas *cp, int restart_link) +{ + if (restart_link) + cas_phy_init(cp); + + cas_init_pause_thresholds(cp); + cas_init_mac(cp); + cas_init_dma(cp); + + if (restart_link) { + /* Default aneg parameters */ + cp->timer_ticks = 0; + cas_begin_auto_negotiation(cp, NULL); + } else if (cp->lstate == link_up) { + cas_set_link_modes(cp); + netif_carrier_on(cp->dev); + } +} + +/* Must be invoked under cp->lock. on earlier cassini boards, + * SOFT_0 is tied to PCI reset. we use this to force a pci reset, + * let it settle out, and then restore pci state. + */ +static void cas_hard_reset(struct cas *cp) +{ + writel(BIM_LOCAL_DEV_SOFT_0, cp->regs + REG_BIM_LOCAL_DEV_EN); + udelay(20); + pci_restore_state(cp->pdev); +} + + +static void cas_global_reset(struct cas *cp, int blkflag) +{ + int limit; + + /* issue a global reset. don't use RSTOUT. */ + if (blkflag && !CAS_PHY_MII(cp->phy_type)) { + /* For PCS, when the blkflag is set, we should set the + * SW_REST_BLOCK_PCS_SLINK bit to prevent the results of + * the last autonegotiation from being cleared. We'll + * need some special handling if the chip is set into a + * loopback mode. + */ + writel((SW_RESET_TX | SW_RESET_RX | SW_RESET_BLOCK_PCS_SLINK), + cp->regs + REG_SW_RESET); + } else { + writel(SW_RESET_TX | SW_RESET_RX, cp->regs + REG_SW_RESET); + } + + /* need to wait at least 3ms before polling register */ + mdelay(3); + + limit = STOP_TRIES; + while (limit-- > 0) { + u32 val = readl(cp->regs + REG_SW_RESET); + if ((val & (SW_RESET_TX | SW_RESET_RX)) == 0) + goto done; + udelay(10); + } + printk(KERN_ERR "%s: sw reset failed.\n", cp->dev->name); + +done: + /* enable various BIM interrupts */ + writel(BIM_CFG_DPAR_INTR_ENABLE | BIM_CFG_RMA_INTR_ENABLE | + BIM_CFG_RTA_INTR_ENABLE, cp->regs + REG_BIM_CFG); + + /* clear out pci error status mask for handled errors. + * we don't deal with DMA counter overflows as they happen + * all the time. + */ + writel(0xFFFFFFFFU & ~(PCI_ERR_BADACK | PCI_ERR_DTRTO | + PCI_ERR_OTHER | PCI_ERR_BIM_DMA_WRITE | + PCI_ERR_BIM_DMA_READ), cp->regs + + REG_PCI_ERR_STATUS_MASK); + + /* set up for MII by default to address mac rx reset timeout + * issue + */ + writel(PCS_DATAPATH_MODE_MII, cp->regs + REG_PCS_DATAPATH_MODE); +} + +static void cas_reset(struct cas *cp, int blkflag) +{ + u32 val; + + cas_mask_intr(cp); + cas_global_reset(cp, blkflag); + cas_mac_reset(cp); + cas_entropy_reset(cp); + + /* disable dma engines. */ + val = readl(cp->regs + REG_TX_CFG); + val &= ~TX_CFG_DMA_EN; + writel(val, cp->regs + REG_TX_CFG); + + val = readl(cp->regs + REG_RX_CFG); + val &= ~RX_CFG_DMA_EN; + writel(val, cp->regs + REG_RX_CFG); + + /* program header parser */ + if ((cp->cas_flags & CAS_FLAG_TARGET_ABORT) || + (CAS_HP_ALT_FIRMWARE == cas_prog_null)) { + cas_load_firmware(cp, CAS_HP_FIRMWARE); + } else { + cas_load_firmware(cp, CAS_HP_ALT_FIRMWARE); + } + + /* clear out error registers */ + spin_lock(&cp->stat_lock[N_TX_RINGS]); + cas_clear_mac_err(cp); + spin_unlock(&cp->stat_lock[N_TX_RINGS]); +} + +/* Shut down the chip, must be called with pm_sem held. */ +static void cas_shutdown(struct cas *cp) +{ + unsigned long flags; + + /* Make us not-running to avoid timers respawning */ + cp->hw_running = 0; + + del_timer_sync(&cp->link_timer); + + /* Stop the reset task */ +#if 0 + while (atomic_read(&cp->reset_task_pending_mtu) || + atomic_read(&cp->reset_task_pending_spare) || + atomic_read(&cp->reset_task_pending_all)) + schedule(); + +#else + while (atomic_read(&cp->reset_task_pending)) + schedule(); +#endif + /* Actually stop the chip */ + cas_lock_all_save(cp, flags); + cas_reset(cp, 0); + if (cp->cas_flags & CAS_FLAG_SATURN) + cas_phy_powerdown(cp); + cas_unlock_all_restore(cp, flags); +} + +static int cas_change_mtu(struct net_device *dev, int new_mtu) +{ + struct cas *cp = netdev_priv(dev); + + if (new_mtu < CAS_MIN_MTU || new_mtu > CAS_MAX_MTU) + return -EINVAL; + + dev->mtu = new_mtu; + if (!netif_running(dev) || !netif_device_present(dev)) + return 0; + + /* let the reset task handle it */ +#if 1 + atomic_inc(&cp->reset_task_pending); + if ((cp->phy_type & CAS_PHY_SERDES)) { + atomic_inc(&cp->reset_task_pending_all); + } else { + atomic_inc(&cp->reset_task_pending_mtu); + } + schedule_work(&cp->reset_task); +#else + atomic_set(&cp->reset_task_pending, (cp->phy_type & CAS_PHY_SERDES) ? + CAS_RESET_ALL : CAS_RESET_MTU); + printk(KERN_ERR "reset called in cas_change_mtu\n"); + schedule_work(&cp->reset_task); +#endif + + flush_scheduled_work(); + return 0; +} + +static void cas_clean_txd(struct cas *cp, int ring) +{ + struct cas_tx_desc *txd = cp->init_txds[ring]; + struct sk_buff *skb, **skbs = cp->tx_skbs[ring]; + u64 daddr, dlen; + int i, size; + + size = TX_DESC_RINGN_SIZE(ring); + for (i = 0; i < size; i++) { + int frag; + + if (skbs[i] == NULL) + continue; + + skb = skbs[i]; + skbs[i] = NULL; + + for (frag = 0; frag <= skb_shinfo(skb)->nr_frags; frag++) { + int ent = i & (size - 1); + + /* first buffer is never a tiny buffer and so + * needs to be unmapped. + */ + daddr = le64_to_cpu(txd[ent].buffer); + dlen = CAS_VAL(TX_DESC_BUFLEN, + le64_to_cpu(txd[ent].control)); + pci_unmap_page(cp->pdev, daddr, dlen, + PCI_DMA_TODEVICE); + + if (frag != skb_shinfo(skb)->nr_frags) { + i++; + + /* next buffer might by a tiny buffer. + * skip past it. + */ + ent = i & (size - 1); + if (cp->tx_tiny_use[ring][ent].used) + i++; + } + } + dev_kfree_skb_any(skb); + } + + /* zero out tiny buf usage */ + memset(cp->tx_tiny_use[ring], 0, size*sizeof(*cp->tx_tiny_use[ring])); +} + +/* freed on close */ +static inline void cas_free_rx_desc(struct cas *cp, int ring) +{ + cas_page_t **page = cp->rx_pages[ring]; + int i, size; + + size = RX_DESC_RINGN_SIZE(ring); + for (i = 0; i < size; i++) { + if (page[i]) { + cas_page_free(cp, page[i]); + page[i] = NULL; + } + } +} + +static void cas_free_rxds(struct cas *cp) +{ + int i; + + for (i = 0; i < N_RX_DESC_RINGS; i++) + cas_free_rx_desc(cp, i); +} + +/* Must be invoked under cp->lock. */ +static void cas_clean_rings(struct cas *cp) +{ + int i; + + /* need to clean all tx rings */ + memset(cp->tx_old, 0, sizeof(*cp->tx_old)*N_TX_RINGS); + memset(cp->tx_new, 0, sizeof(*cp->tx_new)*N_TX_RINGS); + for (i = 0; i < N_TX_RINGS; i++) + cas_clean_txd(cp, i); + + /* zero out init block */ + memset(cp->init_block, 0, sizeof(struct cas_init_block)); + cas_clean_rxds(cp); + cas_clean_rxcs(cp); +} + +/* allocated on open */ +static inline int cas_alloc_rx_desc(struct cas *cp, int ring) +{ + cas_page_t **page = cp->rx_pages[ring]; + int size, i = 0; + + size = RX_DESC_RINGN_SIZE(ring); + for (i = 0; i < size; i++) { + if ((page[i] = cas_page_alloc(cp, GFP_KERNEL)) == NULL) + return -1; + } + return 0; +} + +static int cas_alloc_rxds(struct cas *cp) +{ + int i; + + for (i = 0; i < N_RX_DESC_RINGS; i++) { + if (cas_alloc_rx_desc(cp, i) < 0) { + cas_free_rxds(cp); + return -1; + } + } + return 0; +} + +static void cas_reset_task(void *data) +{ + struct cas *cp = (struct cas *) data; +#if 0 + int pending = atomic_read(&cp->reset_task_pending); +#else + int pending_all = atomic_read(&cp->reset_task_pending_all); + int pending_spare = atomic_read(&cp->reset_task_pending_spare); + int pending_mtu = atomic_read(&cp->reset_task_pending_mtu); + + if (pending_all == 0 && pending_spare == 0 && pending_mtu == 0) { + /* We can have more tasks scheduled than actually + * needed. + */ + atomic_dec(&cp->reset_task_pending); + return; + } +#endif + /* The link went down, we reset the ring, but keep + * DMA stopped. Use this function for reset + * on error as well. + */ + if (cp->hw_running) { + unsigned long flags; + + /* Make sure we don't get interrupts or tx packets */ + netif_device_detach(cp->dev); + cas_lock_all_save(cp, flags); + + if (cp->opened) { + /* We call cas_spare_recover when we call cas_open. + * but we do not initialize the lists cas_spare_recover + * uses until cas_open is called. + */ + cas_spare_recover(cp, GFP_ATOMIC); + } +#if 1 + /* test => only pending_spare set */ + if (!pending_all && !pending_mtu) + goto done; +#else + if (pending == CAS_RESET_SPARE) + goto done; +#endif + /* when pending == CAS_RESET_ALL, the following + * call to cas_init_hw will restart auto negotiation. + * Setting the second argument of cas_reset to + * !(pending == CAS_RESET_ALL) will set this argument + * to 1 (avoiding reinitializing the PHY for the normal + * PCS case) when auto negotiation is not restarted. + */ +#if 1 + cas_reset(cp, !(pending_all > 0)); + if (cp->opened) + cas_clean_rings(cp); + cas_init_hw(cp, (pending_all > 0)); +#else + cas_reset(cp, !(pending == CAS_RESET_ALL)); + if (cp->opened) + cas_clean_rings(cp); + cas_init_hw(cp, pending == CAS_RESET_ALL); +#endif + +done: + cas_unlock_all_restore(cp, flags); + netif_device_attach(cp->dev); + } +#if 1 + atomic_sub(pending_all, &cp->reset_task_pending_all); + atomic_sub(pending_spare, &cp->reset_task_pending_spare); + atomic_sub(pending_mtu, &cp->reset_task_pending_mtu); + atomic_dec(&cp->reset_task_pending); +#else + atomic_set(&cp->reset_task_pending, 0); +#endif +} + +static void cas_link_timer(unsigned long data) +{ + struct cas *cp = (struct cas *) data; + int mask, pending = 0, reset = 0; + unsigned long flags; + + if (link_transition_timeout != 0 && + cp->link_transition_jiffies_valid && + ((jiffies - cp->link_transition_jiffies) > + (link_transition_timeout))) { + /* One-second counter so link-down workaround doesn't + * cause resets to occur so fast as to fool the switch + * into thinking the link is down. + */ + cp->link_transition_jiffies_valid = 0; + } + + if (!cp->hw_running) + return; + + spin_lock_irqsave(&cp->lock, flags); + cas_lock_tx(cp); + cas_entropy_gather(cp); + + /* If the link task is still pending, we just + * reschedule the link timer + */ +#if 1 + if (atomic_read(&cp->reset_task_pending_all) || + atomic_read(&cp->reset_task_pending_spare) || + atomic_read(&cp->reset_task_pending_mtu)) + goto done; +#else + if (atomic_read(&cp->reset_task_pending)) + goto done; +#endif + + /* check for rx cleaning */ + if ((mask = (cp->cas_flags & CAS_FLAG_RXD_POST_MASK))) { + int i, rmask; + + for (i = 0; i < MAX_RX_DESC_RINGS; i++) { + rmask = CAS_FLAG_RXD_POST(i); + if ((mask & rmask) == 0) + continue; + + /* post_rxds will do a mod_timer */ + if (cas_post_rxds_ringN(cp, i, cp->rx_last[i]) < 0) { + pending = 1; + continue; + } + cp->cas_flags &= ~rmask; + } + } + + if (CAS_PHY_MII(cp->phy_type)) { + u16 bmsr; + cas_mif_poll(cp, 0); + bmsr = cas_phy_read(cp, MII_BMSR); + /* WTZ: Solaris driver reads this twice, but that + * may be due to the PCS case and the use of a + * common implementation. Read it twice here to be + * safe. + */ + bmsr = cas_phy_read(cp, MII_BMSR); + cas_mif_poll(cp, 1); + readl(cp->regs + REG_MIF_STATUS); /* avoid dups */ + reset = cas_mii_link_check(cp, bmsr); + } else { + reset = cas_pcs_link_check(cp); + } + + if (reset) + goto done; + + /* check for tx state machine confusion */ + if ((readl(cp->regs + REG_MAC_TX_STATUS) & MAC_TX_FRAME_XMIT) == 0) { + u32 val = readl(cp->regs + REG_MAC_STATE_MACHINE); + u32 wptr, rptr; + int tlm = CAS_VAL(MAC_SM_TLM, val); + + if (((tlm == 0x5) || (tlm == 0x3)) && + (CAS_VAL(MAC_SM_ENCAP_SM, val) == 0)) { + if (netif_msg_tx_err(cp)) + printk(KERN_DEBUG "%s: tx err: " + "MAC_STATE[%08x]\n", + cp->dev->name, val); + reset = 1; + goto done; + } + + val = readl(cp->regs + REG_TX_FIFO_PKT_CNT); + wptr = readl(cp->regs + REG_TX_FIFO_WRITE_PTR); + rptr = readl(cp->regs + REG_TX_FIFO_READ_PTR); + if ((val == 0) && (wptr != rptr)) { + if (netif_msg_tx_err(cp)) + printk(KERN_DEBUG "%s: tx err: " + "TX_FIFO[%08x:%08x:%08x]\n", + cp->dev->name, val, wptr, rptr); + reset = 1; + } + + if (reset) + cas_hard_reset(cp); + } + +done: + if (reset) { +#if 1 + atomic_inc(&cp->reset_task_pending); + atomic_inc(&cp->reset_task_pending_all); + schedule_work(&cp->reset_task); +#else + atomic_set(&cp->reset_task_pending, CAS_RESET_ALL); + printk(KERN_ERR "reset called in cas_link_timer\n"); + schedule_work(&cp->reset_task); +#endif + } + + if (!pending) + mod_timer(&cp->link_timer, jiffies + CAS_LINK_TIMEOUT); + cas_unlock_tx(cp); + spin_unlock_irqrestore(&cp->lock, flags); +} + +/* tiny buffers are used to avoid target abort issues with + * older cassini's + */ +static void cas_tx_tiny_free(struct cas *cp) +{ + struct pci_dev *pdev = cp->pdev; + int i; + + for (i = 0; i < N_TX_RINGS; i++) { + if (!cp->tx_tiny_bufs[i]) + continue; + + pci_free_consistent(pdev, TX_TINY_BUF_BLOCK, + cp->tx_tiny_bufs[i], + cp->tx_tiny_dvma[i]); + cp->tx_tiny_bufs[i] = NULL; + } +} + +static int cas_tx_tiny_alloc(struct cas *cp) +{ + struct pci_dev *pdev = cp->pdev; + int i; + + for (i = 0; i < N_TX_RINGS; i++) { + cp->tx_tiny_bufs[i] = + pci_alloc_consistent(pdev, TX_TINY_BUF_BLOCK, + &cp->tx_tiny_dvma[i]); + if (!cp->tx_tiny_bufs[i]) { + cas_tx_tiny_free(cp); + return -1; + } + } + return 0; +} + + +static int cas_open(struct net_device *dev) +{ + struct cas *cp = netdev_priv(dev); + int hw_was_up, err; + unsigned long flags; + + down(&cp->pm_sem); + + hw_was_up = cp->hw_running; + + /* The power-management semaphore protects the hw_running + * etc. state so it is safe to do this bit without cp->lock + */ + if (!cp->hw_running) { + /* Reset the chip */ + cas_lock_all_save(cp, flags); + /* We set the second arg to cas_reset to zero + * because cas_init_hw below will have its second + * argument set to non-zero, which will force + * autonegotiation to start. + */ + cas_reset(cp, 0); + cp->hw_running = 1; + cas_unlock_all_restore(cp, flags); + } + + if (cas_tx_tiny_alloc(cp) < 0) + return -ENOMEM; + + /* alloc rx descriptors */ + err = -ENOMEM; + if (cas_alloc_rxds(cp) < 0) + goto err_tx_tiny; + + /* allocate spares */ + cas_spare_init(cp); + cas_spare_recover(cp, GFP_KERNEL); + + /* We can now request the interrupt as we know it's masked + * on the controller. cassini+ has up to 4 interrupts + * that can be used, but you need to do explicit pci interrupt + * mapping to expose them + */ + if (request_irq(cp->pdev->irq, cas_interrupt, + SA_SHIRQ, dev->name, (void *) dev)) { + printk(KERN_ERR "%s: failed to request irq !\n", + cp->dev->name); + err = -EAGAIN; + goto err_spare; + } + + /* init hw */ + cas_lock_all_save(cp, flags); + cas_clean_rings(cp); + cas_init_hw(cp, !hw_was_up); + cp->opened = 1; + cas_unlock_all_restore(cp, flags); + + netif_start_queue(dev); + up(&cp->pm_sem); + return 0; + +err_spare: + cas_spare_free(cp); + cas_free_rxds(cp); +err_tx_tiny: + cas_tx_tiny_free(cp); + up(&cp->pm_sem); + return err; +} + +static int cas_close(struct net_device *dev) +{ + unsigned long flags; + struct cas *cp = netdev_priv(dev); + + /* Make sure we don't get distracted by suspend/resume */ + down(&cp->pm_sem); + + netif_stop_queue(dev); + + /* Stop traffic, mark us closed */ + cas_lock_all_save(cp, flags); + cp->opened = 0; + cas_reset(cp, 0); + cas_phy_init(cp); + cas_begin_auto_negotiation(cp, NULL); + cas_clean_rings(cp); + cas_unlock_all_restore(cp, flags); + + free_irq(cp->pdev->irq, (void *) dev); + cas_spare_free(cp); + cas_free_rxds(cp); + cas_tx_tiny_free(cp); + up(&cp->pm_sem); + return 0; +} + +static struct { + const char name[ETH_GSTRING_LEN]; +} ethtool_cassini_statnames[] = { + {"collisions"}, + {"rx_bytes"}, + {"rx_crc_errors"}, + {"rx_dropped"}, + {"rx_errors"}, + {"rx_fifo_errors"}, + {"rx_frame_errors"}, + {"rx_length_errors"}, + {"rx_over_errors"}, + {"rx_packets"}, + {"tx_aborted_errors"}, + {"tx_bytes"}, + {"tx_dropped"}, + {"tx_errors"}, + {"tx_fifo_errors"}, + {"tx_packets"} +}; +#define CAS_NUM_STAT_KEYS (sizeof(ethtool_cassini_statnames)/ETH_GSTRING_LEN) + +static struct { + const int offsets; /* neg. values for 2nd arg to cas_read_phy */ +} ethtool_register_table[] = { + {-MII_BMSR}, + {-MII_BMCR}, + {REG_CAWR}, + {REG_INF_BURST}, + {REG_BIM_CFG}, + {REG_RX_CFG}, + {REG_HP_CFG}, + {REG_MAC_TX_CFG}, + {REG_MAC_RX_CFG}, + {REG_MAC_CTRL_CFG}, + {REG_MAC_XIF_CFG}, + {REG_MIF_CFG}, + {REG_PCS_CFG}, + {REG_SATURN_PCFG}, + {REG_PCS_MII_STATUS}, + {REG_PCS_STATE_MACHINE}, + {REG_MAC_COLL_EXCESS}, + {REG_MAC_COLL_LATE} +}; +#define CAS_REG_LEN (sizeof(ethtool_register_table)/sizeof(int)) +#define CAS_MAX_REGS (sizeof (u32)*CAS_REG_LEN) + +static u8 *cas_get_regs(struct cas *cp) +{ + u8 *ptr = kmalloc(CAS_MAX_REGS, GFP_KERNEL); + u8 *p; + int i; + unsigned long flags; + + if (!ptr) + return NULL; + + spin_lock_irqsave(&cp->lock, flags); + for (i = 0, p = ptr; i < CAS_REG_LEN ; i ++, p += sizeof(u32)) { + u16 hval; + u32 val; + if (ethtool_register_table[i].offsets < 0) { + hval = cas_phy_read(cp, + -ethtool_register_table[i].offsets); + val = hval; + } else { + val= readl(cp->regs+ethtool_register_table[i].offsets); + } + memcpy(p, (u8 *)&val, sizeof(u32)); + } + spin_unlock_irqrestore(&cp->lock, flags); + + return ptr; +} + +static struct net_device_stats *cas_get_stats(struct net_device *dev) +{ + struct cas *cp = netdev_priv(dev); + struct net_device_stats *stats = cp->net_stats; + unsigned long flags; + int i; + unsigned long tmp; + + /* we collate all of the stats into net_stats[N_TX_RING] */ + if (!cp->hw_running) + return stats + N_TX_RINGS; + + /* collect outstanding stats */ + /* WTZ: the Cassini spec gives these as 16 bit counters but + * stored in 32-bit words. Added a mask of 0xffff to be safe, + * in case the chip somehow puts any garbage in the other bits. + * Also, counter usage didn't seem to mach what Adrian did + * in the parts of the code that set these quantities. Made + * that consistent. + */ + spin_lock_irqsave(&cp->stat_lock[N_TX_RINGS], flags); + stats[N_TX_RINGS].rx_crc_errors += + readl(cp->regs + REG_MAC_FCS_ERR) & 0xffff; + stats[N_TX_RINGS].rx_frame_errors += + readl(cp->regs + REG_MAC_ALIGN_ERR) &0xffff; + stats[N_TX_RINGS].rx_length_errors += + readl(cp->regs + REG_MAC_LEN_ERR) & 0xffff; +#if 1 + tmp = (readl(cp->regs + REG_MAC_COLL_EXCESS) & 0xffff) + + (readl(cp->regs + REG_MAC_COLL_LATE) & 0xffff); + stats[N_TX_RINGS].tx_aborted_errors += tmp; + stats[N_TX_RINGS].collisions += + tmp + (readl(cp->regs + REG_MAC_COLL_NORMAL) & 0xffff); +#else + stats[N_TX_RINGS].tx_aborted_errors += + readl(cp->regs + REG_MAC_COLL_EXCESS); + stats[N_TX_RINGS].collisions += readl(cp->regs + REG_MAC_COLL_EXCESS) + + readl(cp->regs + REG_MAC_COLL_LATE); +#endif + cas_clear_mac_err(cp); + + /* saved bits that are unique to ring 0 */ + spin_lock(&cp->stat_lock[0]); + stats[N_TX_RINGS].collisions += stats[0].collisions; + stats[N_TX_RINGS].rx_over_errors += stats[0].rx_over_errors; + stats[N_TX_RINGS].rx_frame_errors += stats[0].rx_frame_errors; + stats[N_TX_RINGS].rx_fifo_errors += stats[0].rx_fifo_errors; + stats[N_TX_RINGS].tx_aborted_errors += stats[0].tx_aborted_errors; + stats[N_TX_RINGS].tx_fifo_errors += stats[0].tx_fifo_errors; + spin_unlock(&cp->stat_lock[0]); + + for (i = 0; i < N_TX_RINGS; i++) { + spin_lock(&cp->stat_lock[i]); + stats[N_TX_RINGS].rx_length_errors += + stats[i].rx_length_errors; + stats[N_TX_RINGS].rx_crc_errors += stats[i].rx_crc_errors; + stats[N_TX_RINGS].rx_packets += stats[i].rx_packets; + stats[N_TX_RINGS].tx_packets += stats[i].tx_packets; + stats[N_TX_RINGS].rx_bytes += stats[i].rx_bytes; + stats[N_TX_RINGS].tx_bytes += stats[i].tx_bytes; + stats[N_TX_RINGS].rx_errors += stats[i].rx_errors; + stats[N_TX_RINGS].tx_errors += stats[i].tx_errors; + stats[N_TX_RINGS].rx_dropped += stats[i].rx_dropped; + stats[N_TX_RINGS].tx_dropped += stats[i].tx_dropped; + memset(stats + i, 0, sizeof(struct net_device_stats)); + spin_unlock(&cp->stat_lock[i]); + } + spin_unlock_irqrestore(&cp->stat_lock[N_TX_RINGS], flags); + return stats + N_TX_RINGS; +} + + +static void cas_set_multicast(struct net_device *dev) +{ + struct cas *cp = netdev_priv(dev); + u32 rxcfg, rxcfg_new; + unsigned long flags; + int limit = STOP_TRIES; + + if (!cp->hw_running) + return; + + spin_lock_irqsave(&cp->lock, flags); + rxcfg = readl(cp->regs + REG_MAC_RX_CFG); + + /* disable RX MAC and wait for completion */ + writel(rxcfg & ~MAC_RX_CFG_EN, cp->regs + REG_MAC_RX_CFG); + while (readl(cp->regs + REG_MAC_RX_CFG) & MAC_RX_CFG_EN) { + if (!limit--) + break; + udelay(10); + } + + /* disable hash filter and wait for completion */ + limit = STOP_TRIES; + rxcfg &= ~(MAC_RX_CFG_PROMISC_EN | MAC_RX_CFG_HASH_FILTER_EN); + writel(rxcfg & ~MAC_RX_CFG_EN, cp->regs + REG_MAC_RX_CFG); + while (readl(cp->regs + REG_MAC_RX_CFG) & MAC_RX_CFG_HASH_FILTER_EN) { + if (!limit--) + break; + udelay(10); + } + + /* program hash filters */ + cp->mac_rx_cfg = rxcfg_new = cas_setup_multicast(cp); + rxcfg |= rxcfg_new; + writel(rxcfg, cp->regs + REG_MAC_RX_CFG); + spin_unlock_irqrestore(&cp->lock, flags); +} + +/* Eventually add support for changing the advertisement + * on autoneg. + */ +static int cas_ethtool_ioctl(struct net_device *dev, void *ep_user) +{ + struct cas *cp = netdev_priv(dev); + u16 bmcr; + int full_duplex, speed, pause; + struct ethtool_cmd ecmd; + unsigned long flags; + enum link_state linkstate = link_up; + + if (copy_from_user(&ecmd, ep_user, sizeof(ecmd))) + return -EFAULT; + + switch(ecmd.cmd) { + case ETHTOOL_GDRVINFO: { + struct ethtool_drvinfo info = { cmd: ETHTOOL_GDRVINFO }; + + strncpy(info.driver, DRV_MODULE_NAME, + ETHTOOL_BUSINFO_LEN); + strncpy(info.version, DRV_MODULE_VERSION, + ETHTOOL_BUSINFO_LEN); + info.fw_version[0] = '\0'; + strncpy(info.bus_info, pci_name(cp->pdev), + ETHTOOL_BUSINFO_LEN); + info.regdump_len = cp->casreg_len < CAS_MAX_REGS ? + cp->casreg_len : CAS_MAX_REGS; + info.n_stats = CAS_NUM_STAT_KEYS; + if (copy_to_user(ep_user, &info, sizeof(info))) + return -EFAULT; + + return 0; + } + + case ETHTOOL_GSET: + ecmd.advertising = 0; + ecmd.supported = SUPPORTED_Autoneg; + if (cp->cas_flags & CAS_FLAG_1000MB_CAP) { + ecmd.supported |= SUPPORTED_1000baseT_Full; + ecmd.advertising |= ADVERTISED_1000baseT_Full; + } + + /* Record PHY settings if HW is on. */ + spin_lock_irqsave(&cp->lock, flags); + bmcr = 0; + linkstate = cp->lstate; + if (CAS_PHY_MII(cp->phy_type)) { + ecmd.port = PORT_MII; + ecmd.transceiver = (cp->cas_flags & CAS_FLAG_SATURN) ? + XCVR_INTERNAL : XCVR_EXTERNAL; + ecmd.phy_address = cp->phy_addr; + ecmd.advertising |= ADVERTISED_TP | ADVERTISED_MII | + ADVERTISED_10baseT_Half | + ADVERTISED_10baseT_Full | + ADVERTISED_100baseT_Half | + ADVERTISED_100baseT_Full; + + ecmd.supported |= + (SUPPORTED_10baseT_Half | + SUPPORTED_10baseT_Full | + SUPPORTED_100baseT_Half | + SUPPORTED_100baseT_Full | + SUPPORTED_TP | SUPPORTED_MII); + + if (cp->hw_running) { + cas_mif_poll(cp, 0); + bmcr = cas_phy_read(cp, MII_BMCR); + cas_read_mii_link_mode(cp, &full_duplex, + &speed, &pause); + cas_mif_poll(cp, 1); + } + + } else { + ecmd.port = PORT_FIBRE; + ecmd.transceiver = XCVR_INTERNAL; + ecmd.phy_address = 0; + ecmd.supported |= SUPPORTED_FIBRE; + ecmd.advertising |= ADVERTISED_FIBRE; + + if (cp->hw_running) { + /* pcs uses the same bits as mii */ + bmcr = readl(cp->regs + REG_PCS_MII_CTRL); + cas_read_pcs_link_mode(cp, &full_duplex, + &speed, &pause); + } + } + spin_unlock_irqrestore(&cp->lock, flags); + + if (bmcr & BMCR_ANENABLE) { + ecmd.advertising |= ADVERTISED_Autoneg; + ecmd.autoneg = AUTONEG_ENABLE; + ecmd.speed = ((speed == 10) ? + SPEED_10 : + ((speed == 1000) ? + SPEED_1000 : SPEED_100)); + ecmd.duplex = full_duplex ? DUPLEX_FULL : DUPLEX_HALF; + } else { + ecmd.autoneg = AUTONEG_DISABLE; + ecmd.speed = + (bmcr & CAS_BMCR_SPEED1000) ? + SPEED_1000 : + ((bmcr & BMCR_SPEED100) ? SPEED_100: + SPEED_10); + ecmd.duplex = + (bmcr & BMCR_FULLDPLX) ? + DUPLEX_FULL : DUPLEX_HALF; + } + if (linkstate != link_up) { + /* Force these to "unknown" if the link is not up and + * autonogotiation in enabled. We can set the link + * speed to 0, but not ecmd.duplex, + * because its legal values are 0 and 1. Ethtool will + * print the value reported in parentheses after the + * word "Unknown" for unrecognized values. + * + * If in forced mode, we report the speed and duplex + * settings that we configured. + */ + if (cp->link_cntl & BMCR_ANENABLE) { + ecmd.speed = 0; + ecmd.duplex = 0xff; + } else { + ecmd.speed = SPEED_10; + if (cp->link_cntl & BMCR_SPEED100) { + ecmd.speed = SPEED_100; + } else if (cp->link_cntl & CAS_BMCR_SPEED1000) { + ecmd.speed = SPEED_1000; + } + ecmd.duplex = (cp->link_cntl & BMCR_FULLDPLX)? + DUPLEX_FULL : DUPLEX_HALF; + } + } + if (copy_to_user(ep_user, &ecmd, sizeof(ecmd))) + return -EFAULT; + return 0; + + case ETHTOOL_SSET: + if (!capable(CAP_NET_ADMIN)) + return -EPERM; + + /* Verify the settings we care about. */ + if (ecmd.autoneg != AUTONEG_ENABLE && + ecmd.autoneg != AUTONEG_DISABLE) + return -EINVAL; + + if (ecmd.autoneg == AUTONEG_DISABLE && + ((ecmd.speed != SPEED_1000 && + ecmd.speed != SPEED_100 && + ecmd.speed != SPEED_10) || + (ecmd.duplex != DUPLEX_HALF && + ecmd.duplex != DUPLEX_FULL))) + return -EINVAL; + + /* Apply settings and restart link process. */ + spin_lock_irqsave(&cp->lock, flags); + cas_begin_auto_negotiation(cp, &ecmd); + spin_unlock_irqrestore(&cp->lock, flags); + return 0; + + case ETHTOOL_NWAY_RST: + if ((cp->link_cntl & BMCR_ANENABLE) == 0) + return -EINVAL; + + /* Restart link process. */ + spin_lock_irqsave(&cp->lock, flags); + cas_begin_auto_negotiation(cp, NULL); + spin_unlock_irqrestore(&cp->lock, flags); + + return 0; + + case ETHTOOL_GWOL: + case ETHTOOL_SWOL: + break; /* doesn't exist */ + + /* get link status */ + case ETHTOOL_GLINK: { + struct ethtool_value edata = { cmd: ETHTOOL_GLINK }; + + edata.data = (cp->lstate == link_up); + if (copy_to_user(ep_user, &edata, sizeof(edata))) + return -EFAULT; + return 0; + } + + /* get message-level */ + case ETHTOOL_GMSGLVL: { + struct ethtool_value edata = { cmd: ETHTOOL_GMSGLVL }; + + edata.data = cp->msg_enable; + if (copy_to_user(ep_user, &edata, sizeof(edata))) + return -EFAULT; + return 0; + } + + /* set message-level */ + case ETHTOOL_SMSGLVL: { + struct ethtool_value edata; + + if (!capable(CAP_NET_ADMIN)) { + return (-EPERM); + } + if (copy_from_user(&edata, ep_user, sizeof(edata))) + return -EFAULT; + cp->msg_enable = edata.data; + return 0; + } + + case ETHTOOL_GREGS: { + struct ethtool_regs edata; + u8 *ptr; + int len = cp->casreg_len < CAS_MAX_REGS ? + cp->casreg_len: CAS_MAX_REGS; + + if (copy_from_user(&edata, ep_user, sizeof (edata))) + return -EFAULT; + + if (edata.len > len) + edata.len = len; + edata.version = 0; + if (copy_to_user (ep_user, &edata, sizeof(edata))) + return -EFAULT; + + /* cas_get_regs handles locks (cp->lock). */ + ptr = cas_get_regs(cp); + if (ptr == NULL) + return -ENOMEM; + if (copy_to_user(ep_user + sizeof (edata), ptr, edata.len)) + return -EFAULT; + + kfree(ptr); + return (0); + } + case ETHTOOL_GSTRINGS: { + struct ethtool_gstrings edata; + int len; + + if (copy_from_user(&edata, ep_user, sizeof(edata))) + return -EFAULT; + + len = edata.len; + switch(edata.string_set) { + case ETH_SS_STATS: + edata.len = (len < CAS_NUM_STAT_KEYS) ? + len : CAS_NUM_STAT_KEYS; + if (copy_to_user(ep_user, &edata, sizeof(edata))) + return -EFAULT; + + if (copy_to_user(ep_user + sizeof(edata), + ðtool_cassini_statnames, + (edata.len * ETH_GSTRING_LEN))) + return -EFAULT; + return 0; + default: + return -EINVAL; + } + } + case ETHTOOL_GSTATS: { + int i = 0; + u64 *tmp; + struct ethtool_stats edata; + struct net_device_stats *stats; + int len; + + if (copy_from_user(&edata, ep_user, sizeof(edata))) + return -EFAULT; + + len = edata.n_stats; + stats = cas_get_stats(cp->dev); + edata.cmd = ETHTOOL_GSTATS; + edata.n_stats = (len < CAS_NUM_STAT_KEYS) ? + len : CAS_NUM_STAT_KEYS; + if (copy_to_user(ep_user, &edata, sizeof (edata))) + return -EFAULT; + + tmp = kmalloc(sizeof(u64)*CAS_NUM_STAT_KEYS, GFP_KERNEL); + if (tmp) { + tmp[i++] = stats->collisions; + tmp[i++] = stats->rx_bytes; + tmp[i++] = stats->rx_crc_errors; + tmp[i++] = stats->rx_dropped; + tmp[i++] = stats->rx_errors; + tmp[i++] = stats->rx_fifo_errors; + tmp[i++] = stats->rx_frame_errors; + tmp[i++] = stats->rx_length_errors; + tmp[i++] = stats->rx_over_errors; + tmp[i++] = stats->rx_packets; + tmp[i++] = stats->tx_aborted_errors; + tmp[i++] = stats->tx_bytes; + tmp[i++] = stats->tx_dropped; + tmp[i++] = stats->tx_errors; + tmp[i++] = stats->tx_fifo_errors; + tmp[i++] = stats->tx_packets; + BUG_ON(i != CAS_NUM_STAT_KEYS); + + i = copy_to_user(ep_user + sizeof(edata), + tmp, sizeof(u64)*edata.n_stats); + kfree(tmp); + } else { + return -ENOMEM; + } + if (i) + return -EFAULT; + return 0; + } + } + + return -EOPNOTSUPP; +} + +static int cas_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd) +{ + struct cas *cp = netdev_priv(dev); + struct mii_ioctl_data *data = (struct mii_ioctl_data *)&ifr->ifr_data; + unsigned long flags; + int rc = -EOPNOTSUPP; + + /* Hold the PM semaphore while doing ioctl's or we may collide + * with open/close and power management and oops. + */ + down(&cp->pm_sem); + switch (cmd) { + case SIOCETHTOOL: + rc = cas_ethtool_ioctl(dev, ifr->ifr_data); + break; + + case SIOCGMIIPHY: /* Get address of MII PHY in use. */ + data->phy_id = cp->phy_addr; + /* Fallthrough... */ + + case SIOCGMIIREG: /* Read MII PHY register. */ + spin_lock_irqsave(&cp->lock, flags); + cas_mif_poll(cp, 0); + data->val_out = cas_phy_read(cp, data->reg_num & 0x1f); + cas_mif_poll(cp, 1); + spin_unlock_irqrestore(&cp->lock, flags); + rc = 0; + break; + + case SIOCSMIIREG: /* Write MII PHY register. */ + if (!capable(CAP_NET_ADMIN)) { + rc = -EPERM; + break; + } + spin_lock_irqsave(&cp->lock, flags); + cas_mif_poll(cp, 0); + rc = cas_phy_write(cp, data->reg_num & 0x1f, data->val_in); + cas_mif_poll(cp, 1); + spin_unlock_irqrestore(&cp->lock, flags); + break; + default: + break; + }; + + up(&cp->pm_sem); + return rc; +} + +static int __devinit cas_init_one(struct pci_dev *pdev, + const struct pci_device_id *ent) +{ + static int cas_version_printed = 0; + unsigned long casreg_base, casreg_len; + struct net_device *dev; + struct cas *cp; + int i, err, pci_using_dac; + u16 pci_cmd; + u8 orig_cacheline_size = 0, cas_cacheline_size = 0; + + if (cas_version_printed++ == 0) + printk(KERN_INFO "%s", version); + + err = pci_enable_device(pdev); + if (err) { + printk(KERN_ERR PFX "Cannot enable PCI device, " + "aborting.\n"); + return err; + } + + if (!(pci_resource_flags(pdev, 0) & IORESOURCE_MEM)) { + printk(KERN_ERR PFX "Cannot find proper PCI device " + "base address, aborting.\n"); + err = -ENODEV; + goto err_out_disable_pdev; + } + + dev = alloc_etherdev(sizeof(*cp)); + if (!dev) { + printk(KERN_ERR PFX "Etherdev alloc failed, aborting.\n"); + err = -ENOMEM; + goto err_out_disable_pdev; + } + SET_MODULE_OWNER(dev); + SET_NETDEV_DEV(dev, &pdev->dev); + + err = pci_request_regions(pdev, dev->name); + if (err) { + printk(KERN_ERR PFX "Cannot obtain PCI resources, " + "aborting.\n"); + goto err_out_free_netdev; + } + pci_set_master(pdev); + + /* we must always turn on parity response or else parity + * doesn't get generated properly. disable SERR/PERR as well. + * in addition, we want to turn MWI on. + */ + pci_read_config_word(pdev, PCI_COMMAND, &pci_cmd); + pci_cmd &= ~PCI_COMMAND_SERR; + pci_cmd |= PCI_COMMAND_PARITY; + pci_write_config_word(pdev, PCI_COMMAND, pci_cmd); + pci_set_mwi(pdev); + /* + * On some architectures, the default cache line size set + * by pci_set_mwi reduces perforamnce. We have to increase + * it for this case. To start, we'll print some configuration + * data. + */ +#if 1 + pci_read_config_byte(pdev, PCI_CACHE_LINE_SIZE, + &orig_cacheline_size); + if (orig_cacheline_size < CAS_PREF_CACHELINE_SIZE) { + cas_cacheline_size = + (CAS_PREF_CACHELINE_SIZE < SMP_CACHE_BYTES) ? + CAS_PREF_CACHELINE_SIZE : SMP_CACHE_BYTES; + if (pci_write_config_byte(pdev, + PCI_CACHE_LINE_SIZE, + cas_cacheline_size)) { + printk(KERN_ERR PFX "Could not set PCI cache " + "line size\n"); + goto err_write_cacheline; + } + } +#endif + + + /* Configure DMA attributes. */ + if (!pci_set_dma_mask(pdev, DMA_64BIT_MASK)) { + pci_using_dac = 1; + err = pci_set_consistent_dma_mask(pdev, + DMA_64BIT_MASK); + if (err < 0) { + printk(KERN_ERR PFX "Unable to obtain 64-bit DMA " + "for consistent allocations\n"); + goto err_out_free_res; + } + + } else { + err = pci_set_dma_mask(pdev, DMA_32BIT_MASK); + if (err) { + printk(KERN_ERR PFX "No usable DMA configuration, " + "aborting.\n"); + goto err_out_free_res; + } + pci_using_dac = 0; + } + + casreg_base = pci_resource_start(pdev, 0); + casreg_len = pci_resource_len(pdev, 0); + + cp = netdev_priv(dev); + cp->pdev = pdev; +#if 1 + /* A value of 0 indicates we never explicitly set it */ + cp->orig_cacheline_size = cas_cacheline_size ? orig_cacheline_size: 0; +#endif + cp->dev = dev; + cp->msg_enable = (cassini_debug < 0) ? CAS_DEF_MSG_ENABLE : + cassini_debug; + + cp->link_transition = LINK_TRANSITION_UNKNOWN; + cp->link_transition_jiffies_valid = 0; + + spin_lock_init(&cp->lock); + spin_lock_init(&cp->rx_inuse_lock); + spin_lock_init(&cp->rx_spare_lock); + for (i = 0; i < N_TX_RINGS; i++) { + spin_lock_init(&cp->stat_lock[i]); + spin_lock_init(&cp->tx_lock[i]); + } + spin_lock_init(&cp->stat_lock[N_TX_RINGS]); + init_MUTEX(&cp->pm_sem); + + init_timer(&cp->link_timer); + cp->link_timer.function = cas_link_timer; + cp->link_timer.data = (unsigned long) cp; + +#if 1 + /* Just in case the implementation of atomic operations + * change so that an explicit initialization is necessary. + */ + atomic_set(&cp->reset_task_pending, 0); + atomic_set(&cp->reset_task_pending_all, 0); + atomic_set(&cp->reset_task_pending_spare, 0); + atomic_set(&cp->reset_task_pending_mtu, 0); +#endif + INIT_WORK(&cp->reset_task, cas_reset_task, cp); + + /* Default link parameters */ + if (link_mode >= 0 && link_mode <= 6) + cp->link_cntl = link_modes[link_mode]; + else + cp->link_cntl = BMCR_ANENABLE; + cp->lstate = link_down; + cp->link_transition = LINK_TRANSITION_LINK_DOWN; + netif_carrier_off(cp->dev); + cp->timer_ticks = 0; + + /* give us access to cassini registers */ + cp->regs = ioremap(casreg_base, casreg_len); + if (cp->regs == 0UL) { + printk(KERN_ERR PFX "Cannot map device registers, " + "aborting.\n"); + goto err_out_free_res; + } + cp->casreg_len = casreg_len; + + pci_save_state(pdev); + cas_check_pci_invariants(cp); + cas_hard_reset(cp); + cas_reset(cp, 0); + if (cas_check_invariants(cp)) + goto err_out_iounmap; + + cp->init_block = (struct cas_init_block *) + pci_alloc_consistent(pdev, sizeof(struct cas_init_block), + &cp->block_dvma); + if (!cp->init_block) { + printk(KERN_ERR PFX "Cannot allocate init block, " + "aborting.\n"); + goto err_out_iounmap; + } + + for (i = 0; i < N_TX_RINGS; i++) + cp->init_txds[i] = cp->init_block->txds[i]; + + for (i = 0; i < N_RX_DESC_RINGS; i++) + cp->init_rxds[i] = cp->init_block->rxds[i]; + + for (i = 0; i < N_RX_COMP_RINGS; i++) + cp->init_rxcs[i] = cp->init_block->rxcs[i]; + + for (i = 0; i < N_RX_FLOWS; i++) + skb_queue_head_init(&cp->rx_flows[i]); + + dev->open = cas_open; + dev->stop = cas_close; + dev->hard_start_xmit = cas_start_xmit; + dev->get_stats = cas_get_stats; + dev->set_multicast_list = cas_set_multicast; + dev->do_ioctl = cas_ioctl; + dev->tx_timeout = cas_tx_timeout; + dev->watchdog_timeo = CAS_TX_TIMEOUT; + dev->change_mtu = cas_change_mtu; +#ifdef USE_NAPI + dev->poll = cas_poll; + dev->weight = 64; +#endif +#ifdef CONFIG_NET_POLL_CONTROLLER + dev->poll_controller = cas_netpoll; +#endif + dev->irq = pdev->irq; + dev->dma = 0; + + /* Cassini features. */ + if ((cp->cas_flags & CAS_FLAG_NO_HW_CSUM) == 0) + dev->features |= NETIF_F_HW_CSUM | NETIF_F_SG; + + if (pci_using_dac) + dev->features |= NETIF_F_HIGHDMA; + + if (register_netdev(dev)) { + printk(KERN_ERR PFX "Cannot register net device, " + "aborting.\n"); + goto err_out_free_consistent; + } + + i = readl(cp->regs + REG_BIM_CFG); + printk(KERN_INFO "%s: Sun Cassini%s (%sbit/%sMHz PCI/%s) " + "Ethernet[%d] ", dev->name, + (cp->cas_flags & CAS_FLAG_REG_PLUS) ? "+" : "", + (i & BIM_CFG_32BIT) ? "32" : "64", + (i & BIM_CFG_66MHZ) ? "66" : "33", + (cp->phy_type == CAS_PHY_SERDES) ? "Fi" : "Cu", pdev->irq); + + for (i = 0; i < 6; i++) + printk("%2.2x%c", dev->dev_addr[i], + i == 5 ? ' ' : ':'); + printk("\n"); + + pci_set_drvdata(pdev, dev); + cp->hw_running = 1; + cas_entropy_reset(cp); + cas_phy_init(cp); + cas_begin_auto_negotiation(cp, NULL); + return 0; + +err_out_free_consistent: + pci_free_consistent(pdev, sizeof(struct cas_init_block), + cp->init_block, cp->block_dvma); + +err_out_iounmap: + down(&cp->pm_sem); + if (cp->hw_running) + cas_shutdown(cp); + up(&cp->pm_sem); + + iounmap((void *) cp->regs); + + +err_out_free_res: + pci_release_regions(pdev); + +err_write_cacheline: + /* Try to restore it in case the error occured after we + * set it. + */ + pci_write_config_byte(pdev, PCI_CACHE_LINE_SIZE, orig_cacheline_size); + +err_out_free_netdev: + free_netdev(dev); + +err_out_disable_pdev: + pci_disable_device(pdev); + pci_set_drvdata(pdev, NULL); + return -ENODEV; +} + +static void __devexit cas_remove_one(struct pci_dev *pdev) +{ + struct net_device *dev = pci_get_drvdata(pdev); + struct cas *cp; + if (!dev) + return; + + cp = netdev_priv(dev); + unregister_netdev(dev); + + down(&cp->pm_sem); + flush_scheduled_work(); + if (cp->hw_running) + cas_shutdown(cp); + up(&cp->pm_sem); + +#if 1 + if (cp->orig_cacheline_size) { + /* Restore the cache line size if we had modified + * it. + */ + pci_write_config_byte(pdev, PCI_CACHE_LINE_SIZE, + cp->orig_cacheline_size); + } +#endif + pci_free_consistent(pdev, sizeof(struct cas_init_block), + cp->init_block, cp->block_dvma); + iounmap((void *) cp->regs); + free_netdev(dev); + pci_release_regions(pdev); + pci_disable_device(pdev); + pci_set_drvdata(pdev, NULL); +} + +#ifdef CONFIG_PM +static int cas_suspend(struct pci_dev *pdev, u32 state) +{ + struct net_device *dev = pci_get_drvdata(pdev); + struct cas *cp = netdev_priv(dev); + unsigned long flags; + + /* We hold the PM semaphore during entire driver + * sleep time + */ + down(&cp->pm_sem); + + /* If the driver is opened, we stop the DMA */ + if (cp->opened) { + netif_device_detach(dev); + + cas_lock_all_save(cp, flags); + + /* We can set the second arg of cas_reset to 0 + * because on resume, we'll call cas_init_hw with + * its second arg set so that autonegotiation is + * restarted. + */ + cas_reset(cp, 0); + cas_clean_rings(cp); + cas_unlock_all_restore(cp, flags); + } + + if (cp->hw_running) + cas_shutdown(cp); + + return 0; +} + +static int cas_resume(struct pci_dev *pdev) +{ + struct net_device *dev = pci_get_drvdata(pdev); + struct cas *cp = netdev_priv(dev); + + printk(KERN_INFO "%s: resuming\n", dev->name); + + cas_hard_reset(cp); + if (cp->opened) { + unsigned long flags; + cas_lock_all_save(cp, flags); + cas_reset(cp, 0); + cp->hw_running = 1; + cas_clean_rings(cp); + cas_init_hw(cp, 1); + cas_unlock_all_restore(cp, flags); + + netif_device_attach(dev); + } + up(&cp->pm_sem); + return 0; +} +#endif /* CONFIG_PM */ + +static struct pci_driver cas_driver = { + .name = DRV_MODULE_NAME, + .id_table = cas_pci_tbl, + .probe = cas_init_one, + .remove = __devexit_p(cas_remove_one), +#ifdef CONFIG_PM + .suspend = cas_suspend, + .resume = cas_resume +#endif +}; + +static int __init cas_init(void) +{ + if (linkdown_timeout > 0) + link_transition_timeout = linkdown_timeout * HZ; + else + link_transition_timeout = 0; + + return pci_module_init(&cas_driver); +} + +static void __exit cas_cleanup(void) +{ + pci_unregister_driver(&cas_driver); +} + +module_init(cas_init); +module_exit(cas_cleanup); diff --git a/drivers/net/cassini.h b/drivers/net/cassini.h new file mode 100644 index 00000000000..88063ef16cf --- /dev/null +++ b/drivers/net/cassini.h @@ -0,0 +1,4425 @@ +/* $Id: cassini.h,v 1.16 2004/08/17 21:15:16 zaumen Exp $ + * cassini.h: Definitions for Sun Microsystems Cassini(+) ethernet driver. + * + * Copyright (C) 2004 Sun Microsystems Inc. + * Copyright (c) 2003 Adrian Sun (asun@darksunrising.com) + * + * 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. + * + * vendor id: 0x108E (Sun Microsystems, Inc.) + * device id: 0xabba (Cassini) + * revision ids: 0x01 = Cassini + * 0x02 = Cassini rev 2 + * 0x10 = Cassini+ + * 0x11 = Cassini+ 0.2u + * + * vendor id: 0x100b (National Semiconductor) + * device id: 0x0035 (DP83065/Saturn) + * revision ids: 0x30 = Saturn B2 + * + * rings are all offset from 0. + * + * there are two clock domains: + * PCI: 33/66MHz clock + * chip: 125MHz clock + */ + +#ifndef _CASSINI_H +#define _CASSINI_H + +/* cassini register map: 2M memory mapped in 32-bit memory space accessible as + * 32-bit words. there is no i/o port access. REG_ addresses are + * shared between cassini and cassini+. REG_PLUS_ addresses only + * appear in cassini+. REG_MINUS_ addresses only appear in cassini. + */ +#define CAS_ID_REV2 0x02 +#define CAS_ID_REVPLUS 0x10 +#define CAS_ID_REVPLUS02u 0x11 +#define CAS_ID_REVSATURNB2 0x30 + +/** global resources **/ + +/* this register sets the weights for the weighted round robin arbiter. e.g., + * if rx weight == 1 and tx weight == 0, rx == 2x tx transfer credit + * for its next turn to access the pci bus. + * map: 0x0 = x1, 0x1 = x2, 0x2 = x4, 0x3 = x8 + * DEFAULT: 0x0, SIZE: 5 bits + */ +#define REG_CAWR 0x0004 /* core arbitration weight */ +#define CAWR_RX_DMA_WEIGHT_SHIFT 0 +#define CAWR_RX_DMA_WEIGHT_MASK 0x03 /* [0:1] */ +#define CAWR_TX_DMA_WEIGHT_SHIFT 2 +#define CAWR_TX_DMA_WEIGHT_MASK 0x0C /* [3:2] */ +#define CAWR_RR_DIS 0x10 /* [4] */ + +/* if enabled, BIM can send bursts across PCI bus > cacheline size. burst + * sizes determined by length of packet or descriptor transfer and the + * max length allowed by the target. + * DEFAULT: 0x0, SIZE: 1 bit + */ +#define REG_INF_BURST 0x0008 /* infinite burst enable reg */ +#define INF_BURST_EN 0x1 /* enable */ + +/* top level interrupts [0-9] are auto-cleared to 0 when the status + * register is read. second level interrupts [13 - 18] are cleared at + * the source. tx completion register 3 is replicated in [19 - 31] + * DEFAULT: 0x00000000, SIZE: 29 bits + */ +#define REG_INTR_STATUS 0x000C /* interrupt status register */ +#define INTR_TX_INTME 0x00000001 /* frame w/ INT ME desc bit set + xferred from host queue to + TX FIFO */ +#define INTR_TX_ALL 0x00000002 /* all xmit frames xferred into + TX FIFO. i.e., + TX Kick == TX complete. if + PACED_MODE set, then TX FIFO + also empty */ +#define INTR_TX_DONE 0x00000004 /* any frame xferred into tx + FIFO */ +#define INTR_TX_TAG_ERROR 0x00000008 /* TX FIFO tag framing + corrupted. FATAL ERROR */ +#define INTR_RX_DONE 0x00000010 /* at least 1 frame xferred + from RX FIFO to host mem. + RX completion reg updated. + may be delayed by recv + intr blanking. */ +#define INTR_RX_BUF_UNAVAIL 0x00000020 /* no more receive buffers. + RX Kick == RX complete */ +#define INTR_RX_TAG_ERROR 0x00000040 /* RX FIFO tag framing + corrupted. FATAL ERROR */ +#define INTR_RX_COMP_FULL 0x00000080 /* no more room in completion + ring to post descriptors. + RX complete head incr to + almost reach RX complete + tail */ +#define INTR_RX_BUF_AE 0x00000100 /* less than the + programmable threshold # + of free descr avail for + hw use */ +#define INTR_RX_COMP_AF 0x00000200 /* less than the + programmable threshold # + of descr spaces for hw + use in completion descr + ring */ +#define INTR_RX_LEN_MISMATCH 0x00000400 /* len field from MAC != + len of non-reassembly pkt + from fifo during DMA or + header parser provides TCP + header and payload size > + MAC packet size. + FATAL ERROR */ +#define INTR_SUMMARY 0x00001000 /* summary interrupt bit. this + bit will be set if an interrupt + generated on the pci bus. useful + when driver is polling for + interrupts */ +#define INTR_PCS_STATUS 0x00002000 /* PCS interrupt status register */ +#define INTR_TX_MAC_STATUS 0x00004000 /* TX MAC status register has at + least 1 unmasked interrupt set */ +#define INTR_RX_MAC_STATUS 0x00008000 /* RX MAC status register has at + least 1 unmasked interrupt set */ +#define INTR_MAC_CTRL_STATUS 0x00010000 /* MAC control status register has + at least 1 unmasked interrupt + set */ +#define INTR_MIF_STATUS 0x00020000 /* MIF status register has at least + 1 unmasked interrupt set */ +#define INTR_PCI_ERROR_STATUS 0x00040000 /* PCI error status register in the + BIF has at least 1 unmasked + interrupt set */ +#define INTR_TX_COMP_3_MASK 0xFFF80000 /* mask for TX completion + 3 reg data */ +#define INTR_TX_COMP_3_SHIFT 19 +#define INTR_ERROR_MASK (INTR_MIF_STATUS | INTR_PCI_ERROR_STATUS | \ + INTR_PCS_STATUS | INTR_RX_LEN_MISMATCH | \ + INTR_TX_MAC_STATUS | INTR_RX_MAC_STATUS | \ + INTR_TX_TAG_ERROR | INTR_RX_TAG_ERROR | \ + INTR_MAC_CTRL_STATUS) + +/* determines which status events will cause an interrupt. layout same + * as REG_INTR_STATUS. + * DEFAULT: 0xFFFFFFFF, SIZE: 16 bits + */ +#define REG_INTR_MASK 0x0010 /* Interrupt mask */ + +/* top level interrupt bits that are cleared during read of REG_INTR_STATUS_ALIAS. + * useful when driver is polling for interrupts. layout same as REG_INTR_MASK. + * DEFAULT: 0x00000000, SIZE: 12 bits + */ +#define REG_ALIAS_CLEAR 0x0014 /* alias clear mask + (used w/ status alias) */ +/* same as REG_INTR_STATUS except that only bits cleared are those selected by + * REG_ALIAS_CLEAR + * DEFAULT: 0x00000000, SIZE: 29 bits + */ +#define REG_INTR_STATUS_ALIAS 0x001C /* interrupt status alias + (selective clear) */ + +/* DEFAULT: 0x0, SIZE: 3 bits */ +#define REG_PCI_ERR_STATUS 0x1000 /* PCI error status */ +#define PCI_ERR_BADACK 0x01 /* reserved in Cassini+. + set if no ACK64# during ABS64 cycle + in Cassini. */ +#define PCI_ERR_DTRTO 0x02 /* delayed xaction timeout. set if + no read retry after 2^15 clocks */ +#define PCI_ERR_OTHER 0x04 /* other PCI errors */ +#define PCI_ERR_BIM_DMA_WRITE 0x08 /* BIM received 0 count DMA write req. + unused in Cassini. */ +#define PCI_ERR_BIM_DMA_READ 0x10 /* BIM received 0 count DMA read req. + unused in Cassini. */ +#define PCI_ERR_BIM_DMA_TIMEOUT 0x20 /* BIM received 255 retries during + DMA. unused in cassini. */ + +/* mask for PCI status events that will set PCI_ERR_STATUS. if cleared, event + * causes an interrupt to be generated. + * DEFAULT: 0x7, SIZE: 3 bits + */ +#define REG_PCI_ERR_STATUS_MASK 0x1004 /* PCI Error status mask */ + +/* used to configure PCI related parameters that are not in PCI config space. + * DEFAULT: 0bxx000, SIZE: 5 bits + */ +#define REG_BIM_CFG 0x1008 /* BIM Configuration */ +#define BIM_CFG_RESERVED0 0x001 /* reserved */ +#define BIM_CFG_RESERVED1 0x002 /* reserved */ +#define BIM_CFG_64BIT_DISABLE 0x004 /* disable 64-bit mode */ +#define BIM_CFG_66MHZ 0x008 /* (ro) 1 = 66MHz, 0 = < 66MHz */ +#define BIM_CFG_32BIT 0x010 /* (ro) 1 = 32-bit slot, 0 = 64-bit */ +#define BIM_CFG_DPAR_INTR_ENABLE 0x020 /* detected parity err enable */ +#define BIM_CFG_RMA_INTR_ENABLE 0x040 /* master abort intr enable */ +#define BIM_CFG_RTA_INTR_ENABLE 0x080 /* target abort intr enable */ +#define BIM_CFG_RESERVED2 0x100 /* reserved */ +#define BIM_CFG_BIM_DISABLE 0x200 /* stop BIM DMA. use before global + reset. reserved in Cassini. */ +#define BIM_CFG_BIM_STATUS 0x400 /* (ro) 1 = BIM DMA suspended. + reserved in Cassini. */ +#define BIM_CFG_PERROR_BLOCK 0x800 /* block PERR# to pci bus. def: 0. + reserved in Cassini. */ + +/* DEFAULT: 0x00000000, SIZE: 32 bits */ +#define REG_BIM_DIAG 0x100C /* BIM Diagnostic */ +#define BIM_DIAG_MSTR_SM_MASK 0x3FFFFF00 /* PCI master controller state + machine bits [21:0] */ +#define BIM_DIAG_BRST_SM_MASK 0x7F /* PCI burst controller state + machine bits [6:0] */ + +/* writing to SW_RESET_TX and SW_RESET_RX will issue a global + * reset. poll until TX and RX read back as 0's for completion. + */ +#define REG_SW_RESET 0x1010 /* Software reset */ +#define SW_RESET_TX 0x00000001 /* reset TX DMA engine. poll until + cleared to 0. */ +#define SW_RESET_RX 0x00000002 /* reset RX DMA engine. poll until + cleared to 0. */ +#define SW_RESET_RSTOUT 0x00000004 /* force RSTOUT# pin active (low). + resets PHY and anything else + connected to RSTOUT#. RSTOUT# + is also activated by local PCI + reset when hot-swap is being + done. */ +#define SW_RESET_BLOCK_PCS_SLINK 0x00000008 /* if a global reset is done with + this bit set, PCS and SLINK + modules won't be reset. + i.e., link won't drop. */ +#define SW_RESET_BREQ_SM_MASK 0x00007F00 /* breq state machine [6:0] */ +#define SW_RESET_PCIARB_SM_MASK 0x00070000 /* pci arbitration state bits: + 0b000: ARB_IDLE1 + 0b001: ARB_IDLE2 + 0b010: ARB_WB_ACK + 0b011: ARB_WB_WAT + 0b100: ARB_RB_ACK + 0b101: ARB_RB_WAT + 0b110: ARB_RB_END + 0b111: ARB_WB_END */ +#define SW_RESET_RDPCI_SM_MASK 0x00300000 /* read pci state bits: + 0b00: RD_PCI_WAT + 0b01: RD_PCI_RDY + 0b11: RD_PCI_ACK */ +#define SW_RESET_RDARB_SM_MASK 0x00C00000 /* read arbitration state bits: + 0b00: AD_IDL_RX + 0b01: AD_ACK_RX + 0b10: AD_ACK_TX + 0b11: AD_IDL_TX */ +#define SW_RESET_WRPCI_SM_MASK 0x06000000 /* write pci state bits + 0b00: WR_PCI_WAT + 0b01: WR_PCI_RDY + 0b11: WR_PCI_ACK */ +#define SW_RESET_WRARB_SM_MASK 0x38000000 /* write arbitration state bits: + 0b000: ARB_IDLE1 + 0b001: ARB_IDLE2 + 0b010: ARB_TX_ACK + 0b011: ARB_TX_WAT + 0b100: ARB_RX_ACK + 0b110: ARB_RX_WAT */ + +/* Cassini only. 64-bit register used to check PCI datapath. when read, + * value written has both lower and upper 32-bit halves rotated to the right + * one bit position. e.g., FFFFFFFF FFFFFFFF -> 7FFFFFFF 7FFFFFFF + */ +#define REG_MINUS_BIM_DATAPATH_TEST 0x1018 /* Cassini: BIM datapath test + Cassini+: reserved */ + +/* output enables are provided for each device's chip select and for the rest + * of the outputs from cassini to its local bus devices. two sw programmable + * bits are connected to general purpus control/status bits. + * DEFAULT: 0x7 + */ +#define REG_BIM_LOCAL_DEV_EN 0x1020 /* BIM local device + output EN. default: 0x7 */ +#define BIM_LOCAL_DEV_PAD 0x01 /* address bus, RW signal, and + OE signal output enable on the + local bus interface. these + are shared between both local + bus devices. tristate when 0. */ +#define BIM_LOCAL_DEV_PROM 0x02 /* PROM chip select */ +#define BIM_LOCAL_DEV_EXT 0x04 /* secondary local bus device chip + select output enable */ +#define BIM_LOCAL_DEV_SOFT_0 0x08 /* sw programmable ctrl bit 0 */ +#define BIM_LOCAL_DEV_SOFT_1 0x10 /* sw programmable ctrl bit 1 */ +#define BIM_LOCAL_DEV_HW_RESET 0x20 /* internal hw reset. Cassini+ only. */ + +/* access 24 entry BIM read and write buffers. put address in REG_BIM_BUFFER_ADDR + * and read/write from/to it REG_BIM_BUFFER_DATA_LOW and _DATA_HI. + * _DATA_HI should be the last access of the sequence. + * DEFAULT: undefined + */ +#define REG_BIM_BUFFER_ADDR 0x1024 /* BIM buffer address. for + purposes. */ +#define BIM_BUFFER_ADDR_MASK 0x3F /* index (0 - 23) of buffer */ +#define BIM_BUFFER_WR_SELECT 0x40 /* write buffer access = 1 + read buffer access = 0 */ +/* DEFAULT: undefined */ +#define REG_BIM_BUFFER_DATA_LOW 0x1028 /* BIM buffer data low */ +#define REG_BIM_BUFFER_DATA_HI 0x102C /* BIM buffer data high */ + +/* set BIM_RAM_BIST_START to start built-in self test for BIM read buffer. + * bit auto-clears when done with status read from _SUMMARY and _PASS bits. + */ +#define REG_BIM_RAM_BIST 0x102C /* BIM RAM (read buffer) BIST + control/status */ +#define BIM_RAM_BIST_RD_START 0x01 /* start BIST for BIM read buffer */ +#define BIM_RAM_BIST_WR_START 0x02 /* start BIST for BIM write buffer. + Cassini only. reserved in + Cassini+. */ +#define BIM_RAM_BIST_RD_PASS 0x04 /* summary BIST pass status for read + buffer. */ +#define BIM_RAM_BIST_WR_PASS 0x08 /* summary BIST pass status for write + buffer. Cassini only. reserved + in Cassini+. */ +#define BIM_RAM_BIST_RD_LOW_PASS 0x10 /* read low bank passes BIST */ +#define BIM_RAM_BIST_RD_HI_PASS 0x20 /* read high bank passes BIST */ +#define BIM_RAM_BIST_WR_LOW_PASS 0x40 /* write low bank passes BIST. + Cassini only. reserved in + Cassini+. */ +#define BIM_RAM_BIST_WR_HI_PASS 0x80 /* write high bank passes BIST. + Cassini only. reserved in + Cassini+. */ + +/* ASUN: i'm not sure what this does as it's not in the spec. + * DEFAULT: 0xFC + */ +#define REG_BIM_DIAG_MUX 0x1030 /* BIM diagnostic probe mux + select register */ + +/* enable probe monitoring mode and select data appearing on the P_A* bus. bit + * values for _SEL_HI_MASK and _SEL_LOW_MASK: + * 0x0: internal probe[7:0] (pci arb state, wtc empty w, wtc full w, wtc empty w, + * wtc empty r, post pci) + * 0x1: internal probe[15:8] (pci wbuf comp, pci wpkt comp, pci rbuf comp, + * pci rpkt comp, txdma wr req, txdma wr ack, + * txdma wr rdy, txdma wr xfr done) + * 0x2: internal probe[23:16] (txdma rd req, txdma rd ack, txdma rd rdy, rxdma rd, + * rd arb state, rd pci state) + * 0x3: internal probe[31:24] (rxdma req, rxdma ack, rxdma rdy, wrarb state, + * wrpci state) + * 0x4: pci io probe[7:0] 0x5: pci io probe[15:8] + * 0x6: pci io probe[23:16] 0x7: pci io probe[31:24] + * 0x8: pci io probe[39:32] 0x9: pci io probe[47:40] + * 0xa: pci io probe[55:48] 0xb: pci io probe[63:56] + * the following are not available in Cassini: + * 0xc: rx probe[7:0] 0xd: tx probe[7:0] + * 0xe: hp probe[7:0] 0xf: mac probe[7:0] + */ +#define REG_PLUS_PROBE_MUX_SELECT 0x1034 /* Cassini+: PROBE MUX SELECT */ +#define PROBE_MUX_EN 0x80000000 /* allow probe signals to be + driven on local bus P_A[15:0] + for debugging */ +#define PROBE_MUX_SUB_MUX_MASK 0x0000FF00 /* select sub module probe signals: + 0x03 = mac[1:0] + 0x0C = rx[1:0] + 0x30 = tx[1:0] + 0xC0 = hp[1:0] */ +#define PROBE_MUX_SEL_HI_MASK 0x000000F0 /* select which module to appear + on P_A[15:8]. see above for + values. */ +#define PROBE_MUX_SEL_LOW_MASK 0x0000000F /* select which module to appear + on P_A[7:0]. see above for + values. */ + +/* values mean the same thing as REG_INTR_MASK excep that it's for INTB. + DEFAULT: 0x1F */ +#define REG_PLUS_INTR_MASK_1 0x1038 /* Cassini+: interrupt mask + register 2 for INTB */ +#define REG_PLUS_INTRN_MASK(x) (REG_PLUS_INTR_MASK_1 + ((x) - 1)*16) +/* bits correspond to both _MASK and _STATUS registers. _ALT corresponds to + * all of the alternate (2-4) INTR registers while _1 corresponds to only + * _MASK_1 and _STATUS_1 registers. + * DEFAULT: 0x7 for MASK registers, 0x0 for ALIAS_CLEAR registers + */ +#define INTR_RX_DONE_ALT 0x01 +#define INTR_RX_COMP_FULL_ALT 0x02 +#define INTR_RX_COMP_AF_ALT 0x04 +#define INTR_RX_BUF_UNAVAIL_1 0x08 +#define INTR_RX_BUF_AE_1 0x10 /* almost empty */ +#define INTRN_MASK_RX_EN 0x80 +#define INTRN_MASK_CLEAR_ALL (INTR_RX_DONE_ALT | \ + INTR_RX_COMP_FULL_ALT | \ + INTR_RX_COMP_AF_ALT | \ + INTR_RX_BUF_UNAVAIL_1 | \ + INTR_RX_BUF_AE_1) +#define REG_PLUS_INTR_STATUS_1 0x103C /* Cassini+: interrupt status + register 2 for INTB. default: 0x1F */ +#define REG_PLUS_INTRN_STATUS(x) (REG_PLUS_INTR_STATUS_1 + ((x) - 1)*16) +#define INTR_STATUS_ALT_INTX_EN 0x80 /* generate INTX when one of the + flags are set. enables desc ring. */ + +#define REG_PLUS_ALIAS_CLEAR_1 0x1040 /* Cassini+: alias clear mask + register 2 for INTB */ +#define REG_PLUS_ALIASN_CLEAR(x) (REG_PLUS_ALIAS_CLEAR_1 + ((x) - 1)*16) + +#define REG_PLUS_INTR_STATUS_ALIAS_1 0x1044 /* Cassini+: interrupt status + register alias 2 for INTB */ +#define REG_PLUS_INTRN_STATUS_ALIAS(x) (REG_PLUS_INTR_STATUS_ALIAS_1 + ((x) - 1)*16) + +#define REG_SATURN_PCFG 0x106c /* pin configuration register for + integrated macphy */ + +#define SATURN_PCFG_TLA 0x00000001 /* 1 = phy actled */ +#define SATURN_PCFG_FLA 0x00000002 /* 1 = phy link10led */ +#define SATURN_PCFG_CLA 0x00000004 /* 1 = phy link100led */ +#define SATURN_PCFG_LLA 0x00000008 /* 1 = phy link1000led */ +#define SATURN_PCFG_RLA 0x00000010 /* 1 = phy duplexled */ +#define SATURN_PCFG_PDS 0x00000020 /* phy debug mode. + 0 = normal */ +#define SATURN_PCFG_MTP 0x00000080 /* test point select */ +#define SATURN_PCFG_GMO 0x00000100 /* GMII observe. 1 = + GMII on SERDES pins for + monitoring. */ +#define SATURN_PCFG_FSI 0x00000200 /* 1 = freeze serdes/gmii. all + pins configed as outputs. + for power saving when using + internal phy. */ +#define SATURN_PCFG_LAD 0x00000800 /* 0 = mac core led ctrl + polarity from strapping + value. + 1 = mac core led ctrl + polarity active low. */ + + +/** transmit dma registers **/ +#define MAX_TX_RINGS_SHIFT 2 +#define MAX_TX_RINGS (1 << MAX_TX_RINGS_SHIFT) +#define MAX_TX_RINGS_MASK (MAX_TX_RINGS - 1) + +/* TX configuration. + * descr ring sizes size = 32 * (1 << n), n < 9. e.g., 0x8 = 8k. default: 0x8 + * DEFAULT: 0x3F000001 + */ +#define REG_TX_CFG 0x2004 /* TX config */ +#define TX_CFG_DMA_EN 0x00000001 /* enable TX DMA. if cleared, DMA + will stop after xfer of current + buffer has been completed. */ +#define TX_CFG_FIFO_PIO_SEL 0x00000002 /* TX DMA FIFO can be + accessed w/ FIFO addr + and data registers. + TX DMA should be + disabled. */ +#define TX_CFG_DESC_RING0_MASK 0x0000003C /* # desc entries in + ring 1. */ +#define TX_CFG_DESC_RING0_SHIFT 2 +#define TX_CFG_DESC_RINGN_MASK(a) (TX_CFG_DESC_RING0_MASK << (a)*4) +#define TX_CFG_DESC_RINGN_SHIFT(a) (TX_CFG_DESC_RING0_SHIFT + (a)*4) +#define TX_CFG_PACED_MODE 0x00100000 /* TX_ALL only set after + TX FIFO becomes empty. + if 0, TX_ALL set + if descr queue empty. */ +#define TX_CFG_DMA_RDPIPE_DIS 0x01000000 /* always set to 1 */ +#define TX_CFG_COMPWB_Q1 0x02000000 /* completion writeback happens at + the end of every packet kicked + through Q1. */ +#define TX_CFG_COMPWB_Q2 0x04000000 /* completion writeback happens at + the end of every packet kicked + through Q2. */ +#define TX_CFG_COMPWB_Q3 0x08000000 /* completion writeback happens at + the end of every packet kicked + through Q3 */ +#define TX_CFG_COMPWB_Q4 0x10000000 /* completion writeback happens at + the end of every packet kicked + through Q4 */ +#define TX_CFG_INTR_COMPWB_DIS 0x20000000 /* disable pre-interrupt completion + writeback */ +#define TX_CFG_CTX_SEL_MASK 0xC0000000 /* selects tx test port + connection + 0b00: tx mac req, + tx mac retry req, + tx ack and tx tag. + 0b01: txdma rd req, + txdma rd ack, + txdma rd rdy, + txdma rd type0 + 0b11: txdma wr req, + txdma wr ack, + txdma wr rdy, + txdma wr xfr done. */ +#define TX_CFG_CTX_SEL_SHIFT 30 + +/* 11-bit counters that point to next location in FIFO to be loaded/retrieved. + * used for diagnostics only. + */ +#define REG_TX_FIFO_WRITE_PTR 0x2014 /* TX FIFO write pointer */ +#define REG_TX_FIFO_SHADOW_WRITE_PTR 0x2018 /* TX FIFO shadow write + pointer. temp hold reg. + diagnostics only. */ +#define REG_TX_FIFO_READ_PTR 0x201C /* TX FIFO read pointer */ +#define REG_TX_FIFO_SHADOW_READ_PTR 0x2020 /* TX FIFO shadow read + pointer */ + +/* (ro) 11-bit up/down counter w/ # of frames currently in TX FIFO */ +#define REG_TX_FIFO_PKT_CNT 0x2024 /* TX FIFO packet counter */ + +/* current state of all state machines in TX */ +#define REG_TX_SM_1 0x2028 /* TX state machine reg #1 */ +#define TX_SM_1_CHAIN_MASK 0x000003FF /* chaining state machine */ +#define TX_SM_1_CSUM_MASK 0x00000C00 /* checksum state machine */ +#define TX_SM_1_FIFO_LOAD_MASK 0x0003F000 /* FIFO load state machine. + = 0x01 when TX disabled. */ +#define TX_SM_1_FIFO_UNLOAD_MASK 0x003C0000 /* FIFO unload state machine */ +#define TX_SM_1_CACHE_MASK 0x03C00000 /* desc. prefetch cache controller + state machine */ +#define TX_SM_1_CBQ_ARB_MASK 0xF8000000 /* CBQ arbiter state machine */ + +#define REG_TX_SM_2 0x202C /* TX state machine reg #2 */ +#define TX_SM_2_COMP_WB_MASK 0x07 /* completion writeback sm */ +#define TX_SM_2_SUB_LOAD_MASK 0x38 /* sub load state machine */ +#define TX_SM_2_KICK_MASK 0xC0 /* kick state machine */ + +/* 64-bit pointer to the transmit data buffer. only the 50 LSB are incremented + * while the upper 23 bits are taken from the TX descriptor + */ +#define REG_TX_DATA_PTR_LOW 0x2030 /* TX data pointer low */ +#define REG_TX_DATA_PTR_HI 0x2034 /* TX data pointer high */ + +/* 13 bit registers written by driver w/ descriptor value that follows + * last valid xmit descriptor. kick # and complete # values are used by + * the xmit dma engine to control tx descr fetching. if > 1 valid + * tx descr is available within the cache line being read, cassini will + * internally cache up to 4 of them. 0 on reset. _KICK = rw, _COMP = ro. + */ +#define REG_TX_KICK0 0x2038 /* TX kick reg #1 */ +#define REG_TX_KICKN(x) (REG_TX_KICK0 + (x)*4) +#define REG_TX_COMP0 0x2048 /* TX completion reg #1 */ +#define REG_TX_COMPN(x) (REG_TX_COMP0 + (x)*4) + +/* values of TX_COMPLETE_1-4 are written. each completion register + * is 2bytes in size and contiguous. 8B allocation w/ 8B alignment. + * NOTE: completion reg values are only written back prior to TX_INTME and + * TX_ALL interrupts. at all other times, the most up-to-date index values + * should be obtained from the REG_TX_COMPLETE_# registers. + * here's the layout: + * offset from base addr completion # byte + * 0 TX_COMPLETE_1_MSB + * 1 TX_COMPLETE_1_LSB + * 2 TX_COMPLETE_2_MSB + * 3 TX_COMPLETE_2_LSB + * 4 TX_COMPLETE_3_MSB + * 5 TX_COMPLETE_3_LSB + * 6 TX_COMPLETE_4_MSB + * 7 TX_COMPLETE_4_LSB + */ +#define TX_COMPWB_SIZE 8 +#define REG_TX_COMPWB_DB_LOW 0x2058 /* TX completion write back + base low */ +#define REG_TX_COMPWB_DB_HI 0x205C /* TX completion write back + base high */ +#define TX_COMPWB_MSB_MASK 0x00000000000000FFULL +#define TX_COMPWB_MSB_SHIFT 0 +#define TX_COMPWB_LSB_MASK 0x000000000000FF00ULL +#define TX_COMPWB_LSB_SHIFT 8 +#define TX_COMPWB_NEXT(x) ((x) >> 16) + +/* 53 MSB used as base address. 11 LSB assumed to be 0. TX desc pointer must + * be 2KB-aligned. */ +#define REG_TX_DB0_LOW 0x2060 /* TX descriptor base low #1 */ +#define REG_TX_DB0_HI 0x2064 /* TX descriptor base hi #1 */ +#define REG_TX_DBN_LOW(x) (REG_TX_DB0_LOW + (x)*8) +#define REG_TX_DBN_HI(x) (REG_TX_DB0_HI + (x)*8) + +/* 16-bit registers hold weights for the weighted round-robin of the + * four CBQ TX descr rings. weights correspond to # bytes xferred from + * host to TXFIFO in a round of WRR arbitration. can be set + * dynamically with new weights set upon completion of the current + * packet transfer from host memory to TXFIFO. a dummy write to any of + * these registers causes a queue1 pre-emption with all historical bw + * deficit data reset to 0 (useful when congestion requires a + * pre-emption/re-allocation of network bandwidth + */ +#define REG_TX_MAXBURST_0 0x2080 /* TX MaxBurst #1 */ +#define REG_TX_MAXBURST_1 0x2084 /* TX MaxBurst #2 */ +#define REG_TX_MAXBURST_2 0x2088 /* TX MaxBurst #3 */ +#define REG_TX_MAXBURST_3 0x208C /* TX MaxBurst #4 */ + +/* diagnostics access to any TX FIFO location. every access is 65 + * bits. _DATA_LOW = 32 LSB, _DATA_HI_T1/T0 = 32 MSB. _TAG = tag bit. + * writing _DATA_HI_T0 sets tag bit low, writing _DATA_HI_T1 sets tag + * bit high. TX_FIFO_PIO_SEL must be set for TX FIFO PIO access. if + * TX FIFO data integrity is desired, TX DMA should be + * disabled. _DATA_HI_Tx should be the last access of the sequence. + */ +#define REG_TX_FIFO_ADDR 0x2104 /* TX FIFO address */ +#define REG_TX_FIFO_TAG 0x2108 /* TX FIFO tag */ +#define REG_TX_FIFO_DATA_LOW 0x210C /* TX FIFO data low */ +#define REG_TX_FIFO_DATA_HI_T1 0x2110 /* TX FIFO data high t1 */ +#define REG_TX_FIFO_DATA_HI_T0 0x2114 /* TX FIFO data high t0 */ +#define REG_TX_FIFO_SIZE 0x2118 /* (ro) TX FIFO size = 0x090 = 9KB */ + +/* 9-bit register controls BIST of TX FIFO. bit set indicates that the BIST + * passed for the specified memory + */ +#define REG_TX_RAMBIST 0x211C /* TX RAMBIST control/status */ +#define TX_RAMBIST_STATE 0x01C0 /* progress state of RAMBIST + controller state machine */ +#define TX_RAMBIST_RAM33A_PASS 0x0020 /* RAM33A passed */ +#define TX_RAMBIST_RAM32A_PASS 0x0010 /* RAM32A passed */ +#define TX_RAMBIST_RAM33B_PASS 0x0008 /* RAM33B passed */ +#define TX_RAMBIST_RAM32B_PASS 0x0004 /* RAM32B passed */ +#define TX_RAMBIST_SUMMARY 0x0002 /* all RAM passed */ +#define TX_RAMBIST_START 0x0001 /* write 1 to start BIST. self + clears on completion. */ + +/** receive dma registers **/ +#define MAX_RX_DESC_RINGS 2 +#define MAX_RX_COMP_RINGS 4 + +/* receive DMA channel configuration. default: 0x80910 + * free ring size = (1 << n)*32 -> [32 - 8k] + * completion ring size = (1 << n)*128 -> [128 - 32k], n < 9 + * DEFAULT: 0x80910 + */ +#define REG_RX_CFG 0x4000 /* RX config */ +#define RX_CFG_DMA_EN 0x00000001 /* enable RX DMA. 0 stops + channel as soon as current + frame xfer has completed. + driver should disable MAC + for 200ms before disabling + RX */ +#define RX_CFG_DESC_RING_MASK 0x0000001E /* # desc entries in RX + free desc ring. + def: 0x8 = 8k */ +#define RX_CFG_DESC_RING_SHIFT 1 +#define RX_CFG_COMP_RING_MASK 0x000001E0 /* # desc entries in RX complete + ring. def: 0x8 = 32k */ +#define RX_CFG_COMP_RING_SHIFT 5 +#define RX_CFG_BATCH_DIS 0x00000200 /* disable receive desc + batching. def: 0x0 = + enabled */ +#define RX_CFG_SWIVEL_MASK 0x00001C00 /* byte offset of the 1st + data byte of the packet + w/in 8 byte boundares. + this swivels the data + DMA'ed to header + buffers, jumbo buffers + when header split is not + requested and MTU sized + buffers. def: 0x2 */ +#define RX_CFG_SWIVEL_SHIFT 10 + +/* cassini+ only */ +#define RX_CFG_DESC_RING1_MASK 0x000F0000 /* # of desc entries in + RX free desc ring 2. + def: 0x8 = 8k */ +#define RX_CFG_DESC_RING1_SHIFT 16 + + +/* the page size register allows cassini chips to do the following with + * received data: + * [--------------------------------------------------------------] page + * [off][buf1][pad][off][buf2][pad][off][buf3][pad][off][buf4][pad] + * |--------------| = PAGE_SIZE_BUFFER_STRIDE + * page = PAGE_SIZE + * offset = PAGE_SIZE_MTU_OFF + * for the above example, MTU_BUFFER_COUNT = 4. + * NOTE: as is apparent, you need to ensure that the following holds: + * MTU_BUFFER_COUNT <= PAGE_SIZE/PAGE_SIZE_BUFFER_STRIDE + * DEFAULT: 0x48002002 (8k pages) + */ +#define REG_RX_PAGE_SIZE 0x4004 /* RX page size */ +#define RX_PAGE_SIZE_MASK 0x00000003 /* size of pages pointed to + by receive descriptors. + if jumbo buffers are + supported the page size + should not be < 8k. + 0b00 = 2k, 0b01 = 4k + 0b10 = 8k, 0b11 = 16k + DEFAULT: 8k */ +#define RX_PAGE_SIZE_SHIFT 0 +#define RX_PAGE_SIZE_MTU_COUNT_MASK 0x00007800 /* # of MTU buffers the hw + packs into a page. + DEFAULT: 4 */ +#define RX_PAGE_SIZE_MTU_COUNT_SHIFT 11 +#define RX_PAGE_SIZE_MTU_STRIDE_MASK 0x18000000 /* # of bytes that separate + each MTU buffer + + offset from each + other. + 0b00 = 1k, 0b01 = 2k + 0b10 = 4k, 0b11 = 8k + DEFAULT: 0x1 */ +#define RX_PAGE_SIZE_MTU_STRIDE_SHIFT 27 +#define RX_PAGE_SIZE_MTU_OFF_MASK 0xC0000000 /* offset in each page that + hw writes the MTU buffer + into. + 0b00 = 0, + 0b01 = 64 bytes + 0b10 = 96, 0b11 = 128 + DEFAULT: 0x1 */ +#define RX_PAGE_SIZE_MTU_OFF_SHIFT 30 + +/* 11-bit counter points to next location in RX FIFO to be loaded/read. + * shadow write pointers enable retries in case of early receive aborts. + * DEFAULT: 0x0. generated on 64-bit boundaries. + */ +#define REG_RX_FIFO_WRITE_PTR 0x4008 /* RX FIFO write pointer */ +#define REG_RX_FIFO_READ_PTR 0x400C /* RX FIFO read pointer */ +#define REG_RX_IPP_FIFO_SHADOW_WRITE_PTR 0x4010 /* RX IPP FIFO shadow write + pointer */ +#define REG_RX_IPP_FIFO_SHADOW_READ_PTR 0x4014 /* RX IPP FIFO shadow read + pointer */ +#define REG_RX_IPP_FIFO_READ_PTR 0x400C /* RX IPP FIFO read + pointer. (8-bit counter) */ + +/* current state of RX DMA state engines + other info + * DEFAULT: 0x0 + */ +#define REG_RX_DEBUG 0x401C /* RX debug */ +#define RX_DEBUG_LOAD_STATE_MASK 0x0000000F /* load state machine w/ MAC: + 0x0 = idle, 0x1 = load_bop + 0x2 = load 1, 0x3 = load 2 + 0x4 = load 3, 0x5 = load 4 + 0x6 = last detect + 0x7 = wait req + 0x8 = wait req statuss 1st + 0x9 = load st + 0xa = bubble mac + 0xb = error */ +#define RX_DEBUG_LM_STATE_MASK 0x00000070 /* load state machine w/ HP and + RX FIFO: + 0x0 = idle, 0x1 = hp xfr + 0x2 = wait hp ready + 0x3 = wait flow code + 0x4 = fifo xfer + 0x5 = make status + 0x6 = csum ready + 0x7 = error */ +#define RX_DEBUG_FC_STATE_MASK 0x000000180 /* flow control state machine + w/ MAC: + 0x0 = idle + 0x1 = wait xoff ack + 0x2 = wait xon + 0x3 = wait xon ack */ +#define RX_DEBUG_DATA_STATE_MASK 0x000001E00 /* unload data state machine + states: + 0x0 = idle data + 0x1 = header begin + 0x2 = xfer header + 0x3 = xfer header ld + 0x4 = mtu begin + 0x5 = xfer mtu + 0x6 = xfer mtu ld + 0x7 = jumbo begin + 0x8 = xfer jumbo + 0x9 = xfer jumbo ld + 0xa = reas begin + 0xb = xfer reas + 0xc = flush tag + 0xd = xfer reas ld + 0xe = error + 0xf = bubble idle */ +#define RX_DEBUG_DESC_STATE_MASK 0x0001E000 /* unload desc state machine + states: + 0x0 = idle desc + 0x1 = wait ack + 0x9 = wait ack 2 + 0x2 = fetch desc 1 + 0xa = fetch desc 2 + 0x3 = load ptrs + 0x4 = wait dma + 0x5 = wait ack batch + 0x6 = post batch + 0x7 = xfr done */ +#define RX_DEBUG_INTR_READ_PTR_MASK 0x30000000 /* interrupt read ptr of the + interrupt queue */ +#define RX_DEBUG_INTR_WRITE_PTR_MASK 0xC0000000 /* interrupt write pointer + of the interrupt queue */ + +/* flow control frames are emmitted using two PAUSE thresholds: + * XOFF PAUSE uses pause time value pre-programmed in the Send PAUSE MAC reg + * XON PAUSE uses a pause time of 0. granularity of threshold is 64bytes. + * PAUSE thresholds defined in terms of FIFO occupancy and may be translated + * into FIFO vacancy using RX_FIFO_SIZE. setting ON will trigger XON frames + * when FIFO reaches 0. OFF threshold should not be > size of RX FIFO. max + * value is is 0x6F. + * DEFAULT: 0x00078 + */ +#define REG_RX_PAUSE_THRESH 0x4020 /* RX pause thresholds */ +#define RX_PAUSE_THRESH_QUANTUM 64 +#define RX_PAUSE_THRESH_OFF_MASK 0x000001FF /* XOFF PAUSE emitted when + RX FIFO occupancy > + value*64B */ +#define RX_PAUSE_THRESH_OFF_SHIFT 0 +#define RX_PAUSE_THRESH_ON_MASK 0x001FF000 /* XON PAUSE emitted after + emitting XOFF PAUSE when RX + FIFO occupancy falls below + this value*64B. must be + < XOFF threshold. if = + RX_FIFO_SIZE< XON frames are + never emitted. */ +#define RX_PAUSE_THRESH_ON_SHIFT 12 + +/* 13-bit register used to control RX desc fetching and intr generation. if 4+ + * valid RX descriptors are available, Cassini will read 4 at a time. + * writing N means that all desc up to *but* excluding N are available. N must + * be a multiple of 4 (N % 4 = 0). first desc should be cache-line aligned. + * DEFAULT: 0 on reset + */ +#define REG_RX_KICK 0x4024 /* RX kick reg */ + +/* 8KB aligned 64-bit pointer to the base of the RX free/completion rings. + * lower 13 bits of the low register are hard-wired to 0. + */ +#define REG_RX_DB_LOW 0x4028 /* RX descriptor ring + base low */ +#define REG_RX_DB_HI 0x402C /* RX descriptor ring + base hi */ +#define REG_RX_CB_LOW 0x4030 /* RX completion ring + base low */ +#define REG_RX_CB_HI 0x4034 /* RX completion ring + base hi */ +/* 13-bit register indicate desc used by cassini for receive frames. used + * for diagnostic purposes. + * DEFAULT: 0 on reset + */ +#define REG_RX_COMP 0x4038 /* (ro) RX completion */ + +/* HEAD and TAIL are used to control RX desc posting and interrupt + * generation. hw moves the head register to pass ownership to sw. sw + * moves the tail register to pass ownership back to hw. to give all + * entries to hw, set TAIL = HEAD. if HEAD and TAIL indicate that no + * more entries are available, DMA will pause and an interrupt will be + * generated to indicate no more entries are available. sw can use + * this interrupt to reduce the # of times it must update the + * completion tail register. + * DEFAULT: 0 on reset + */ +#define REG_RX_COMP_HEAD 0x403C /* RX completion head */ +#define REG_RX_COMP_TAIL 0x4040 /* RX completion tail */ + +/* values used for receive interrupt blanking. loaded each time the ISR is read + * DEFAULT: 0x00000000 + */ +#define REG_RX_BLANK 0x4044 /* RX blanking register + for ISR read */ +#define RX_BLANK_INTR_PKT_MASK 0x000001FF /* RX_DONE intr asserted if + this many sets of completion + writebacks (up to 2 packets) + occur since the last time + the ISR was read. 0 = no + packet blanking */ +#define RX_BLANK_INTR_PKT_SHIFT 0 +#define RX_BLANK_INTR_TIME_MASK 0x3FFFF000 /* RX_DONE interrupt asserted + if that many clocks were + counted since last time the + ISR was read. + each count is 512 core + clocks (125MHz). 0 = no + time blanking */ +#define RX_BLANK_INTR_TIME_SHIFT 12 + +/* values used for interrupt generation based on threshold values of how + * many free desc and completion entries are available for hw use. + * DEFAULT: 0x00000000 + */ +#define REG_RX_AE_THRESH 0x4048 /* RX almost empty + thresholds */ +#define RX_AE_THRESH_FREE_MASK 0x00001FFF /* RX_BUF_AE will be + generated if # desc + avail for hw use <= + # */ +#define RX_AE_THRESH_FREE_SHIFT 0 +#define RX_AE_THRESH_COMP_MASK 0x0FFFE000 /* RX_COMP_AE will be + generated if # of + completion entries + avail for hw use <= + # */ +#define RX_AE_THRESH_COMP_SHIFT 13 + +/* probabilities for random early drop (RED) thresholds on a FIFO threshold + * basis. probability should increase when the FIFO level increases. control + * packets are never dropped and not counted in stats. probability programmed + * on a 12.5% granularity. e.g., 0x1 = 1/8 packets dropped. + * DEFAULT: 0x00000000 + */ +#define REG_RX_RED 0x404C /* RX random early detect enable */ +#define RX_RED_4K_6K_FIFO_MASK 0x000000FF /* 4KB < FIFO thresh < 6KB */ +#define RX_RED_6K_8K_FIFO_MASK 0x0000FF00 /* 6KB < FIFO thresh < 8KB */ +#define RX_RED_8K_10K_FIFO_MASK 0x00FF0000 /* 8KB < FIFO thresh < 10KB */ +#define RX_RED_10K_12K_FIFO_MASK 0xFF000000 /* 10KB < FIFO thresh < 12KB */ + +/* FIFO fullness levels for RX FIFO, RX control FIFO, and RX IPP FIFO. + * RX control FIFO = # of packets in RX FIFO. + * DEFAULT: 0x0 + */ +#define REG_RX_FIFO_FULLNESS 0x4050 /* (ro) RX FIFO fullness */ +#define RX_FIFO_FULLNESS_RX_FIFO_MASK 0x3FF80000 /* level w/ 8B granularity */ +#define RX_FIFO_FULLNESS_IPP_FIFO_MASK 0x0007FF00 /* level w/ 8B granularity */ +#define RX_FIFO_FULLNESS_RX_PKT_MASK 0x000000FF /* # packets in RX FIFO */ +#define REG_RX_IPP_PACKET_COUNT 0x4054 /* RX IPP packet counter */ +#define REG_RX_WORK_DMA_PTR_LOW 0x4058 /* RX working DMA ptr low */ +#define REG_RX_WORK_DMA_PTR_HI 0x405C /* RX working DMA ptr + high */ + +/* BIST testing ro RX FIFO, RX control FIFO, and RX IPP FIFO. only RX BIST + * START/COMPLETE is writeable. START will clear when the BIST has completed + * checking all 17 RAMS. + * DEFAULT: 0bxxxx xxxxx xxxx xxxx xxxx x000 0000 0000 00x0 + */ +#define REG_RX_BIST 0x4060 /* (ro) RX BIST */ +#define RX_BIST_32A_PASS 0x80000000 /* RX FIFO 32A passed */ +#define RX_BIST_33A_PASS 0x40000000 /* RX FIFO 33A passed */ +#define RX_BIST_32B_PASS 0x20000000 /* RX FIFO 32B passed */ +#define RX_BIST_33B_PASS 0x10000000 /* RX FIFO 33B passed */ +#define RX_BIST_32C_PASS 0x08000000 /* RX FIFO 32C passed */ +#define RX_BIST_33C_PASS 0x04000000 /* RX FIFO 33C passed */ +#define RX_BIST_IPP_32A_PASS 0x02000000 /* RX IPP FIFO 33B passed */ +#define RX_BIST_IPP_33A_PASS 0x01000000 /* RX IPP FIFO 33A passed */ +#define RX_BIST_IPP_32B_PASS 0x00800000 /* RX IPP FIFO 32B passed */ +#define RX_BIST_IPP_33B_PASS 0x00400000 /* RX IPP FIFO 33B passed */ +#define RX_BIST_IPP_32C_PASS 0x00200000 /* RX IPP FIFO 32C passed */ +#define RX_BIST_IPP_33C_PASS 0x00100000 /* RX IPP FIFO 33C passed */ +#define RX_BIST_CTRL_32_PASS 0x00800000 /* RX CTRL FIFO 32 passed */ +#define RX_BIST_CTRL_33_PASS 0x00400000 /* RX CTRL FIFO 33 passed */ +#define RX_BIST_REAS_26A_PASS 0x00200000 /* RX Reas 26A passed */ +#define RX_BIST_REAS_26B_PASS 0x00100000 /* RX Reas 26B passed */ +#define RX_BIST_REAS_27_PASS 0x00080000 /* RX Reas 27 passed */ +#define RX_BIST_STATE_MASK 0x00078000 /* BIST state machine */ +#define RX_BIST_SUMMARY 0x00000002 /* when BIST complete, + summary pass bit + contains AND of BIST + results of all 16 + RAMS */ +#define RX_BIST_START 0x00000001 /* write 1 to start + BIST. self clears + on completion. */ + +/* next location in RX CTRL FIFO that will be loaded w/ data from RX IPP/read + * from to retrieve packet control info. + * DEFAULT: 0 + */ +#define REG_RX_CTRL_FIFO_WRITE_PTR 0x4064 /* (ro) RX control FIFO + write ptr */ +#define REG_RX_CTRL_FIFO_READ_PTR 0x4068 /* (ro) RX control FIFO read + ptr */ + +/* receive interrupt blanking. loaded each time interrupt alias register is + * read. + * DEFAULT: 0x0 + */ +#define REG_RX_BLANK_ALIAS_READ 0x406C /* RX blanking register for + alias read */ +#define RX_BAR_INTR_PACKET_MASK 0x000001FF /* assert RX_DONE if # + completion writebacks + > # since last ISR + read. 0 = no + blanking. up to 2 + packets per + completion wb. */ +#define RX_BAR_INTR_TIME_MASK 0x3FFFF000 /* assert RX_DONE if # + clocks > # since last + ISR read. each count + is 512 core clocks + (125MHz). 0 = no + blanking. */ + +/* diagnostic access to RX FIFO. 32 LSB accessed via DATA_LOW. 32 MSB accessed + * via DATA_HI_T0 or DATA_HI_T1. TAG reads the tag bit. writing HI_T0 + * will unset the tag bit while writing HI_T1 will set the tag bit. to reset + * to normal operation after diagnostics, write to address location 0x0. + * RX_DMA_EN bit must be set to 0x0 for RX FIFO PIO access. DATA_HI should + * be the last write access of a write sequence. + * DEFAULT: undefined + */ +#define REG_RX_FIFO_ADDR 0x4080 /* RX FIFO address */ +#define REG_RX_FIFO_TAG 0x4084 /* RX FIFO tag */ +#define REG_RX_FIFO_DATA_LOW 0x4088 /* RX FIFO data low */ +#define REG_RX_FIFO_DATA_HI_T0 0x408C /* RX FIFO data high T0 */ +#define REG_RX_FIFO_DATA_HI_T1 0x4090 /* RX FIFO data high T1 */ + +/* diagnostic assess to RX CTRL FIFO. 8-bit FIFO_ADDR holds address of + * 81 bit control entry and 6 bit flow id. LOW and MID are both 32-bit + * accesses. HI is 7-bits with 6-bit flow id and 1 bit control + * word. RX_DMA_EN must be 0 for RX CTRL FIFO PIO access. DATA_HI + * should be last write access of the write sequence. + * DEFAULT: undefined + */ +#define REG_RX_CTRL_FIFO_ADDR 0x4094 /* RX Control FIFO and + Batching FIFO addr */ +#define REG_RX_CTRL_FIFO_DATA_LOW 0x4098 /* RX Control FIFO data + low */ +#define REG_RX_CTRL_FIFO_DATA_MID 0x409C /* RX Control FIFO data + mid */ +#define REG_RX_CTRL_FIFO_DATA_HI 0x4100 /* RX Control FIFO data + hi and flow id */ +#define RX_CTRL_FIFO_DATA_HI_CTRL 0x0001 /* upper bit of ctrl word */ +#define RX_CTRL_FIFO_DATA_HI_FLOW_MASK 0x007E /* flow id */ + +/* diagnostic access to RX IPP FIFO. same semantics as RX_FIFO. + * DEFAULT: undefined + */ +#define REG_RX_IPP_FIFO_ADDR 0x4104 /* RX IPP FIFO address */ +#define REG_RX_IPP_FIFO_TAG 0x4108 /* RX IPP FIFO tag */ +#define REG_RX_IPP_FIFO_DATA_LOW 0x410C /* RX IPP FIFO data low */ +#define REG_RX_IPP_FIFO_DATA_HI_T0 0x4110 /* RX IPP FIFO data high + T0 */ +#define REG_RX_IPP_FIFO_DATA_HI_T1 0x4114 /* RX IPP FIFO data high + T1 */ + +/* 64-bit pointer to receive data buffer in host memory used for headers and + * small packets. MSB in high register. loaded by DMA state machine and + * increments as DMA writes receive data. only 50 LSB are incremented. top + * 13 bits taken from RX descriptor. + * DEFAULT: undefined + */ +#define REG_RX_HEADER_PAGE_PTR_LOW 0x4118 /* (ro) RX header page ptr + low */ +#define REG_RX_HEADER_PAGE_PTR_HI 0x411C /* (ro) RX header page ptr + high */ +#define REG_RX_MTU_PAGE_PTR_LOW 0x4120 /* (ro) RX MTU page pointer + low */ +#define REG_RX_MTU_PAGE_PTR_HI 0x4124 /* (ro) RX MTU page pointer + high */ + +/* PIO diagnostic access to RX reassembly DMA Table RAM. 6-bit register holds + * one of 64 79-bit locations in the RX Reassembly DMA table and the addr of + * one of the 64 byte locations in the Batching table. LOW holds 32 LSB. + * MID holds the next 32 LSB. HIGH holds the 15 MSB. RX_DMA_EN must be set + * to 0 for PIO access. DATA_HIGH should be last write of write sequence. + * layout: + * reassmbl ptr [78:15] | reassmbl index [14:1] | reassmbl entry valid [0] + * DEFAULT: undefined + */ +#define REG_RX_TABLE_ADDR 0x4128 /* RX reassembly DMA table + address */ +#define RX_TABLE_ADDR_MASK 0x0000003F /* address mask */ + +#define REG_RX_TABLE_DATA_LOW 0x412C /* RX reassembly DMA table + data low */ +#define REG_RX_TABLE_DATA_MID 0x4130 /* RX reassembly DMA table + data mid */ +#define REG_RX_TABLE_DATA_HI 0x4134 /* RX reassembly DMA table + data high */ + +/* cassini+ only */ +/* 8KB aligned 64-bit pointer to base of RX rings. lower 13 bits hardwired to + * 0. same semantics as primary desc/complete rings. + */ +#define REG_PLUS_RX_DB1_LOW 0x4200 /* RX descriptor ring + 2 base low */ +#define REG_PLUS_RX_DB1_HI 0x4204 /* RX descriptor ring + 2 base high */ +#define REG_PLUS_RX_CB1_LOW 0x4208 /* RX completion ring + 2 base low. 4 total */ +#define REG_PLUS_RX_CB1_HI 0x420C /* RX completion ring + 2 base high. 4 total */ +#define REG_PLUS_RX_CBN_LOW(x) (REG_PLUS_RX_CB1_LOW + 8*((x) - 1)) +#define REG_PLUS_RX_CBN_HI(x) (REG_PLUS_RX_CB1_HI + 8*((x) - 1)) +#define REG_PLUS_RX_KICK1 0x4220 /* RX Kick 2 register */ +#define REG_PLUS_RX_COMP1 0x4224 /* (ro) RX completion 2 + reg */ +#define REG_PLUS_RX_COMP1_HEAD 0x4228 /* (ro) RX completion 2 + head reg. 4 total. */ +#define REG_PLUS_RX_COMP1_TAIL 0x422C /* RX completion 2 + tail reg. 4 total. */ +#define REG_PLUS_RX_COMPN_HEAD(x) (REG_PLUS_RX_COMP1_HEAD + 8*((x) - 1)) +#define REG_PLUS_RX_COMPN_TAIL(x) (REG_PLUS_RX_COMP1_TAIL + 8*((x) - 1)) +#define REG_PLUS_RX_AE1_THRESH 0x4240 /* RX almost empty 2 + thresholds */ +#define RX_AE1_THRESH_FREE_MASK RX_AE_THRESH_FREE_MASK +#define RX_AE1_THRESH_FREE_SHIFT RX_AE_THRESH_FREE_SHIFT + +/** header parser registers **/ + +/* RX parser configuration register. + * DEFAULT: 0x1651004 + */ +#define REG_HP_CFG 0x4140 /* header parser + configuration reg */ +#define HP_CFG_PARSE_EN 0x00000001 /* enab header parsing */ +#define HP_CFG_NUM_CPU_MASK 0x000000FC /* # processors + 0 = 64. 0x3f = 63 */ +#define HP_CFG_NUM_CPU_SHIFT 2 +#define HP_CFG_SYN_INC_MASK 0x00000100 /* SYN bit won't increment + TCP seq # by one when + stored in FDBM */ +#define HP_CFG_TCP_THRESH_MASK 0x000FFE00 /* # bytes of TCP data + needed to be considered + for reassembly */ +#define HP_CFG_TCP_THRESH_SHIFT 9 + +/* access to RX Instruction RAM. 5-bit register/counter holds addr + * of 39 bit entry to be read/written. 32 LSB in _DATA_LOW. 7 MSB in _DATA_HI. + * RX_DMA_EN must be 0 for RX instr PIO access. DATA_HI should be last access + * of sequence. + * DEFAULT: undefined + */ +#define REG_HP_INSTR_RAM_ADDR 0x4144 /* HP instruction RAM + address */ +#define HP_INSTR_RAM_ADDR_MASK 0x01F /* 5-bit mask */ +#define REG_HP_INSTR_RAM_DATA_LOW 0x4148 /* HP instruction RAM + data low */ +#define HP_INSTR_RAM_LOW_OUTMASK_MASK 0x0000FFFF +#define HP_INSTR_RAM_LOW_OUTMASK_SHIFT 0 +#define HP_INSTR_RAM_LOW_OUTSHIFT_MASK 0x000F0000 +#define HP_INSTR_RAM_LOW_OUTSHIFT_SHIFT 16 +#define HP_INSTR_RAM_LOW_OUTEN_MASK 0x00300000 +#define HP_INSTR_RAM_LOW_OUTEN_SHIFT 20 +#define HP_INSTR_RAM_LOW_OUTARG_MASK 0xFFC00000 +#define HP_INSTR_RAM_LOW_OUTARG_SHIFT 22 +#define REG_HP_INSTR_RAM_DATA_MID 0x414C /* HP instruction RAM + data mid */ +#define HP_INSTR_RAM_MID_OUTARG_MASK 0x00000003 +#define HP_INSTR_RAM_MID_OUTARG_SHIFT 0 +#define HP_INSTR_RAM_MID_OUTOP_MASK 0x0000003C +#define HP_INSTR_RAM_MID_OUTOP_SHIFT 2 +#define HP_INSTR_RAM_MID_FNEXT_MASK 0x000007C0 +#define HP_INSTR_RAM_MID_FNEXT_SHIFT 6 +#define HP_INSTR_RAM_MID_FOFF_MASK 0x0003F800 +#define HP_INSTR_RAM_MID_FOFF_SHIFT 11 +#define HP_INSTR_RAM_MID_SNEXT_MASK 0x007C0000 +#define HP_INSTR_RAM_MID_SNEXT_SHIFT 18 +#define HP_INSTR_RAM_MID_SOFF_MASK 0x3F800000 +#define HP_INSTR_RAM_MID_SOFF_SHIFT 23 +#define HP_INSTR_RAM_MID_OP_MASK 0xC0000000 +#define HP_INSTR_RAM_MID_OP_SHIFT 30 +#define REG_HP_INSTR_RAM_DATA_HI 0x4150 /* HP instruction RAM + data high */ +#define HP_INSTR_RAM_HI_VAL_MASK 0x0000FFFF +#define HP_INSTR_RAM_HI_VAL_SHIFT 0 +#define HP_INSTR_RAM_HI_MASK_MASK 0xFFFF0000 +#define HP_INSTR_RAM_HI_MASK_SHIFT 16 + +/* PIO access into RX Header parser data RAM and flow database. + * 11-bit register. Data fills the LSB portion of bus if less than 32 bits. + * DATA_RAM: write RAM_FDB_DATA with index to access DATA_RAM. + * RAM bytes = 4*(x - 1) + [3:0]. e.g., 0 -> [3:0], 31 -> [123:120] + * FLOWDB: write DATA_RAM_FDB register and then read/write FDB1-12 to access + * flow database. + * RX_DMA_EN must be 0 for RX parser RAM PIO access. RX Parser RAM data reg + * should be the last write access of the write sequence. + * DEFAULT: undefined + */ +#define REG_HP_DATA_RAM_FDB_ADDR 0x4154 /* HP data and FDB + RAM address */ +#define HP_DATA_RAM_FDB_DATA_MASK 0x001F /* select 1 of 86 byte + locations in header + parser data ram to + read/write */ +#define HP_DATA_RAM_FDB_FDB_MASK 0x3F00 /* 1 of 64 353-bit locations + in the flow database */ +#define REG_HP_DATA_RAM_DATA 0x4158 /* HP data RAM data */ + +/* HP flow database registers: 1 - 12, 0x415C - 0x4188, 4 8-bit bytes + * FLOW_DB(1) = IP_SA[127:96], FLOW_DB(2) = IP_SA[95:64] + * FLOW_DB(3) = IP_SA[63:32], FLOW_DB(4) = IP_SA[31:0] + * FLOW_DB(5) = IP_DA[127:96], FLOW_DB(6) = IP_DA[95:64] + * FLOW_DB(7) = IP_DA[63:32], FLOW_DB(8) = IP_DA[31:0] + * FLOW_DB(9) = {TCP_SP[15:0],TCP_DP[15:0]} + * FLOW_DB(10) = bit 0 has value for flow valid + * FLOW_DB(11) = TCP_SEQ[63:32], FLOW_DB(12) = TCP_SEQ[31:0] + */ +#define REG_HP_FLOW_DB0 0x415C /* HP flow database 1 reg */ +#define REG_HP_FLOW_DBN(x) (REG_HP_FLOW_DB0 + (x)*4) + +/* diagnostics for RX Header Parser block. + * ASUN: the header parser state machine register is used for diagnostics + * purposes. however, the spec doesn't have any details on it. + */ +#define REG_HP_STATE_MACHINE 0x418C /* (ro) HP state machine */ +#define REG_HP_STATUS0 0x4190 /* (ro) HP status 1 */ +#define HP_STATUS0_SAP_MASK 0xFFFF0000 /* SAP */ +#define HP_STATUS0_L3_OFF_MASK 0x0000FE00 /* L3 offset */ +#define HP_STATUS0_LB_CPUNUM_MASK 0x000001F8 /* load balancing CPU + number */ +#define HP_STATUS0_HRP_OPCODE_MASK 0x00000007 /* HRP opcode */ + +#define REG_HP_STATUS1 0x4194 /* (ro) HP status 2 */ +#define HP_STATUS1_ACCUR2_MASK 0xE0000000 /* accu R2[6:4] */ +#define HP_STATUS1_FLOWID_MASK 0x1F800000 /* flow id */ +#define HP_STATUS1_TCP_OFF_MASK 0x007F0000 /* tcp payload offset */ +#define HP_STATUS1_TCP_SIZE_MASK 0x0000FFFF /* tcp payload size */ + +#define REG_HP_STATUS2 0x4198 /* (ro) HP status 3 */ +#define HP_STATUS2_ACCUR2_MASK 0xF0000000 /* accu R2[3:0] */ +#define HP_STATUS2_CSUM_OFF_MASK 0x07F00000 /* checksum start + start offset */ +#define HP_STATUS2_ACCUR1_MASK 0x000FE000 /* accu R1 */ +#define HP_STATUS2_FORCE_DROP 0x00001000 /* force drop */ +#define HP_STATUS2_BWO_REASSM 0x00000800 /* batching w/o + reassembly */ +#define HP_STATUS2_JH_SPLIT_EN 0x00000400 /* jumbo header split + enable */ +#define HP_STATUS2_FORCE_TCP_NOCHECK 0x00000200 /* force tcp no payload + check */ +#define HP_STATUS2_DATA_MASK_ZERO 0x00000100 /* mask of data length + equal to zero */ +#define HP_STATUS2_FORCE_TCP_CHECK 0x00000080 /* force tcp payload + chk */ +#define HP_STATUS2_MASK_TCP_THRESH 0x00000040 /* mask of payload + threshold */ +#define HP_STATUS2_NO_ASSIST 0x00000020 /* no assist */ +#define HP_STATUS2_CTRL_PACKET_FLAG 0x00000010 /* control packet flag */ +#define HP_STATUS2_TCP_FLAG_CHECK 0x00000008 /* tcp flag check */ +#define HP_STATUS2_SYN_FLAG 0x00000004 /* syn flag */ +#define HP_STATUS2_TCP_CHECK 0x00000002 /* tcp payload chk */ +#define HP_STATUS2_TCP_NOCHECK 0x00000001 /* tcp no payload chk */ + +/* BIST for header parser(HP) and flow database memories (FDBM). set _START + * to start BIST. controller clears _START on completion. _START can also + * be cleared to force termination of BIST. a bit set indicates that that + * memory passed its BIST. + */ +#define REG_HP_RAM_BIST 0x419C /* HP RAM BIST reg */ +#define HP_RAM_BIST_HP_DATA_PASS 0x80000000 /* HP data ram */ +#define HP_RAM_BIST_HP_INSTR0_PASS 0x40000000 /* HP instr ram 0 */ +#define HP_RAM_BIST_HP_INSTR1_PASS 0x20000000 /* HP instr ram 1 */ +#define HP_RAM_BIST_HP_INSTR2_PASS 0x10000000 /* HP instr ram 2 */ +#define HP_RAM_BIST_FDBM_AGE0_PASS 0x08000000 /* FDBM aging RAM0 */ +#define HP_RAM_BIST_FDBM_AGE1_PASS 0x04000000 /* FDBM aging RAM1 */ +#define HP_RAM_BIST_FDBM_FLOWID00_PASS 0x02000000 /* FDBM flowid RAM0 + bank 0 */ +#define HP_RAM_BIST_FDBM_FLOWID10_PASS 0x01000000 /* FDBM flowid RAM1 + bank 0 */ +#define HP_RAM_BIST_FDBM_FLOWID20_PASS 0x00800000 /* FDBM flowid RAM2 + bank 0 */ +#define HP_RAM_BIST_FDBM_FLOWID30_PASS 0x00400000 /* FDBM flowid RAM3 + bank 0 */ +#define HP_RAM_BIST_FDBM_FLOWID01_PASS 0x00200000 /* FDBM flowid RAM0 + bank 1 */ +#define HP_RAM_BIST_FDBM_FLOWID11_PASS 0x00100000 /* FDBM flowid RAM1 + bank 2 */ +#define HP_RAM_BIST_FDBM_FLOWID21_PASS 0x00080000 /* FDBM flowid RAM2 + bank 1 */ +#define HP_RAM_BIST_FDBM_FLOWID31_PASS 0x00040000 /* FDBM flowid RAM3 + bank 1 */ +#define HP_RAM_BIST_FDBM_TCPSEQ_PASS 0x00020000 /* FDBM tcp sequence + RAM */ +#define HP_RAM_BIST_SUMMARY 0x00000002 /* all BIST tests */ +#define HP_RAM_BIST_START 0x00000001 /* start/stop BIST */ + + +/** MAC registers. **/ +/* reset bits are set using a PIO write and self-cleared after the command + * execution has completed. + */ +#define REG_MAC_TX_RESET 0x6000 /* TX MAC software reset + command (default: 0x0) */ +#define REG_MAC_RX_RESET 0x6004 /* RX MAC software reset + command (default: 0x0) */ +/* execute a pause flow control frame transmission + DEFAULT: 0x0XXXX */ +#define REG_MAC_SEND_PAUSE 0x6008 /* send pause command reg */ +#define MAC_SEND_PAUSE_TIME_MASK 0x0000FFFF /* value of pause time + to be sent on network + in units of slot + times */ +#define MAC_SEND_PAUSE_SEND 0x00010000 /* send pause flow ctrl + frame on network */ + +/* bit set indicates that event occurred. auto-cleared when status register + * is read and have corresponding mask bits in mask register. events will + * trigger an interrupt if the corresponding mask bit is 0. + * status register default: 0x00000000 + * mask register default = 0xFFFFFFFF on reset + */ +#define REG_MAC_TX_STATUS 0x6010 /* TX MAC status reg */ +#define MAC_TX_FRAME_XMIT 0x0001 /* successful frame + transmision */ +#define MAC_TX_UNDERRUN 0x0002 /* terminated frame + transmission due to + data starvation in the + xmit data path */ +#define MAC_TX_MAX_PACKET_ERR 0x0004 /* frame exceeds max allowed + length passed to TX MAC + by the DMA engine */ +#define MAC_TX_COLL_NORMAL 0x0008 /* rollover of the normal + collision counter */ +#define MAC_TX_COLL_EXCESS 0x0010 /* rollover of the excessive + collision counter */ +#define MAC_TX_COLL_LATE 0x0020 /* rollover of the late + collision counter */ +#define MAC_TX_COLL_FIRST 0x0040 /* rollover of the first + collision counter */ +#define MAC_TX_DEFER_TIMER 0x0080 /* rollover of the defer + timer */ +#define MAC_TX_PEAK_ATTEMPTS 0x0100 /* rollover of the peak + attempts counter */ + +#define REG_MAC_RX_STATUS 0x6014 /* RX MAC status reg */ +#define MAC_RX_FRAME_RECV 0x0001 /* successful receipt of + a frame */ +#define MAC_RX_OVERFLOW 0x0002 /* dropped frame due to + RX FIFO overflow */ +#define MAC_RX_FRAME_COUNT 0x0004 /* rollover of receive frame + counter */ +#define MAC_RX_ALIGN_ERR 0x0008 /* rollover of alignment + error counter */ +#define MAC_RX_CRC_ERR 0x0010 /* rollover of crc error + counter */ +#define MAC_RX_LEN_ERR 0x0020 /* rollover of length + error counter */ +#define MAC_RX_VIOL_ERR 0x0040 /* rollover of code + violation error */ + +/* DEFAULT: 0xXXXX0000 on reset */ +#define REG_MAC_CTRL_STATUS 0x6018 /* MAC control status reg */ +#define MAC_CTRL_PAUSE_RECEIVED 0x00000001 /* successful + reception of a + pause control + frame */ +#define MAC_CTRL_PAUSE_STATE 0x00000002 /* MAC has made a + transition from + "not paused" to + "paused" */ +#define MAC_CTRL_NOPAUSE_STATE 0x00000004 /* MAC has made a + transition from + "paused" to "not + paused" */ +#define MAC_CTRL_PAUSE_TIME_MASK 0xFFFF0000 /* value of pause time + operand that was + received in the last + pause flow control + frame */ + +/* layout identical to TX MAC[8:0] */ +#define REG_MAC_TX_MASK 0x6020 /* TX MAC mask reg */ +/* layout identical to RX MAC[6:0] */ +#define REG_MAC_RX_MASK 0x6024 /* RX MAC mask reg */ +/* layout identical to CTRL MAC[2:0] */ +#define REG_MAC_CTRL_MASK 0x6028 /* MAC control mask reg */ + +/* to ensure proper operation, CFG_EN must be cleared to 0 and a delay + * imposed before writes to other bits in the TX_MAC_CFG register or any of + * the MAC parameters is performed. delay dependent upon time required to + * transmit a maximum size frame (= MAC_FRAMESIZE_MAX*8/Mbps). e.g., + * the delay for a 1518-byte frame on a 100Mbps network is 125us. + * alternatively, just poll TX_CFG_EN until it reads back as 0. + * NOTE: on half-duplex 1Gbps, TX_CFG_CARRIER_EXTEND and + * RX_CFG_CARRIER_EXTEND should be set and the SLOT_TIME register should + * be 0x200 (slot time of 512 bytes) + */ +#define REG_MAC_TX_CFG 0x6030 /* TX MAC config reg */ +#define MAC_TX_CFG_EN 0x0001 /* enable TX MAC. 0 will + force TXMAC state + machine to remain in + idle state or to + transition to idle state + on completion of an + ongoing packet. */ +#define MAC_TX_CFG_IGNORE_CARRIER 0x0002 /* disable CSMA/CD deferral + process. set to 1 when + full duplex and 0 when + half duplex */ +#define MAC_TX_CFG_IGNORE_COLL 0x0004 /* disable CSMA/CD backoff + algorithm. set to 1 when + full duplex and 0 when + half duplex */ +#define MAC_TX_CFG_IPG_EN 0x0008 /* enable extension of the + Rx-to-TX IPG. after + receiving a frame, TX + MAC will reset its + deferral process to + carrier sense for the + amount of time = IPG0 + + IPG1 and commit to + transmission for time + specified in IPG2. when + 0 or when xmitting frames + back-to-pack (Tx-to-Tx + IPG), TX MAC ignores + IPG0 and will only use + IPG1 for deferral time. + IPG2 still used. */ +#define MAC_TX_CFG_NEVER_GIVE_UP_EN 0x0010 /* TX MAC will not easily + give up on frame + xmission. if backoff + algorithm reaches the + ATTEMPT_LIMIT, it will + clear attempts counter + and continue trying to + send the frame as + specified by + GIVE_UP_LIM. when 0, + TX MAC will execute + standard CSMA/CD prot. */ +#define MAC_TX_CFG_NEVER_GIVE_UP_LIM 0x0020 /* when set, TX MAC will + continue to try to xmit + until successful. when + 0, TX MAC will continue + to try xmitting until + successful or backoff + algorithm reaches + ATTEMPT_LIMIT*16 */ +#define MAC_TX_CFG_NO_BACKOFF 0x0040 /* modify CSMA/CD to disable + backoff algorithm. TX + MAC will not back off + after a xmission attempt + that resulted in a + collision. */ +#define MAC_TX_CFG_SLOW_DOWN 0x0080 /* modify CSMA/CD so that + deferral process is reset + in response to carrier + sense during the entire + duration of IPG. TX MAC + will only commit to frame + xmission after frame + xmission has actually + begun. */ +#define MAC_TX_CFG_NO_FCS 0x0100 /* TX MAC will not generate + CRC for all xmitted + packets. when clear, CRC + generation is dependent + upon NO_CRC bit in the + xmit control word from + TX DMA */ +#define MAC_TX_CFG_CARRIER_EXTEND 0x0200 /* enables xmit part of the + carrier extension + feature. this allows for + longer collision domains + by extending the carrier + and collision window + from the end of FCS until + the end of the slot time + if necessary. Required + for half-duplex at 1Gbps, + clear otherwise. */ + +/* when CRC is not stripped, reassembly packets will not contain the CRC. + * these will be stripped by HRP because it reassembles layer 4 data, and the + * CRC is layer 2. however, non-reassembly packets will still contain the CRC + * when passed to the host. to ensure proper operation, need to wait 3.2ms + * after clearing RX_CFG_EN before writing to any other RX MAC registers + * or other MAC parameters. alternatively, poll RX_CFG_EN until it clears + * to 0. similary, HASH_FILTER_EN and ADDR_FILTER_EN have the same + * restrictions as CFG_EN. + */ +#define REG_MAC_RX_CFG 0x6034 /* RX MAC config reg */ +#define MAC_RX_CFG_EN 0x0001 /* enable RX MAC */ +#define MAC_RX_CFG_STRIP_PAD 0x0002 /* always program to 0. + feature not supported */ +#define MAC_RX_CFG_STRIP_FCS 0x0004 /* RX MAC will strip the + last 4 bytes of a + received frame. */ +#define MAC_RX_CFG_PROMISC_EN 0x0008 /* promiscuous mode */ +#define MAC_RX_CFG_PROMISC_GROUP_EN 0x0010 /* accept all valid + multicast frames (group + bit in DA field set) */ +#define MAC_RX_CFG_HASH_FILTER_EN 0x0020 /* use hash table to filter + multicast addresses */ +#define MAC_RX_CFG_ADDR_FILTER_EN 0x0040 /* cause RX MAC to use + address filtering regs + to filter both unicast + and multicast + addresses */ +#define MAC_RX_CFG_DISABLE_DISCARD 0x0080 /* pass errored frames to + RX DMA by setting BAD + bit but not Abort bit + in the status. CRC, + framing, and length errs + will not increment + error counters. frames + which don't match dest + addr will be passed up + w/ BAD bit set. */ +#define MAC_RX_CFG_CARRIER_EXTEND 0x0100 /* enable reception of + packet bursts generated + by carrier extension + with packet bursting + senders. only applies + to half-duplex 1Gbps */ + +/* DEFAULT: 0x0 */ +#define REG_MAC_CTRL_CFG 0x6038 /* MAC control config reg */ +#define MAC_CTRL_CFG_SEND_PAUSE_EN 0x0001 /* respond to requests for + sending pause flow ctrl + frames */ +#define MAC_CTRL_CFG_RECV_PAUSE_EN 0x0002 /* respond to received + pause flow ctrl frames */ +#define MAC_CTRL_CFG_PASS_CTRL 0x0004 /* pass valid MAC ctrl + packets to RX DMA */ + +/* to ensure proper operation, a global initialization sequence should be + * performed when a loopback config is entered or exited. if programmed after + * a hw or global sw reset, RX/TX MAC software reset and initialization + * should be done to ensure stable clocking. + * DEFAULT: 0x0 + */ +#define REG_MAC_XIF_CFG 0x603C /* XIF config reg */ +#define MAC_XIF_TX_MII_OUTPUT_EN 0x0001 /* enable output drivers + on MII xmit bus */ +#define MAC_XIF_MII_INT_LOOPBACK 0x0002 /* loopback GMII xmit data + path to GMII recv data + path. phy mode register + clock selection must be + set to GMII mode and + GMII_MODE should be set + to 1. in loopback mode, + REFCLK will drive the + entire mac core. 0 for + normal operation. */ +#define MAC_XIF_DISABLE_ECHO 0x0004 /* disables receive data + path during packet + xmission. clear to 0 + in any full duplex mode, + in any loopback mode, + or in half-duplex SERDES + or SLINK modes. set when + in half-duplex when + using external phy. */ +#define MAC_XIF_GMII_MODE 0x0008 /* MAC operates with GMII + clocks and datapath */ +#define MAC_XIF_MII_BUFFER_OUTPUT_EN 0x0010 /* MII_BUF_EN pin. enable + external tristate buffer + on the MII receive + bus. */ +#define MAC_XIF_LINK_LED 0x0020 /* LINKLED# active (low) */ +#define MAC_XIF_FDPLX_LED 0x0040 /* FDPLXLED# active (low) */ + +#define REG_MAC_IPG0 0x6040 /* inter-packet gap0 reg. + recommended: 0x00 */ +#define REG_MAC_IPG1 0x6044 /* inter-packet gap1 reg + recommended: 0x08 */ +#define REG_MAC_IPG2 0x6048 /* inter-packet gap2 reg + recommended: 0x04 */ +#define REG_MAC_SLOT_TIME 0x604C /* slot time reg + recommended: 0x40 */ +#define REG_MAC_FRAMESIZE_MIN 0x6050 /* min frame size reg + recommended: 0x40 */ + +/* FRAMESIZE_MAX holds both the max frame size as well as the max burst size. + * recommended value: 0x2000.05EE + */ +#define REG_MAC_FRAMESIZE_MAX 0x6054 /* max frame size reg */ +#define MAC_FRAMESIZE_MAX_BURST_MASK 0x3FFF0000 /* max burst size */ +#define MAC_FRAMESIZE_MAX_BURST_SHIFT 16 +#define MAC_FRAMESIZE_MAX_FRAME_MASK 0x00007FFF /* max frame size */ +#define MAC_FRAMESIZE_MAX_FRAME_SHIFT 0 +#define REG_MAC_PA_SIZE 0x6058 /* PA size reg. number of + preamble bytes that the + TX MAC will xmit at the + beginning of each frame + value should be 2 or + greater. recommended + value: 0x07 */ +#define REG_MAC_JAM_SIZE 0x605C /* jam size reg. duration + of jam in units of media + byte time. recommended + value: 0x04 */ +#define REG_MAC_ATTEMPT_LIMIT 0x6060 /* attempt limit reg. # + of attempts TX MAC will + make to xmit a frame + before it resets its + attempts counter. after + the limit has been + reached, TX MAC may or + may not drop the frame + dependent upon value + in TX_MAC_CFG. + recommended + value: 0x10 */ +#define REG_MAC_CTRL_TYPE 0x6064 /* MAC control type reg. + type field of a MAC + ctrl frame. recommended + value: 0x8808 */ + +/* mac address registers: 0 - 44, 0x6080 - 0x6130, 4 8-bit bytes. + * register contains comparison + * 0 16 MSB of primary MAC addr [47:32] of DA field + * 1 16 middle bits "" [31:16] of DA field + * 2 16 LSB "" [15:0] of DA field + * 3*x 16MSB of alt MAC addr 1-15 [47:32] of DA field + * 4*x 16 middle bits "" [31:16] + * 5*x 16 LSB "" [15:0] + * 42 16 MSB of MAC CTRL addr [47:32] of DA. + * 43 16 middle bits "" [31:16] + * 44 16 LSB "" [15:0] + * MAC CTRL addr must be the reserved multicast addr for MAC CTRL frames. + * if there is a match, MAC will set the bit for alternative address + * filter pass [15] + + * here is the map of registers given MAC address notation: a:b:c:d:e:f + * ab cd ef + * primary addr reg 2 reg 1 reg 0 + * alt addr 1 reg 5 reg 4 reg 3 + * alt addr x reg 5*x reg 4*x reg 3*x + * ctrl addr reg 44 reg 43 reg 42 + */ +#define REG_MAC_ADDR0 0x6080 /* MAC address 0 reg */ +#define REG_MAC_ADDRN(x) (REG_MAC_ADDR0 + (x)*4) +#define REG_MAC_ADDR_FILTER0 0x614C /* address filter 0 reg + [47:32] */ +#define REG_MAC_ADDR_FILTER1 0x6150 /* address filter 1 reg + [31:16] */ +#define REG_MAC_ADDR_FILTER2 0x6154 /* address filter 2 reg + [15:0] */ +#define REG_MAC_ADDR_FILTER2_1_MASK 0x6158 /* address filter 2 and 1 + mask reg. 8-bit reg + contains nibble mask for + reg 2 and 1. */ +#define REG_MAC_ADDR_FILTER0_MASK 0x615C /* address filter 0 mask + reg */ + +/* hash table registers: 0 - 15, 0x6160 - 0x619C, 4 8-bit bytes + * 16-bit registers contain bits of the hash table. + * reg x -> [16*(15 - x) + 15 : 16*(15 - x)]. + * e.g., 15 -> [15:0], 0 -> [255:240] + */ +#define REG_MAC_HASH_TABLE0 0x6160 /* hash table 0 reg */ +#define REG_MAC_HASH_TABLEN(x) (REG_MAC_HASH_TABLE0 + (x)*4) + +/* statistics registers. these registers generate an interrupt on + * overflow. recommended initialization: 0x0000. most are 16-bits except + * for PEAK_ATTEMPTS register which is 8 bits. + */ +#define REG_MAC_COLL_NORMAL 0x61A0 /* normal collision + counter. */ +#define REG_MAC_COLL_FIRST 0x61A4 /* first attempt + successful collision + counter */ +#define REG_MAC_COLL_EXCESS 0x61A8 /* excessive collision + counter */ +#define REG_MAC_COLL_LATE 0x61AC /* late collision counter */ +#define REG_MAC_TIMER_DEFER 0x61B0 /* defer timer. time base + is the media byte + clock/256 */ +#define REG_MAC_ATTEMPTS_PEAK 0x61B4 /* peak attempts reg */ +#define REG_MAC_RECV_FRAME 0x61B8 /* receive frame counter */ +#define REG_MAC_LEN_ERR 0x61BC /* length error counter */ +#define REG_MAC_ALIGN_ERR 0x61C0 /* alignment error counter */ +#define REG_MAC_FCS_ERR 0x61C4 /* FCS error counter */ +#define REG_MAC_RX_CODE_ERR 0x61C8 /* RX code violation + error counter */ + +/* misc registers */ +#define REG_MAC_RANDOM_SEED 0x61CC /* random number seed reg. + 10-bit register used as a + seed for the random number + generator for the CSMA/CD + backoff algorithm. only + programmed after power-on + reset and should be a + random value which has a + high likelihood of being + unique for each MAC + attached to a network + segment (e.g., 10 LSB of + MAC address) */ + +/* ASUN: there's a PAUSE_TIMER (ro) described, but it's not in the address + * map + */ + +/* 27-bit register has the current state for key state machines in the MAC */ +#define REG_MAC_STATE_MACHINE 0x61D0 /* (ro) state machine reg */ +#define MAC_SM_RLM_MASK 0x07800000 +#define MAC_SM_RLM_SHIFT 23 +#define MAC_SM_RX_FC_MASK 0x00700000 +#define MAC_SM_RX_FC_SHIFT 20 +#define MAC_SM_TLM_MASK 0x000F0000 +#define MAC_SM_TLM_SHIFT 16 +#define MAC_SM_ENCAP_SM_MASK 0x0000F000 +#define MAC_SM_ENCAP_SM_SHIFT 12 +#define MAC_SM_TX_REQ_MASK 0x00000C00 +#define MAC_SM_TX_REQ_SHIFT 10 +#define MAC_SM_TX_FC_MASK 0x000003C0 +#define MAC_SM_TX_FC_SHIFT 6 +#define MAC_SM_FIFO_WRITE_SEL_MASK 0x00000038 +#define MAC_SM_FIFO_WRITE_SEL_SHIFT 3 +#define MAC_SM_TX_FIFO_EMPTY_MASK 0x00000007 +#define MAC_SM_TX_FIFO_EMPTY_SHIFT 0 + +/** MIF registers. the MIF can be programmed in either bit-bang or + * frame mode. + **/ +#define REG_MIF_BIT_BANG_CLOCK 0x6200 /* MIF bit-bang clock. + 1 -> 0 will generate a + rising edge. 0 -> 1 will + generate a falling edge. */ +#define REG_MIF_BIT_BANG_DATA 0x6204 /* MIF bit-bang data. 1-bit + register generates data */ +#define REG_MIF_BIT_BANG_OUTPUT_EN 0x6208 /* MIF bit-bang output + enable. enable when + xmitting data from MIF to + transceiver. */ + +/* 32-bit register serves as an instruction register when the MIF is + * programmed in frame mode. load this register w/ a valid instruction + * (as per IEEE 802.3u MII spec). poll this register to check for instruction + * execution completion. during a read operation, this register will also + * contain the 16-bit data returned by the tranceiver. unless specified + * otherwise, fields are considered "don't care" when polling for + * completion. + */ +#define REG_MIF_FRAME 0x620C /* MIF frame/output reg */ +#define MIF_FRAME_START_MASK 0xC0000000 /* start of frame. + load w/ 01 when + issuing an instr */ +#define MIF_FRAME_ST 0x40000000 /* STart of frame */ +#define MIF_FRAME_OPCODE_MASK 0x30000000 /* opcode. 01 for a + write. 10 for a + read */ +#define MIF_FRAME_OP_READ 0x20000000 /* read OPcode */ +#define MIF_FRAME_OP_WRITE 0x10000000 /* write OPcode */ +#define MIF_FRAME_PHY_ADDR_MASK 0x0F800000 /* phy address. when + issuing an instr, + this field should be + loaded w/ the XCVR + addr */ +#define MIF_FRAME_PHY_ADDR_SHIFT 23 +#define MIF_FRAME_REG_ADDR_MASK 0x007C0000 /* register address. + when issuing an instr, + addr of register + to be read/written */ +#define MIF_FRAME_REG_ADDR_SHIFT 18 +#define MIF_FRAME_TURN_AROUND_MSB 0x00020000 /* turn around, MSB. + when issuing an instr, + set this bit to 1 */ +#define MIF_FRAME_TURN_AROUND_LSB 0x00010000 /* turn around, LSB. + when issuing an instr, + set this bit to 0. + when polling for + completion, 1 means + that instr execution + has been completed */ +#define MIF_FRAME_DATA_MASK 0x0000FFFF /* instruction payload + load with 16-bit data + to be written in + transceiver reg for a + write. doesn't matter + in a read. when + polling for + completion, field is + "don't care" for write + and 16-bit data + returned by the + transceiver for a + read (if valid bit + is set) */ +#define REG_MIF_CFG 0x6210 /* MIF config reg */ +#define MIF_CFG_PHY_SELECT 0x0001 /* 1 -> select MDIO_1 + 0 -> select MDIO_0 */ +#define MIF_CFG_POLL_EN 0x0002 /* enable polling + mechanism. if set, + BB_MODE should be 0 */ +#define MIF_CFG_BB_MODE 0x0004 /* 1 -> bit-bang mode + 0 -> frame mode */ +#define MIF_CFG_POLL_REG_MASK 0x00F8 /* register address to be + used by polling mode. + only meaningful if POLL_EN + is set to 1 */ +#define MIF_CFG_POLL_REG_SHIFT 3 +#define MIF_CFG_MDIO_0 0x0100 /* (ro) dual purpose. + when MDIO_0 is idle, + 1 -> tranceiver is + connected to MDIO_0. + when MIF is communicating + w/ MDIO_0 in bit-bang + mode, this bit indicates + the incoming bit stream + during a read op */ +#define MIF_CFG_MDIO_1 0x0200 /* (ro) dual purpose. + when MDIO_1 is idle, + 1 -> transceiver is + connected to MDIO_1. + when MIF is communicating + w/ MDIO_1 in bit-bang + mode, this bit indicates + the incoming bit stream + during a read op */ +#define MIF_CFG_POLL_PHY_MASK 0x7C00 /* tranceiver address to + be polled */ +#define MIF_CFG_POLL_PHY_SHIFT 10 + +/* 16-bit register used to determine which bits in the POLL_STATUS portion of + * the MIF_STATUS register will cause an interrupt. if a mask bit is 0, + * corresponding bit of the POLL_STATUS will generate a MIF interrupt when + * set. DEFAULT: 0xFFFF + */ +#define REG_MIF_MASK 0x6214 /* MIF mask reg */ + +/* 32-bit register used when in poll mode. auto-cleared after being read */ +#define REG_MIF_STATUS 0x6218 /* MIF status reg */ +#define MIF_STATUS_POLL_DATA_MASK 0xFFFF0000 /* poll data contains + the "latest image" + update of the XCVR + reg being read */ +#define MIF_STATUS_POLL_DATA_SHIFT 16 +#define MIF_STATUS_POLL_STATUS_MASK 0x0000FFFF /* poll status indicates + which bits in the + POLL_DATA field have + changed since the + MIF_STATUS reg was + last read */ +#define MIF_STATUS_POLL_STATUS_SHIFT 0 + +/* 7-bit register has current state for all state machines in the MIF */ +#define REG_MIF_STATE_MACHINE 0x621C /* MIF state machine reg */ +#define MIF_SM_CONTROL_MASK 0x07 /* control state machine + state */ +#define MIF_SM_EXECUTION_MASK 0x60 /* execution state machine + state */ + +/** PCS/Serialink. the following registers are equivalent to the standard + * MII management registers except that they're directly mapped in + * Cassini's register space. + **/ + +/* the auto-negotiation enable bit should be programmed the same at + * the link partner as in the local device to enable auto-negotiation to + * complete. when that bit is reprogrammed, auto-neg/manual config is + * restarted automatically. + * DEFAULT: 0x1040 + */ +#define REG_PCS_MII_CTRL 0x9000 /* PCS MII control reg */ +#define PCS_MII_CTRL_1000_SEL 0x0040 /* reads 1. ignored on + writes */ +#define PCS_MII_CTRL_COLLISION_TEST 0x0080 /* COL signal at the PCS + to MAC interface is + activated regardless + of activity */ +#define PCS_MII_CTRL_DUPLEX 0x0100 /* forced 0x0. PCS + behaviour same for + half and full dplx */ +#define PCS_MII_RESTART_AUTONEG 0x0200 /* self clearing. + restart auto- + negotiation */ +#define PCS_MII_ISOLATE 0x0400 /* read as 0. ignored + on writes */ +#define PCS_MII_POWER_DOWN 0x0800 /* read as 0. ignored + on writes */ +#define PCS_MII_AUTONEG_EN 0x1000 /* default 1. PCS goes + through automatic + link config before it + can be used. when 0, + link can be used + w/out any link config + phase */ +#define PCS_MII_10_100_SEL 0x2000 /* read as 0. ignored on + writes */ +#define PCS_MII_RESET 0x8000 /* reset PCS. self-clears + when done */ + +/* DEFAULT: 0x0108 */ +#define REG_PCS_MII_STATUS 0x9004 /* PCS MII status reg */ +#define PCS_MII_STATUS_EXTEND_CAP 0x0001 /* reads 0 */ +#define PCS_MII_STATUS_JABBER_DETECT 0x0002 /* reads 0 */ +#define PCS_MII_STATUS_LINK_STATUS 0x0004 /* 1 -> link up. + 0 -> link down. 0 is + latched so that 0 is + kept until read. read + 2x to determine if the + link has gone up again */ +#define PCS_MII_STATUS_AUTONEG_ABLE 0x0008 /* reads 1 (able to perform + auto-neg) */ +#define PCS_MII_STATUS_REMOTE_FAULT 0x0010 /* 1 -> remote fault detected + from received link code + word. only valid after + auto-neg completed */ +#define PCS_MII_STATUS_AUTONEG_COMP 0x0020 /* 1 -> auto-negotiation + completed + 0 -> auto-negotiation not + completed */ +#define PCS_MII_STATUS_EXTEND_STATUS 0x0100 /* reads as 1. used as an + indication that this is + a 1000 Base-X PHY. writes + to it are ignored */ + +/* used during auto-negotiation. + * DEFAULT: 0x00E0 + */ +#define REG_PCS_MII_ADVERT 0x9008 /* PCS MII advertisement + reg */ +#define PCS_MII_ADVERT_FD 0x0020 /* advertise full duplex + 1000 Base-X */ +#define PCS_MII_ADVERT_HD 0x0040 /* advertise half-duplex + 1000 Base-X */ +#define PCS_MII_ADVERT_SYM_PAUSE 0x0080 /* advertise PAUSE + symmetric capability */ +#define PCS_MII_ADVERT_ASYM_PAUSE 0x0100 /* advertises PAUSE + asymmetric capability */ +#define PCS_MII_ADVERT_RF_MASK 0x3000 /* remote fault. write bit13 + to optionally indicate to + link partner that chip is + going off-line. bit12 will + get set when signal + detect == FAIL and will + remain set until + successful negotiation */ +#define PCS_MII_ADVERT_ACK 0x4000 /* (ro) */ +#define PCS_MII_ADVERT_NEXT_PAGE 0x8000 /* (ro) forced 0x0 */ + +/* contents updated as a result of autonegotiation. layout and definitions + * identical to PCS_MII_ADVERT + */ +#define REG_PCS_MII_LPA 0x900C /* PCS MII link partner + ability reg */ +#define PCS_MII_LPA_FD PCS_MII_ADVERT_FD +#define PCS_MII_LPA_HD PCS_MII_ADVERT_HD +#define PCS_MII_LPA_SYM_PAUSE PCS_MII_ADVERT_SYM_PAUSE +#define PCS_MII_LPA_ASYM_PAUSE PCS_MII_ADVERT_ASYM_PAUSE +#define PCS_MII_LPA_RF_MASK PCS_MII_ADVERT_RF_MASK +#define PCS_MII_LPA_ACK PCS_MII_ADVERT_ACK +#define PCS_MII_LPA_NEXT_PAGE PCS_MII_ADVERT_NEXT_PAGE + +/* DEFAULT: 0x0 */ +#define REG_PCS_CFG 0x9010 /* PCS config reg */ +#define PCS_CFG_EN 0x01 /* enable PCS. must be + 0 when modifying + PCS_MII_ADVERT */ +#define PCS_CFG_SD_OVERRIDE 0x02 /* sets signal detect to + OK. bit is + non-resettable */ +#define PCS_CFG_SD_ACTIVE_LOW 0x04 /* changes interpretation + of optical signal to make + signal detect okay when + signal is low */ +#define PCS_CFG_JITTER_STUDY_MASK 0x18 /* used to make jitter + measurements. a single + code group is xmitted + regularly. + 0x0 = normal operation + 0x1 = high freq test + pattern, D21.5 + 0x2 = low freq test + pattern, K28.7 + 0x3 = reserved */ +#define PCS_CFG_10MS_TIMER_OVERRIDE 0x20 /* shortens 10-20ms auto- + negotiation timer to + a few cycles for test + purposes */ + +/* used for diagnostic purposes. bits 20-22 autoclear on read */ +#define REG_PCS_STATE_MACHINE 0x9014 /* (ro) PCS state machine + and diagnostic reg */ +#define PCS_SM_TX_STATE_MASK 0x0000000F /* 0 and 1 indicate + xmission of idle. + otherwise, xmission of + a packet */ +#define PCS_SM_RX_STATE_MASK 0x000000F0 /* 0 indicates reception + of idle. otherwise, + reception of packet */ +#define PCS_SM_WORD_SYNC_STATE_MASK 0x00000700 /* 0 indicates loss of + sync */ +#define PCS_SM_SEQ_DETECT_STATE_MASK 0x00001800 /* cycling through 0-3 + indicates reception of + Config codes. cycling + through 0-1 indicates + reception of idles */ +#define PCS_SM_LINK_STATE_MASK 0x0001E000 +#define SM_LINK_STATE_UP 0x00016000 /* link state is up */ + +#define PCS_SM_LOSS_LINK_C 0x00100000 /* loss of link due to + recept of Config + codes */ +#define PCS_SM_LOSS_LINK_SYNC 0x00200000 /* loss of link due to + loss of sync */ +#define PCS_SM_LOSS_SIGNAL_DETECT 0x00400000 /* signal detect goes + from OK to FAIL. bit29 + will also be set if + this is set */ +#define PCS_SM_NO_LINK_BREAKLINK 0x01000000 /* link not up due to + receipt of breaklink + C codes from partner. + C codes w/ 0 content + received triggering + start/restart of + autonegotiation. + should be sent for + no longer than 20ms */ +#define PCS_SM_NO_LINK_SERDES 0x02000000 /* serdes being + initialized. see serdes + state reg */ +#define PCS_SM_NO_LINK_C 0x04000000 /* C codes not stable or + not received */ +#define PCS_SM_NO_LINK_SYNC 0x08000000 /* word sync not + achieved */ +#define PCS_SM_NO_LINK_WAIT_C 0x10000000 /* waiting for C codes + w/ ack bit set */ +#define PCS_SM_NO_LINK_NO_IDLE 0x20000000 /* link partner continues + to send C codes + instead of idle + symbols or pkt data */ + +/* this register indicates interrupt changes in specific PCS MII status bits. + * PCS_INT may be masked at the ISR level. only a single bit is implemented + * for link status change. + */ +#define REG_PCS_INTR_STATUS 0x9018 /* PCS interrupt status */ +#define PCS_INTR_STATUS_LINK_CHANGE 0x04 /* link status has changed + since last read */ + +/* control which network interface is used. no more than one bit should + * be set. + * DEFAULT: none + */ +#define REG_PCS_DATAPATH_MODE 0x9050 /* datapath mode reg */ +#define PCS_DATAPATH_MODE_MII 0x00 /* PCS is not used and + MII/GMII is selected. + selection between MII and + GMII is controlled by + XIF_CFG */ +#define PCS_DATAPATH_MODE_SERDES 0x02 /* PCS is used via the + 10-bit interface */ + +/* input to serdes chip or serialink block */ +#define REG_PCS_SERDES_CTRL 0x9054 /* serdes control reg */ +#define PCS_SERDES_CTRL_LOOPBACK 0x01 /* enable loopback on + serdes interface */ +#define PCS_SERDES_CTRL_SYNCD_EN 0x02 /* enable sync carrier + detection. should be + 0x0 for normal + operation */ +#define PCS_SERDES_CTRL_LOCKREF 0x04 /* frequency-lock RBC[0:1] + to REFCLK when set. + when clear, receiver + clock locks to incoming + serial data */ + +/* multiplex test outputs into the PROM address (PA_3 through PA_0) pins. + * should be 0x0 for normal operations. + * 0b000 normal operation, PROM address[3:0] selected + * 0b001 rxdma req, rxdma ack, rxdma ready, rxdma read + * 0b010 rxmac req, rx ack, rx tag, rx clk shared + * 0b011 txmac req, tx ack, tx tag, tx retry req + * 0b100 tx tp3, tx tp2, tx tp1, tx tp0 + * 0b101 R period RX, R period TX, R period HP, R period BIM + * DEFAULT: 0x0 + */ +#define REG_PCS_SHARED_OUTPUT_SEL 0x9058 /* shared output select */ +#define PCS_SOS_PROM_ADDR_MASK 0x0007 + +/* used for diagnostics. this register indicates progress of the SERDES + * boot up. + * 0b00 undergoing reset + * 0b01 waiting 500us while lockrefn is asserted + * 0b10 waiting for comma detect + * 0b11 receive data is synchronized + * DEFAULT: 0x0 + */ +#define REG_PCS_SERDES_STATE 0x905C /* (ro) serdes state */ +#define PCS_SERDES_STATE_MASK 0x03 + +/* used for diagnostics. indicates number of packets transmitted or received. + * counters rollover w/out generating an interrupt. + * DEFAULT: 0x0 + */ +#define REG_PCS_PACKET_COUNT 0x9060 /* (ro) PCS packet counter */ +#define PCS_PACKET_COUNT_TX 0x000007FF /* pkts xmitted by PCS */ +#define PCS_PACKET_COUNT_RX 0x07FF0000 /* pkts recvd by PCS + whether they + encountered an error + or not */ + +/** LocalBus Devices. the following provides run-time access to the + * Cassini's PROM + ***/ +#define REG_EXPANSION_ROM_RUN_START 0x100000 /* expansion rom run time + access */ +#define REG_EXPANSION_ROM_RUN_END 0x17FFFF + +#define REG_SECOND_LOCALBUS_START 0x180000 /* secondary local bus + device */ +#define REG_SECOND_LOCALBUS_END 0x1FFFFF + +/* entropy device */ +#define REG_ENTROPY_START REG_SECOND_LOCALBUS_START +#define REG_ENTROPY_DATA (REG_ENTROPY_START + 0x00) +#define REG_ENTROPY_STATUS (REG_ENTROPY_START + 0x04) +#define ENTROPY_STATUS_DRDY 0x01 +#define ENTROPY_STATUS_BUSY 0x02 +#define ENTROPY_STATUS_CIPHER 0x04 +#define ENTROPY_STATUS_BYPASS_MASK 0x18 +#define REG_ENTROPY_MODE (REG_ENTROPY_START + 0x05) +#define ENTROPY_MODE_KEY_MASK 0x07 +#define ENTROPY_MODE_ENCRYPT 0x40 +#define REG_ENTROPY_RAND_REG (REG_ENTROPY_START + 0x06) +#define REG_ENTROPY_RESET (REG_ENTROPY_START + 0x07) +#define ENTROPY_RESET_DES_IO 0x01 +#define ENTROPY_RESET_STC_MODE 0x02 +#define ENTROPY_RESET_KEY_CACHE 0x04 +#define ENTROPY_RESET_IV 0x08 +#define REG_ENTROPY_IV (REG_ENTROPY_START + 0x08) +#define REG_ENTROPY_KEY0 (REG_ENTROPY_START + 0x10) +#define REG_ENTROPY_KEYN(x) (REG_ENTROPY_KEY0 + 4*(x)) + +/* phys of interest w/ their special mii registers */ +#define PHY_LUCENT_B0 0x00437421 +#define LUCENT_MII_REG 0x1F + +#define PHY_NS_DP83065 0x20005c78 +#define DP83065_MII_MEM 0x16 +#define DP83065_MII_REGD 0x1D +#define DP83065_MII_REGE 0x1E + +#define PHY_BROADCOM_5411 0x00206071 +#define PHY_BROADCOM_B0 0x00206050 +#define BROADCOM_MII_REG4 0x14 +#define BROADCOM_MII_REG5 0x15 +#define BROADCOM_MII_REG7 0x17 +#define BROADCOM_MII_REG8 0x18 + +#define CAS_MII_ANNPTR 0x07 +#define CAS_MII_ANNPRR 0x08 +#define CAS_MII_1000_CTRL 0x09 +#define CAS_MII_1000_STATUS 0x0A +#define CAS_MII_1000_EXTEND 0x0F + +#define CAS_BMSR_1000_EXTEND 0x0100 /* supports 1000Base-T extended status */ +/* + * if autoneg is disabled, here's the table: + * BMCR_SPEED100 = 100Mbps + * BMCR_SPEED1000 = 1000Mbps + * ~(BMCR_SPEED100 | BMCR_SPEED1000) = 10Mbps + */ +#define CAS_BMCR_SPEED1000 0x0040 /* Select 1000Mbps */ + +#define CAS_ADVERTISE_1000HALF 0x0100 +#define CAS_ADVERTISE_1000FULL 0x0200 +#define CAS_ADVERTISE_PAUSE 0x0400 +#define CAS_ADVERTISE_ASYM_PAUSE 0x0800 + +/* regular lpa register */ +#define CAS_LPA_PAUSE CAS_ADVERTISE_PAUSE +#define CAS_LPA_ASYM_PAUSE CAS_ADVERTISE_ASYM_PAUSE + +/* 1000_STATUS register */ +#define CAS_LPA_1000HALF 0x0400 +#define CAS_LPA_1000FULL 0x0800 + +#define CAS_EXTEND_1000XFULL 0x8000 +#define CAS_EXTEND_1000XHALF 0x4000 +#define CAS_EXTEND_1000TFULL 0x2000 +#define CAS_EXTEND_1000THALF 0x1000 + +/* cassini header parser firmware */ +typedef struct cas_hp_inst { + const char *note; + + u16 mask, val; + + u8 op; + u8 soff, snext; /* if match succeeds, new offset and match */ + u8 foff, fnext; /* if match fails, new offset and match */ + /* output info */ + u8 outop; /* output opcode */ + + u16 outarg; /* output argument */ + u8 outenab; /* output enable: 0 = not, 1 = if match + 2 = if !match, 3 = always */ + u8 outshift; /* barrel shift right, 4 bits */ + u16 outmask; +} cas_hp_inst_t; + +/* comparison */ +#define OP_EQ 0 /* packet == value */ +#define OP_LT 1 /* packet < value */ +#define OP_GT 2 /* packet > value */ +#define OP_NP 3 /* new packet */ + +/* output opcodes */ +#define CL_REG 0 +#define LD_FID 1 +#define LD_SEQ 2 +#define LD_CTL 3 +#define LD_SAP 4 +#define LD_R1 5 +#define LD_L3 6 +#define LD_SUM 7 +#define LD_HDR 8 +#define IM_FID 9 +#define IM_SEQ 10 +#define IM_SAP 11 +#define IM_R1 12 +#define IM_CTL 13 +#define LD_LEN 14 +#define ST_FLG 15 + +/* match setp #s for IP4TCP4 */ +#define S1_PCKT 0 +#define S1_VLAN 1 +#define S1_CFI 2 +#define S1_8023 3 +#define S1_LLC 4 +#define S1_LLCc 5 +#define S1_IPV4 6 +#define S1_IPV4c 7 +#define S1_IPV4F 8 +#define S1_TCP44 9 +#define S1_IPV6 10 +#define S1_IPV6L 11 +#define S1_IPV6c 12 +#define S1_TCP64 13 +#define S1_TCPSQ 14 +#define S1_TCPFG 15 +#define S1_TCPHL 16 +#define S1_TCPHc 17 +#define S1_CLNP 18 +#define S1_CLNP2 19 +#define S1_DROP 20 +#define S2_HTTP 21 +#define S1_ESP4 22 +#define S1_AH4 23 +#define S1_ESP6 24 +#define S1_AH6 25 + +#define CAS_PROG_IP46TCP4_PREAMBLE \ +{ "packet arrival?", 0xffff, 0x0000, OP_NP, 6, S1_VLAN, 0, S1_PCKT, \ + CL_REG, 0x3ff, 1, 0x0, 0x0000}, \ +{ "VLAN?", 0xffff, 0x8100, OP_EQ, 1, S1_CFI, 0, S1_8023, \ + IM_CTL, 0x00a, 3, 0x0, 0xffff}, \ +{ "CFI?", 0x1000, 0x1000, OP_EQ, 0, S1_DROP, 1, S1_8023, \ + CL_REG, 0x000, 0, 0x0, 0x0000}, \ +{ "8023?", 0xffff, 0x0600, OP_LT, 1, S1_LLC, 0, S1_IPV4, \ + CL_REG, 0x000, 0, 0x0, 0x0000}, \ +{ "LLC?", 0xffff, 0xaaaa, OP_EQ, 1, S1_LLCc, 0, S1_CLNP, \ + CL_REG, 0x000, 0, 0x0, 0x0000}, \ +{ "LLCc?", 0xff00, 0x0300, OP_EQ, 2, S1_IPV4, 0, S1_CLNP, \ + CL_REG, 0x000, 0, 0x0, 0x0000}, \ +{ "IPV4?", 0xffff, 0x0800, OP_EQ, 1, S1_IPV4c, 0, S1_IPV6, \ + LD_SAP, 0x100, 3, 0x0, 0xffff}, \ +{ "IPV4 cont?", 0xff00, 0x4500, OP_EQ, 3, S1_IPV4F, 0, S1_CLNP, \ + LD_SUM, 0x00a, 1, 0x0, 0x0000}, \ +{ "IPV4 frag?", 0x3fff, 0x0000, OP_EQ, 1, S1_TCP44, 0, S1_CLNP, \ + LD_LEN, 0x03e, 1, 0x0, 0xffff}, \ +{ "TCP44?", 0x00ff, 0x0006, OP_EQ, 7, S1_TCPSQ, 0, S1_CLNP, \ + LD_FID, 0x182, 1, 0x0, 0xffff}, /* FID IP4&TCP src+dst */ \ +{ "IPV6?", 0xffff, 0x86dd, OP_EQ, 1, S1_IPV6L, 0, S1_CLNP, \ + LD_SUM, 0x015, 1, 0x0, 0x0000}, \ +{ "IPV6 len", 0xf000, 0x6000, OP_EQ, 0, S1_IPV6c, 0, S1_CLNP, \ + IM_R1, 0x128, 1, 0x0, 0xffff}, \ +{ "IPV6 cont?", 0x0000, 0x0000, OP_EQ, 3, S1_TCP64, 0, S1_CLNP, \ + LD_FID, 0x484, 1, 0x0, 0xffff}, /* FID IP6&TCP src+dst */ \ +{ "TCP64?", 0xff00, 0x0600, OP_EQ, 18, S1_TCPSQ, 0, S1_CLNP, \ + LD_LEN, 0x03f, 1, 0x0, 0xffff} + +#ifdef USE_HP_IP46TCP4 +static cas_hp_inst_t cas_prog_ip46tcp4tab[] = { + CAS_PROG_IP46TCP4_PREAMBLE, + { "TCP seq", /* DADDR should point to dest port */ + 0x0000, 0x0000, OP_EQ, 0, S1_TCPFG, 4, S1_TCPFG, LD_SEQ, + 0x081, 3, 0x0, 0xffff}, /* Load TCP seq # */ + { "TCP control flags", 0x0000, 0x0000, OP_EQ, 0, S1_TCPHL, 0, + S1_TCPHL, ST_FLG, 0x045, 3, 0x0, 0x002f}, /* Load TCP flags */ + { "TCP length", 0x0000, 0x0000, OP_EQ, 0, S1_TCPHc, 0, + S1_TCPHc, LD_R1, 0x205, 3, 0xB, 0xf000}, + { "TCP length cont", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, + S1_PCKT, LD_HDR, 0x0ff, 3, 0x0, 0xffff}, + { "Cleanup", 0x0000, 0x0000, OP_EQ, 0, S1_CLNP2, 0, S1_CLNP2, + IM_CTL, 0x001, 3, 0x0, 0x0001}, + { "Cleanup 2", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + IM_CTL, 0x000, 0, 0x0, 0x0000}, + { "Drop packet", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + IM_CTL, 0x080, 3, 0x0, 0xffff}, + { NULL }, +}; +#ifdef HP_IP46TCP4_DEFAULT +#define CAS_HP_FIRMWARE cas_prog_ip46tcp4tab +#endif +#endif + +/* + * Alternate table load which excludes HTTP server traffic from reassembly. + * It is substantially similar to the basic table, with one extra state + * and a few extra compares. */ +#ifdef USE_HP_IP46TCP4NOHTTP +static cas_hp_inst_t cas_prog_ip46tcp4nohttptab[] = { + CAS_PROG_IP46TCP4_PREAMBLE, + { "TCP seq", /* DADDR should point to dest port */ + 0xFFFF, 0x0080, OP_EQ, 0, S2_HTTP, 0, S1_TCPFG, LD_SEQ, + 0x081, 3, 0x0, 0xffff} , /* Load TCP seq # */ + { "TCP control flags", 0xFFFF, 0x8080, OP_EQ, 0, S2_HTTP, 0, + S1_TCPHL, ST_FLG, 0x145, 2, 0x0, 0x002f, }, /* Load TCP flags */ + { "TCP length", 0x0000, 0x0000, OP_EQ, 0, S1_TCPHc, 0, S1_TCPHc, + LD_R1, 0x205, 3, 0xB, 0xf000}, + { "TCP length cont", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + LD_HDR, 0x0ff, 3, 0x0, 0xffff}, + { "Cleanup", 0x0000, 0x0000, OP_EQ, 0, S1_CLNP2, 0, S1_CLNP2, + IM_CTL, 0x001, 3, 0x0, 0x0001}, + { "Cleanup 2", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + CL_REG, 0x002, 3, 0x0, 0x0000}, + { "Drop packet", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + IM_CTL, 0x080, 3, 0x0, 0xffff}, + { "No HTTP", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + IM_CTL, 0x044, 3, 0x0, 0xffff}, + { NULL }, +}; +#ifdef HP_IP46TCP4NOHTTP_DEFAULT +#define CAS_HP_FIRMWARE cas_prog_ip46tcp4nohttptab +#endif +#endif + +/* match step #s for IP4FRAG */ +#define S3_IPV6c 11 +#define S3_TCP64 12 +#define S3_TCPSQ 13 +#define S3_TCPFG 14 +#define S3_TCPHL 15 +#define S3_TCPHc 16 +#define S3_FRAG 17 +#define S3_FOFF 18 +#define S3_CLNP 19 + +#ifdef USE_HP_IP4FRAG +static cas_hp_inst_t cas_prog_ip4fragtab[] = { + { "packet arrival?", 0xffff, 0x0000, OP_NP, 6, S1_VLAN, 0, S1_PCKT, + CL_REG, 0x3ff, 1, 0x0, 0x0000}, + { "VLAN?", 0xffff, 0x8100, OP_EQ, 1, S1_CFI, 0, S1_8023, + IM_CTL, 0x00a, 3, 0x0, 0xffff}, + { "CFI?", 0x1000, 0x1000, OP_EQ, 0, S3_CLNP, 1, S1_8023, + CL_REG, 0x000, 0, 0x0, 0x0000}, + { "8023?", 0xffff, 0x0600, OP_LT, 1, S1_LLC, 0, S1_IPV4, + CL_REG, 0x000, 0, 0x0, 0x0000}, + { "LLC?", 0xffff, 0xaaaa, OP_EQ, 1, S1_LLCc, 0, S3_CLNP, + CL_REG, 0x000, 0, 0x0, 0x0000}, + { "LLCc?",0xff00, 0x0300, OP_EQ, 2, S1_IPV4, 0, S3_CLNP, + CL_REG, 0x000, 0, 0x0, 0x0000}, + { "IPV4?", 0xffff, 0x0800, OP_EQ, 1, S1_IPV4c, 0, S1_IPV6, + LD_SAP, 0x100, 3, 0x0, 0xffff}, + { "IPV4 cont?", 0xff00, 0x4500, OP_EQ, 3, S1_IPV4F, 0, S3_CLNP, + LD_SUM, 0x00a, 1, 0x0, 0x0000}, + { "IPV4 frag?", 0x3fff, 0x0000, OP_EQ, 1, S1_TCP44, 0, S3_FRAG, + LD_LEN, 0x03e, 3, 0x0, 0xffff}, + { "TCP44?", 0x00ff, 0x0006, OP_EQ, 7, S3_TCPSQ, 0, S3_CLNP, + LD_FID, 0x182, 3, 0x0, 0xffff}, /* FID IP4&TCP src+dst */ + { "IPV6?", 0xffff, 0x86dd, OP_EQ, 1, S3_IPV6c, 0, S3_CLNP, + LD_SUM, 0x015, 1, 0x0, 0x0000}, + { "IPV6 cont?", 0xf000, 0x6000, OP_EQ, 3, S3_TCP64, 0, S3_CLNP, + LD_FID, 0x484, 1, 0x0, 0xffff}, /* FID IP6&TCP src+dst */ + { "TCP64?", 0xff00, 0x0600, OP_EQ, 18, S3_TCPSQ, 0, S3_CLNP, + LD_LEN, 0x03f, 1, 0x0, 0xffff}, + { "TCP seq", /* DADDR should point to dest port */ + 0x0000, 0x0000, OP_EQ, 0, S3_TCPFG, 4, S3_TCPFG, LD_SEQ, + 0x081, 3, 0x0, 0xffff}, /* Load TCP seq # */ + { "TCP control flags", 0x0000, 0x0000, OP_EQ, 0, S3_TCPHL, 0, + S3_TCPHL, ST_FLG, 0x045, 3, 0x0, 0x002f}, /* Load TCP flags */ + { "TCP length", 0x0000, 0x0000, OP_EQ, 0, S3_TCPHc, 0, S3_TCPHc, + LD_R1, 0x205, 3, 0xB, 0xf000}, + { "TCP length cont", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + LD_HDR, 0x0ff, 3, 0x0, 0xffff}, + { "IP4 Fragment", 0x0000, 0x0000, OP_EQ, 0, S3_FOFF, 0, S3_FOFF, + LD_FID, 0x103, 3, 0x0, 0xffff}, /* FID IP4 src+dst */ + { "IP4 frag offset", 0x0000, 0x0000, OP_EQ, 0, S3_FOFF, 0, S3_FOFF, + LD_SEQ, 0x040, 1, 0xD, 0xfff8}, + { "Cleanup", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + IM_CTL, 0x001, 3, 0x0, 0x0001}, + { NULL }, +}; +#ifdef HP_IP4FRAG_DEFAULT +#define CAS_HP_FIRMWARE cas_prog_ip4fragtab +#endif +#endif + +/* + * Alternate table which does batching without reassembly + */ +#ifdef USE_HP_IP46TCP4BATCH +static cas_hp_inst_t cas_prog_ip46tcp4batchtab[] = { + CAS_PROG_IP46TCP4_PREAMBLE, + { "TCP seq", /* DADDR should point to dest port */ + 0x0000, 0x0000, OP_EQ, 0, S1_TCPFG, 0, S1_TCPFG, LD_SEQ, + 0x081, 3, 0x0, 0xffff}, /* Load TCP seq # */ + { "TCP control flags", 0x0000, 0x0000, OP_EQ, 0, S1_TCPHL, 0, + S1_TCPHL, ST_FLG, 0x000, 3, 0x0, 0x0000}, /* Load TCP flags */ + { "TCP length", 0x0000, 0x0000, OP_EQ, 0, S1_TCPHc, 0, + S1_TCPHc, LD_R1, 0x205, 3, 0xB, 0xf000}, + { "TCP length cont", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, + S1_PCKT, IM_CTL, 0x040, 3, 0x0, 0xffff}, /* set batch bit */ + { "Cleanup", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + IM_CTL, 0x001, 3, 0x0, 0x0001}, + { "Drop packet", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, + S1_PCKT, IM_CTL, 0x080, 3, 0x0, 0xffff}, + { NULL }, +}; +#ifdef HP_IP46TCP4BATCH_DEFAULT +#define CAS_HP_FIRMWARE cas_prog_ip46tcp4batchtab +#endif +#endif + +/* Workaround for Cassini rev2 descriptor corruption problem. + * Does batching without reassembly, and sets the SAP to a known + * data pattern for all packets. + */ +#ifdef USE_HP_WORKAROUND +static cas_hp_inst_t cas_prog_workaroundtab[] = { + { "packet arrival?", 0xffff, 0x0000, OP_NP, 6, S1_VLAN, 0, + S1_PCKT, CL_REG, 0x3ff, 1, 0x0, 0x0000} , + { "VLAN?", 0xffff, 0x8100, OP_EQ, 1, S1_CFI, 0, S1_8023, + IM_CTL, 0x04a, 3, 0x0, 0xffff}, + { "CFI?", 0x1000, 0x1000, OP_EQ, 0, S1_CLNP, 1, S1_8023, + CL_REG, 0x000, 0, 0x0, 0x0000}, + { "8023?", 0xffff, 0x0600, OP_LT, 1, S1_LLC, 0, S1_IPV4, + CL_REG, 0x000, 0, 0x0, 0x0000}, + { "LLC?", 0xffff, 0xaaaa, OP_EQ, 1, S1_LLCc, 0, S1_CLNP, + CL_REG, 0x000, 0, 0x0, 0x0000}, + { "LLCc?", 0xff00, 0x0300, OP_EQ, 2, S1_IPV4, 0, S1_CLNP, + CL_REG, 0x000, 0, 0x0, 0x0000}, + { "IPV4?", 0xffff, 0x0800, OP_EQ, 1, S1_IPV4c, 0, S1_IPV6, + IM_SAP, 0x6AE, 3, 0x0, 0xffff}, + { "IPV4 cont?", 0xff00, 0x4500, OP_EQ, 3, S1_IPV4F, 0, S1_CLNP, + LD_SUM, 0x00a, 1, 0x0, 0x0000}, + { "IPV4 frag?", 0x3fff, 0x0000, OP_EQ, 1, S1_TCP44, 0, S1_CLNP, + LD_LEN, 0x03e, 1, 0x0, 0xffff}, + { "TCP44?", 0x00ff, 0x0006, OP_EQ, 7, S1_TCPSQ, 0, S1_CLNP, + LD_FID, 0x182, 3, 0x0, 0xffff}, /* FID IP4&TCP src+dst */ + { "IPV6?", 0xffff, 0x86dd, OP_EQ, 1, S1_IPV6L, 0, S1_CLNP, + LD_SUM, 0x015, 1, 0x0, 0x0000}, + { "IPV6 len", 0xf000, 0x6000, OP_EQ, 0, S1_IPV6c, 0, S1_CLNP, + IM_R1, 0x128, 1, 0x0, 0xffff}, + { "IPV6 cont?", 0x0000, 0x0000, OP_EQ, 3, S1_TCP64, 0, S1_CLNP, + LD_FID, 0x484, 1, 0x0, 0xffff}, /* FID IP6&TCP src+dst */ + { "TCP64?", 0xff00, 0x0600, OP_EQ, 18, S1_TCPSQ, 0, S1_CLNP, + LD_LEN, 0x03f, 1, 0x0, 0xffff}, + { "TCP seq", /* DADDR should point to dest port */ + 0x0000, 0x0000, OP_EQ, 0, S1_TCPFG, 4, S1_TCPFG, LD_SEQ, + 0x081, 3, 0x0, 0xffff}, /* Load TCP seq # */ + { "TCP control flags", 0x0000, 0x0000, OP_EQ, 0, S1_TCPHL, 0, + S1_TCPHL, ST_FLG, 0x045, 3, 0x0, 0x002f}, /* Load TCP flags */ + { "TCP length", 0x0000, 0x0000, OP_EQ, 0, S1_TCPHc, 0, S1_TCPHc, + LD_R1, 0x205, 3, 0xB, 0xf000}, + { "TCP length cont", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, + S1_PCKT, LD_HDR, 0x0ff, 3, 0x0, 0xffff}, + { "Cleanup", 0x0000, 0x0000, OP_EQ, 0, S1_CLNP2, 0, S1_CLNP2, + IM_SAP, 0x6AE, 3, 0x0, 0xffff} , + { "Cleanup 2", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + IM_CTL, 0x001, 3, 0x0, 0x0001}, + { NULL }, +}; +#ifdef HP_WORKAROUND_DEFAULT +#define CAS_HP_FIRMWARE cas_prog_workaroundtab +#endif +#endif + +#ifdef USE_HP_ENCRYPT +static cas_hp_inst_t cas_prog_encryptiontab[] = { + { "packet arrival?", 0xffff, 0x0000, OP_NP, 6, S1_VLAN, 0, + S1_PCKT, CL_REG, 0x3ff, 1, 0x0, 0x0000}, + { "VLAN?", 0xffff, 0x8100, OP_EQ, 1, S1_CFI, 0, S1_8023, + IM_CTL, 0x00a, 3, 0x0, 0xffff}, +#if 0 +//"CFI?", /* 02 FIND CFI and If FIND go to S1_DROP */ +//0x1000, 0x1000, OP_EQ, 0, S1_DROP, 1, S1_8023, CL_REG, 0x000, 0, 0x0, 0x00 + 00, +#endif + { "CFI?", /* FIND CFI and If FIND go to CleanUP1 (ignore and send to host) */ + 0x1000, 0x1000, OP_EQ, 0, S1_CLNP, 1, S1_8023, + CL_REG, 0x000, 0, 0x0, 0x0000}, + { "8023?", 0xffff, 0x0600, OP_LT, 1, S1_LLC, 0, S1_IPV4, + CL_REG, 0x000, 0, 0x0, 0x0000}, + { "LLC?", 0xffff, 0xaaaa, OP_EQ, 1, S1_LLCc, 0, S1_CLNP, + CL_REG, 0x000, 0, 0x0, 0x0000}, + { "LLCc?", 0xff00, 0x0300, OP_EQ, 2, S1_IPV4, 0, S1_CLNP, + CL_REG, 0x000, 0, 0x0, 0x0000}, + { "IPV4?", 0xffff, 0x0800, OP_EQ, 1, S1_IPV4c, 0, S1_IPV6, + LD_SAP, 0x100, 3, 0x0, 0xffff}, + { "IPV4 cont?", 0xff00, 0x4500, OP_EQ, 3, S1_IPV4F, 0, S1_CLNP, + LD_SUM, 0x00a, 1, 0x0, 0x0000}, + { "IPV4 frag?", 0x3fff, 0x0000, OP_EQ, 1, S1_TCP44, 0, S1_CLNP, + LD_LEN, 0x03e, 1, 0x0, 0xffff}, + { "TCP44?", 0x00ff, 0x0006, OP_EQ, 7, S1_TCPSQ, 0, S1_ESP4, + LD_FID, 0x182, 1, 0x0, 0xffff}, /* FID IP4&TCP src+dst */ + { "IPV6?", 0xffff, 0x86dd, OP_EQ, 1, S1_IPV6L, 0, S1_CLNP, + LD_SUM, 0x015, 1, 0x0, 0x0000}, + { "IPV6 len", 0xf000, 0x6000, OP_EQ, 0, S1_IPV6c, 0, S1_CLNP, + IM_R1, 0x128, 1, 0x0, 0xffff}, + { "IPV6 cont?", 0x0000, 0x0000, OP_EQ, 3, S1_TCP64, 0, S1_CLNP, + LD_FID, 0x484, 1, 0x0, 0xffff}, /* FID IP6&TCP src+dst */ + { "TCP64?", +#if 0 +//@@@0xff00, 0x0600, OP_EQ, 18, S1_TCPSQ, 0, S1_ESP6, LD_LEN, 0x03f, 1, 0x0, 0xffff, +#endif + 0xff00, 0x0600, OP_EQ, 12, S1_TCPSQ, 0, S1_ESP6, LD_LEN, + 0x03f, 1, 0x0, 0xffff}, + { "TCP seq", /* 14:DADDR should point to dest port */ + 0xFFFF, 0x0080, OP_EQ, 0, S2_HTTP, 0, S1_TCPFG, LD_SEQ, + 0x081, 3, 0x0, 0xffff}, /* Load TCP seq # */ + { "TCP control flags", 0xFFFF, 0x8080, OP_EQ, 0, S2_HTTP, 0, + S1_TCPHL, ST_FLG, 0x145, 2, 0x0, 0x002f}, /* Load TCP flags */ + { "TCP length", 0x0000, 0x0000, OP_EQ, 0, S1_TCPHc, 0, S1_TCPHc, + LD_R1, 0x205, 3, 0xB, 0xf000} , + { "TCP length cont", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, + S1_PCKT, LD_HDR, 0x0ff, 3, 0x0, 0xffff}, + { "Cleanup", 0x0000, 0x0000, OP_EQ, 0, S1_CLNP2, 0, S1_CLNP2, + IM_CTL, 0x001, 3, 0x0, 0x0001}, + { "Cleanup 2", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + CL_REG, 0x002, 3, 0x0, 0x0000}, + { "Drop packet", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + IM_CTL, 0x080, 3, 0x0, 0xffff}, + { "No HTTP", 0x0000, 0x0000, OP_EQ, 0, S1_PCKT, 0, S1_PCKT, + IM_CTL, 0x044, 3, 0x0, 0xffff}, + { "IPV4 ESP encrypted?", /* S1_ESP4 */ + 0x00ff, 0x0032, OP_EQ, 0, S1_CLNP2, 0, S1_AH4, IM_CTL, + 0x021, 1, 0x0, 0xffff}, + { "IPV4 AH encrypted?", /* S1_AH4 */ + 0x00ff, 0x0033, OP_EQ, 0, S1_CLNP2, 0, S1_CLNP, IM_CTL, + 0x021, 1, 0x0, 0xffff}, + { "IPV6 ESP encrypted?", /* S1_ESP6 */ +#if 0 +//@@@0x00ff, 0x0032, OP_EQ, 0, S1_CLNP2, 0, S1_AH6, IM_CTL, 0x021, 1, 0x0, 0xffff, +#endif + 0xff00, 0x3200, OP_EQ, 0, S1_CLNP2, 0, S1_AH6, IM_CTL, + 0x021, 1, 0x0, 0xffff}, + { "IPV6 AH encrypted?", /* S1_AH6 */ +#if 0 +//@@@0x00ff, 0x0033, OP_EQ, 0, S1_CLNP2, 0, S1_CLNP, IM_CTL, 0x021, 1, 0x0, 0xffff, +#endif + 0xff00, 0x3300, OP_EQ, 0, S1_CLNP2, 0, S1_CLNP, IM_CTL, + 0x021, 1, 0x0, 0xffff}, + { NULL }, +}; +#ifdef HP_ENCRYPT_DEFAULT +#define CAS_HP_FIRMWARE cas_prog_encryptiontab +#endif +#endif + +static cas_hp_inst_t cas_prog_null[] = { {NULL} }; +#ifdef HP_NULL_DEFAULT +#define CAS_HP_FIRMWARE cas_prog_null +#endif + +/* firmware patch for NS_DP83065 */ +typedef struct cas_saturn_patch { + u16 addr; + u16 val; +} cas_saturn_patch_t; + +#if 1 +cas_saturn_patch_t cas_saturn_patch[] = { +{0x8200, 0x007e}, {0x8201, 0x0082}, {0x8202, 0x0009}, +{0x8203, 0x0000}, {0x8204, 0x0000}, {0x8205, 0x0000}, +{0x8206, 0x0000}, {0x8207, 0x0000}, {0x8208, 0x0000}, +{0x8209, 0x008e}, {0x820a, 0x008e}, {0x820b, 0x00ff}, +{0x820c, 0x00ce}, {0x820d, 0x0082}, {0x820e, 0x0025}, +{0x820f, 0x00ff}, {0x8210, 0x0001}, {0x8211, 0x000f}, +{0x8212, 0x00ce}, {0x8213, 0x0084}, {0x8214, 0x0026}, +{0x8215, 0x00ff}, {0x8216, 0x0001}, {0x8217, 0x0011}, +{0x8218, 0x00ce}, {0x8219, 0x0085}, {0x821a, 0x003d}, +{0x821b, 0x00df}, {0x821c, 0x00e5}, {0x821d, 0x0086}, +{0x821e, 0x0039}, {0x821f, 0x00b7}, {0x8220, 0x008f}, +{0x8221, 0x00f8}, {0x8222, 0x007e}, {0x8223, 0x00c3}, +{0x8224, 0x00c2}, {0x8225, 0x0096}, {0x8226, 0x0047}, +{0x8227, 0x0084}, {0x8228, 0x00f3}, {0x8229, 0x008a}, +{0x822a, 0x0000}, {0x822b, 0x0097}, {0x822c, 0x0047}, +{0x822d, 0x00ce}, {0x822e, 0x0082}, {0x822f, 0x0033}, +{0x8230, 0x00ff}, {0x8231, 0x0001}, {0x8232, 0x000f}, +{0x8233, 0x0096}, {0x8234, 0x0046}, {0x8235, 0x0084}, +{0x8236, 0x000c}, {0x8237, 0x0081}, {0x8238, 0x0004}, +{0x8239, 0x0027}, {0x823a, 0x000b}, {0x823b, 0x0096}, +{0x823c, 0x0046}, {0x823d, 0x0084}, {0x823e, 0x000c}, +{0x823f, 0x0081}, {0x8240, 0x0008}, {0x8241, 0x0027}, +{0x8242, 0x0057}, {0x8243, 0x007e}, {0x8244, 0x0084}, +{0x8245, 0x0025}, {0x8246, 0x0096}, {0x8247, 0x0047}, +{0x8248, 0x0084}, {0x8249, 0x00f3}, {0x824a, 0x008a}, +{0x824b, 0x0004}, {0x824c, 0x0097}, {0x824d, 0x0047}, +{0x824e, 0x00ce}, {0x824f, 0x0082}, {0x8250, 0x0054}, +{0x8251, 0x00ff}, {0x8252, 0x0001}, {0x8253, 0x000f}, +{0x8254, 0x0096}, {0x8255, 0x0046}, {0x8256, 0x0084}, +{0x8257, 0x000c}, {0x8258, 0x0081}, {0x8259, 0x0004}, +{0x825a, 0x0026}, {0x825b, 0x0038}, {0x825c, 0x00b6}, +{0x825d, 0x0012}, {0x825e, 0x0020}, {0x825f, 0x0084}, +{0x8260, 0x0020}, {0x8261, 0x0026}, {0x8262, 0x0003}, +{0x8263, 0x007e}, {0x8264, 0x0084}, {0x8265, 0x0025}, +{0x8266, 0x0096}, {0x8267, 0x007b}, {0x8268, 0x00d6}, +{0x8269, 0x007c}, {0x826a, 0x00fe}, {0x826b, 0x008f}, +{0x826c, 0x0056}, {0x826d, 0x00bd}, {0x826e, 0x00f7}, +{0x826f, 0x00b6}, {0x8270, 0x00fe}, {0x8271, 0x008f}, +{0x8272, 0x004e}, {0x8273, 0x00bd}, {0x8274, 0x00ec}, +{0x8275, 0x008e}, {0x8276, 0x00bd}, {0x8277, 0x00fa}, +{0x8278, 0x00f7}, {0x8279, 0x00bd}, {0x827a, 0x00f7}, +{0x827b, 0x0028}, {0x827c, 0x00ce}, {0x827d, 0x0082}, +{0x827e, 0x0082}, {0x827f, 0x00ff}, {0x8280, 0x0001}, +{0x8281, 0x000f}, {0x8282, 0x0096}, {0x8283, 0x0046}, +{0x8284, 0x0084}, {0x8285, 0x000c}, {0x8286, 0x0081}, +{0x8287, 0x0004}, {0x8288, 0x0026}, {0x8289, 0x000a}, +{0x828a, 0x00b6}, {0x828b, 0x0012}, {0x828c, 0x0020}, +{0x828d, 0x0084}, {0x828e, 0x0020}, {0x828f, 0x0027}, +{0x8290, 0x00b5}, {0x8291, 0x007e}, {0x8292, 0x0084}, +{0x8293, 0x0025}, {0x8294, 0x00bd}, {0x8295, 0x00f7}, +{0x8296, 0x001f}, {0x8297, 0x007e}, {0x8298, 0x0084}, +{0x8299, 0x001f}, {0x829a, 0x0096}, {0x829b, 0x0047}, +{0x829c, 0x0084}, {0x829d, 0x00f3}, {0x829e, 0x008a}, +{0x829f, 0x0008}, {0x82a0, 0x0097}, {0x82a1, 0x0047}, +{0x82a2, 0x00de}, {0x82a3, 0x00e1}, {0x82a4, 0x00ad}, +{0x82a5, 0x0000}, {0x82a6, 0x00ce}, {0x82a7, 0x0082}, +{0x82a8, 0x00af}, {0x82a9, 0x00ff}, {0x82aa, 0x0001}, +{0x82ab, 0x000f}, {0x82ac, 0x007e}, {0x82ad, 0x0084}, +{0x82ae, 0x0025}, {0x82af, 0x0096}, {0x82b0, 0x0041}, +{0x82b1, 0x0085}, {0x82b2, 0x0010}, {0x82b3, 0x0026}, +{0x82b4, 0x0006}, {0x82b5, 0x0096}, {0x82b6, 0x0023}, +{0x82b7, 0x0085}, {0x82b8, 0x0040}, {0x82b9, 0x0027}, +{0x82ba, 0x0006}, {0x82bb, 0x00bd}, {0x82bc, 0x00ed}, +{0x82bd, 0x0000}, {0x82be, 0x007e}, {0x82bf, 0x0083}, +{0x82c0, 0x00a2}, {0x82c1, 0x00de}, {0x82c2, 0x0042}, +{0x82c3, 0x00bd}, {0x82c4, 0x00eb}, {0x82c5, 0x008e}, +{0x82c6, 0x0096}, {0x82c7, 0x0024}, {0x82c8, 0x0084}, +{0x82c9, 0x0008}, {0x82ca, 0x0027}, {0x82cb, 0x0003}, +{0x82cc, 0x007e}, {0x82cd, 0x0083}, {0x82ce, 0x00df}, +{0x82cf, 0x0096}, {0x82d0, 0x007b}, {0x82d1, 0x00d6}, +{0x82d2, 0x007c}, {0x82d3, 0x00fe}, {0x82d4, 0x008f}, +{0x82d5, 0x0056}, {0x82d6, 0x00bd}, {0x82d7, 0x00f7}, +{0x82d8, 0x00b6}, {0x82d9, 0x00fe}, {0x82da, 0x008f}, +{0x82db, 0x0050}, {0x82dc, 0x00bd}, {0x82dd, 0x00ec}, +{0x82de, 0x008e}, {0x82df, 0x00bd}, {0x82e0, 0x00fa}, +{0x82e1, 0x00f7}, {0x82e2, 0x0086}, {0x82e3, 0x0011}, +{0x82e4, 0x00c6}, {0x82e5, 0x0049}, {0x82e6, 0x00bd}, +{0x82e7, 0x00e4}, {0x82e8, 0x0012}, {0x82e9, 0x00ce}, +{0x82ea, 0x0082}, {0x82eb, 0x00ef}, {0x82ec, 0x00ff}, +{0x82ed, 0x0001}, {0x82ee, 0x000f}, {0x82ef, 0x0096}, +{0x82f0, 0x0046}, {0x82f1, 0x0084}, {0x82f2, 0x000c}, +{0x82f3, 0x0081}, {0x82f4, 0x0000}, {0x82f5, 0x0027}, +{0x82f6, 0x0017}, {0x82f7, 0x00c6}, {0x82f8, 0x0049}, +{0x82f9, 0x00bd}, {0x82fa, 0x00e4}, {0x82fb, 0x0091}, +{0x82fc, 0x0024}, {0x82fd, 0x000d}, {0x82fe, 0x00b6}, +{0x82ff, 0x0012}, {0x8300, 0x0020}, {0x8301, 0x0085}, +{0x8302, 0x0020}, {0x8303, 0x0026}, {0x8304, 0x000c}, +{0x8305, 0x00ce}, {0x8306, 0x0082}, {0x8307, 0x00c1}, +{0x8308, 0x00ff}, {0x8309, 0x0001}, {0x830a, 0x000f}, +{0x830b, 0x007e}, {0x830c, 0x0084}, {0x830d, 0x0025}, +{0x830e, 0x007e}, {0x830f, 0x0084}, {0x8310, 0x0016}, +{0x8311, 0x00fe}, {0x8312, 0x008f}, {0x8313, 0x0052}, +{0x8314, 0x00bd}, {0x8315, 0x00ec}, {0x8316, 0x008e}, +{0x8317, 0x00bd}, {0x8318, 0x00fa}, {0x8319, 0x00f7}, +{0x831a, 0x0086}, {0x831b, 0x006a}, {0x831c, 0x00c6}, +{0x831d, 0x0049}, {0x831e, 0x00bd}, {0x831f, 0x00e4}, +{0x8320, 0x0012}, {0x8321, 0x00ce}, {0x8322, 0x0083}, +{0x8323, 0x0027}, {0x8324, 0x00ff}, {0x8325, 0x0001}, +{0x8326, 0x000f}, {0x8327, 0x0096}, {0x8328, 0x0046}, +{0x8329, 0x0084}, {0x832a, 0x000c}, {0x832b, 0x0081}, +{0x832c, 0x0000}, {0x832d, 0x0027}, {0x832e, 0x000a}, +{0x832f, 0x00c6}, {0x8330, 0x0049}, {0x8331, 0x00bd}, +{0x8332, 0x00e4}, {0x8333, 0x0091}, {0x8334, 0x0025}, +{0x8335, 0x0006}, {0x8336, 0x007e}, {0x8337, 0x0084}, +{0x8338, 0x0025}, {0x8339, 0x007e}, {0x833a, 0x0084}, +{0x833b, 0x0016}, {0x833c, 0x00b6}, {0x833d, 0x0018}, +{0x833e, 0x0070}, {0x833f, 0x00bb}, {0x8340, 0x0019}, +{0x8341, 0x0070}, {0x8342, 0x002a}, {0x8343, 0x0004}, +{0x8344, 0x0081}, {0x8345, 0x00af}, {0x8346, 0x002e}, +{0x8347, 0x0019}, {0x8348, 0x0096}, {0x8349, 0x007b}, +{0x834a, 0x00f6}, {0x834b, 0x0020}, {0x834c, 0x0007}, +{0x834d, 0x00fa}, {0x834e, 0x0020}, {0x834f, 0x0027}, +{0x8350, 0x00c4}, {0x8351, 0x0038}, {0x8352, 0x0081}, +{0x8353, 0x0038}, {0x8354, 0x0027}, {0x8355, 0x000b}, +{0x8356, 0x00f6}, {0x8357, 0x0020}, {0x8358, 0x0007}, +{0x8359, 0x00fa}, {0x835a, 0x0020}, {0x835b, 0x0027}, +{0x835c, 0x00cb}, {0x835d, 0x0008}, {0x835e, 0x007e}, +{0x835f, 0x0082}, {0x8360, 0x00d3}, {0x8361, 0x00bd}, +{0x8362, 0x00f7}, {0x8363, 0x0066}, {0x8364, 0x0086}, +{0x8365, 0x0074}, {0x8366, 0x00c6}, {0x8367, 0x0049}, +{0x8368, 0x00bd}, {0x8369, 0x00e4}, {0x836a, 0x0012}, +{0x836b, 0x00ce}, {0x836c, 0x0083}, {0x836d, 0x0071}, +{0x836e, 0x00ff}, {0x836f, 0x0001}, {0x8370, 0x000f}, +{0x8371, 0x0096}, {0x8372, 0x0046}, {0x8373, 0x0084}, +{0x8374, 0x000c}, {0x8375, 0x0081}, {0x8376, 0x0008}, +{0x8377, 0x0026}, {0x8378, 0x000a}, {0x8379, 0x00c6}, +{0x837a, 0x0049}, {0x837b, 0x00bd}, {0x837c, 0x00e4}, +{0x837d, 0x0091}, {0x837e, 0x0025}, {0x837f, 0x0006}, +{0x8380, 0x007e}, {0x8381, 0x0084}, {0x8382, 0x0025}, +{0x8383, 0x007e}, {0x8384, 0x0084}, {0x8385, 0x0016}, +{0x8386, 0x00bd}, {0x8387, 0x00f7}, {0x8388, 0x003e}, +{0x8389, 0x0026}, {0x838a, 0x000e}, {0x838b, 0x00bd}, +{0x838c, 0x00e5}, {0x838d, 0x0009}, {0x838e, 0x0026}, +{0x838f, 0x0006}, {0x8390, 0x00ce}, {0x8391, 0x0082}, +{0x8392, 0x00c1}, {0x8393, 0x00ff}, {0x8394, 0x0001}, +{0x8395, 0x000f}, {0x8396, 0x007e}, {0x8397, 0x0084}, +{0x8398, 0x0025}, {0x8399, 0x00fe}, {0x839a, 0x008f}, +{0x839b, 0x0054}, {0x839c, 0x00bd}, {0x839d, 0x00ec}, +{0x839e, 0x008e}, {0x839f, 0x00bd}, {0x83a0, 0x00fa}, +{0x83a1, 0x00f7}, {0x83a2, 0x00bd}, {0x83a3, 0x00f7}, +{0x83a4, 0x0033}, {0x83a5, 0x0086}, {0x83a6, 0x000f}, +{0x83a7, 0x00c6}, {0x83a8, 0x0051}, {0x83a9, 0x00bd}, +{0x83aa, 0x00e4}, {0x83ab, 0x0012}, {0x83ac, 0x00ce}, +{0x83ad, 0x0083}, {0x83ae, 0x00b2}, {0x83af, 0x00ff}, +{0x83b0, 0x0001}, {0x83b1, 0x000f}, {0x83b2, 0x0096}, +{0x83b3, 0x0046}, {0x83b4, 0x0084}, {0x83b5, 0x000c}, +{0x83b6, 0x0081}, {0x83b7, 0x0008}, {0x83b8, 0x0026}, +{0x83b9, 0x005c}, {0x83ba, 0x00b6}, {0x83bb, 0x0012}, +{0x83bc, 0x0020}, {0x83bd, 0x0084}, {0x83be, 0x003f}, +{0x83bf, 0x0081}, {0x83c0, 0x003a}, {0x83c1, 0x0027}, +{0x83c2, 0x001c}, {0x83c3, 0x0096}, {0x83c4, 0x0023}, +{0x83c5, 0x0085}, {0x83c6, 0x0040}, {0x83c7, 0x0027}, +{0x83c8, 0x0003}, {0x83c9, 0x007e}, {0x83ca, 0x0084}, +{0x83cb, 0x0025}, {0x83cc, 0x00c6}, {0x83cd, 0x0051}, +{0x83ce, 0x00bd}, {0x83cf, 0x00e4}, {0x83d0, 0x0091}, +{0x83d1, 0x0025}, {0x83d2, 0x0003}, {0x83d3, 0x007e}, +{0x83d4, 0x0084}, {0x83d5, 0x0025}, {0x83d6, 0x00ce}, +{0x83d7, 0x0082}, {0x83d8, 0x00c1}, {0x83d9, 0x00ff}, +{0x83da, 0x0001}, {0x83db, 0x000f}, {0x83dc, 0x007e}, +{0x83dd, 0x0084}, {0x83de, 0x0025}, {0x83df, 0x00bd}, +{0x83e0, 0x00f8}, {0x83e1, 0x0037}, {0x83e2, 0x007c}, +{0x83e3, 0x0000}, {0x83e4, 0x007a}, {0x83e5, 0x00ce}, +{0x83e6, 0x0083}, {0x83e7, 0x00ee}, {0x83e8, 0x00ff}, +{0x83e9, 0x0001}, {0x83ea, 0x000f}, {0x83eb, 0x007e}, +{0x83ec, 0x0084}, {0x83ed, 0x0025}, {0x83ee, 0x0096}, +{0x83ef, 0x0046}, {0x83f0, 0x0084}, {0x83f1, 0x000c}, +{0x83f2, 0x0081}, {0x83f3, 0x0008}, {0x83f4, 0x0026}, +{0x83f5, 0x0020}, {0x83f6, 0x0096}, {0x83f7, 0x0024}, +{0x83f8, 0x0084}, {0x83f9, 0x0008}, {0x83fa, 0x0026}, +{0x83fb, 0x0029}, {0x83fc, 0x00b6}, {0x83fd, 0x0018}, +{0x83fe, 0x0082}, {0x83ff, 0x00bb}, {0x8400, 0x0019}, +{0x8401, 0x0082}, {0x8402, 0x00b1}, {0x8403, 0x0001}, +{0x8404, 0x003b}, {0x8405, 0x0022}, {0x8406, 0x0009}, +{0x8407, 0x00b6}, {0x8408, 0x0012}, {0x8409, 0x0020}, +{0x840a, 0x0084}, {0x840b, 0x0037}, {0x840c, 0x0081}, +{0x840d, 0x0032}, {0x840e, 0x0027}, {0x840f, 0x0015}, +{0x8410, 0x00bd}, {0x8411, 0x00f8}, {0x8412, 0x0044}, +{0x8413, 0x007e}, {0x8414, 0x0082}, {0x8415, 0x00c1}, +{0x8416, 0x00bd}, {0x8417, 0x00f7}, {0x8418, 0x001f}, +{0x8419, 0x00bd}, {0x841a, 0x00f8}, {0x841b, 0x0044}, +{0x841c, 0x00bd}, {0x841d, 0x00fc}, {0x841e, 0x0029}, +{0x841f, 0x00ce}, {0x8420, 0x0082}, {0x8421, 0x0025}, +{0x8422, 0x00ff}, {0x8423, 0x0001}, {0x8424, 0x000f}, +{0x8425, 0x0039}, {0x8426, 0x0096}, {0x8427, 0x0047}, +{0x8428, 0x0084}, {0x8429, 0x00fc}, {0x842a, 0x008a}, +{0x842b, 0x0000}, {0x842c, 0x0097}, {0x842d, 0x0047}, +{0x842e, 0x00ce}, {0x842f, 0x0084}, {0x8430, 0x0034}, +{0x8431, 0x00ff}, {0x8432, 0x0001}, {0x8433, 0x0011}, +{0x8434, 0x0096}, {0x8435, 0x0046}, {0x8436, 0x0084}, +{0x8437, 0x0003}, {0x8438, 0x0081}, {0x8439, 0x0002}, +{0x843a, 0x0027}, {0x843b, 0x0003}, {0x843c, 0x007e}, +{0x843d, 0x0085}, {0x843e, 0x001e}, {0x843f, 0x0096}, +{0x8440, 0x0047}, {0x8441, 0x0084}, {0x8442, 0x00fc}, +{0x8443, 0x008a}, {0x8444, 0x0002}, {0x8445, 0x0097}, +{0x8446, 0x0047}, {0x8447, 0x00de}, {0x8448, 0x00e1}, +{0x8449, 0x00ad}, {0x844a, 0x0000}, {0x844b, 0x0086}, +{0x844c, 0x0001}, {0x844d, 0x00b7}, {0x844e, 0x0012}, +{0x844f, 0x0051}, {0x8450, 0x00bd}, {0x8451, 0x00f7}, +{0x8452, 0x0014}, {0x8453, 0x00b6}, {0x8454, 0x0010}, +{0x8455, 0x0031}, {0x8456, 0x0084}, {0x8457, 0x00fd}, +{0x8458, 0x00b7}, {0x8459, 0x0010}, {0x845a, 0x0031}, +{0x845b, 0x00bd}, {0x845c, 0x00f8}, {0x845d, 0x001e}, +{0x845e, 0x0096}, {0x845f, 0x0081}, {0x8460, 0x00d6}, +{0x8461, 0x0082}, {0x8462, 0x00fe}, {0x8463, 0x008f}, +{0x8464, 0x005a}, {0x8465, 0x00bd}, {0x8466, 0x00f7}, +{0x8467, 0x00b6}, {0x8468, 0x00fe}, {0x8469, 0x008f}, +{0x846a, 0x005c}, {0x846b, 0x00bd}, {0x846c, 0x00ec}, +{0x846d, 0x008e}, {0x846e, 0x00bd}, {0x846f, 0x00fa}, +{0x8470, 0x00f7}, {0x8471, 0x0086}, {0x8472, 0x0008}, +{0x8473, 0x00d6}, {0x8474, 0x0000}, {0x8475, 0x00c5}, +{0x8476, 0x0010}, {0x8477, 0x0026}, {0x8478, 0x0002}, +{0x8479, 0x008b}, {0x847a, 0x0020}, {0x847b, 0x00c6}, +{0x847c, 0x0051}, {0x847d, 0x00bd}, {0x847e, 0x00e4}, +{0x847f, 0x0012}, {0x8480, 0x00ce}, {0x8481, 0x0084}, +{0x8482, 0x0086}, {0x8483, 0x00ff}, {0x8484, 0x0001}, +{0x8485, 0x0011}, {0x8486, 0x0096}, {0x8487, 0x0046}, +{0x8488, 0x0084}, {0x8489, 0x0003}, {0x848a, 0x0081}, +{0x848b, 0x0002}, {0x848c, 0x0027}, {0x848d, 0x0003}, +{0x848e, 0x007e}, {0x848f, 0x0085}, {0x8490, 0x000f}, +{0x8491, 0x00c6}, {0x8492, 0x0051}, {0x8493, 0x00bd}, +{0x8494, 0x00e4}, {0x8495, 0x0091}, {0x8496, 0x0025}, +{0x8497, 0x0003}, {0x8498, 0x007e}, {0x8499, 0x0085}, +{0x849a, 0x001e}, {0x849b, 0x0096}, {0x849c, 0x0044}, +{0x849d, 0x0085}, {0x849e, 0x0010}, {0x849f, 0x0026}, +{0x84a0, 0x000a}, {0x84a1, 0x00b6}, {0x84a2, 0x0012}, +{0x84a3, 0x0050}, {0x84a4, 0x00ba}, {0x84a5, 0x0001}, +{0x84a6, 0x003c}, {0x84a7, 0x0085}, {0x84a8, 0x0010}, +{0x84a9, 0x0027}, {0x84aa, 0x00a8}, {0x84ab, 0x00bd}, +{0x84ac, 0x00f7}, {0x84ad, 0x0066}, {0x84ae, 0x00ce}, +{0x84af, 0x0084}, {0x84b0, 0x00b7}, {0x84b1, 0x00ff}, +{0x84b2, 0x0001}, {0x84b3, 0x0011}, {0x84b4, 0x007e}, +{0x84b5, 0x0085}, {0x84b6, 0x001e}, {0x84b7, 0x0096}, +{0x84b8, 0x0046}, {0x84b9, 0x0084}, {0x84ba, 0x0003}, +{0x84bb, 0x0081}, {0x84bc, 0x0002}, {0x84bd, 0x0026}, +{0x84be, 0x0050}, {0x84bf, 0x00b6}, {0x84c0, 0x0012}, +{0x84c1, 0x0030}, {0x84c2, 0x0084}, {0x84c3, 0x0003}, +{0x84c4, 0x0081}, {0x84c5, 0x0001}, {0x84c6, 0x0027}, +{0x84c7, 0x0003}, {0x84c8, 0x007e}, {0x84c9, 0x0085}, +{0x84ca, 0x001e}, {0x84cb, 0x0096}, {0x84cc, 0x0044}, +{0x84cd, 0x0085}, {0x84ce, 0x0010}, {0x84cf, 0x0026}, +{0x84d0, 0x0013}, {0x84d1, 0x00b6}, {0x84d2, 0x0012}, +{0x84d3, 0x0050}, {0x84d4, 0x00ba}, {0x84d5, 0x0001}, +{0x84d6, 0x003c}, {0x84d7, 0x0085}, {0x84d8, 0x0010}, +{0x84d9, 0x0026}, {0x84da, 0x0009}, {0x84db, 0x00ce}, +{0x84dc, 0x0084}, {0x84dd, 0x0053}, {0x84de, 0x00ff}, +{0x84df, 0x0001}, {0x84e0, 0x0011}, {0x84e1, 0x007e}, +{0x84e2, 0x0085}, {0x84e3, 0x001e}, {0x84e4, 0x00b6}, +{0x84e5, 0x0010}, {0x84e6, 0x0031}, {0x84e7, 0x008a}, +{0x84e8, 0x0002}, {0x84e9, 0x00b7}, {0x84ea, 0x0010}, +{0x84eb, 0x0031}, {0x84ec, 0x00bd}, {0x84ed, 0x0085}, +{0x84ee, 0x001f}, {0x84ef, 0x00bd}, {0x84f0, 0x00f8}, +{0x84f1, 0x0037}, {0x84f2, 0x007c}, {0x84f3, 0x0000}, +{0x84f4, 0x0080}, {0x84f5, 0x00ce}, {0x84f6, 0x0084}, +{0x84f7, 0x00fe}, {0x84f8, 0x00ff}, {0x84f9, 0x0001}, +{0x84fa, 0x0011}, {0x84fb, 0x007e}, {0x84fc, 0x0085}, +{0x84fd, 0x001e}, {0x84fe, 0x0096}, {0x84ff, 0x0046}, +{0x8500, 0x0084}, {0x8501, 0x0003}, {0x8502, 0x0081}, +{0x8503, 0x0002}, {0x8504, 0x0026}, {0x8505, 0x0009}, +{0x8506, 0x00b6}, {0x8507, 0x0012}, {0x8508, 0x0030}, +{0x8509, 0x0084}, {0x850a, 0x0003}, {0x850b, 0x0081}, +{0x850c, 0x0001}, {0x850d, 0x0027}, {0x850e, 0x000f}, +{0x850f, 0x00bd}, {0x8510, 0x00f8}, {0x8511, 0x0044}, +{0x8512, 0x00bd}, {0x8513, 0x00f7}, {0x8514, 0x000b}, +{0x8515, 0x00bd}, {0x8516, 0x00fc}, {0x8517, 0x0029}, +{0x8518, 0x00ce}, {0x8519, 0x0084}, {0x851a, 0x0026}, +{0x851b, 0x00ff}, {0x851c, 0x0001}, {0x851d, 0x0011}, +{0x851e, 0x0039}, {0x851f, 0x00d6}, {0x8520, 0x0022}, +{0x8521, 0x00c4}, {0x8522, 0x000f}, {0x8523, 0x00b6}, +{0x8524, 0x0012}, {0x8525, 0x0030}, {0x8526, 0x00ba}, +{0x8527, 0x0012}, {0x8528, 0x0032}, {0x8529, 0x0084}, +{0x852a, 0x0004}, {0x852b, 0x0027}, {0x852c, 0x000d}, +{0x852d, 0x0096}, {0x852e, 0x0022}, {0x852f, 0x0085}, +{0x8530, 0x0004}, {0x8531, 0x0027}, {0x8532, 0x0005}, +{0x8533, 0x00ca}, {0x8534, 0x0010}, {0x8535, 0x007e}, +{0x8536, 0x0085}, {0x8537, 0x003a}, {0x8538, 0x00ca}, +{0x8539, 0x0020}, {0x853a, 0x00d7}, {0x853b, 0x0022}, +{0x853c, 0x0039}, {0x853d, 0x0086}, {0x853e, 0x0000}, +{0x853f, 0x0097}, {0x8540, 0x0083}, {0x8541, 0x0018}, +{0x8542, 0x00ce}, {0x8543, 0x001c}, {0x8544, 0x0000}, +{0x8545, 0x00bd}, {0x8546, 0x00eb}, {0x8547, 0x0046}, +{0x8548, 0x0096}, {0x8549, 0x0057}, {0x854a, 0x0085}, +{0x854b, 0x0001}, {0x854c, 0x0027}, {0x854d, 0x0002}, +{0x854e, 0x004f}, {0x854f, 0x0039}, {0x8550, 0x0085}, +{0x8551, 0x0002}, {0x8552, 0x0027}, {0x8553, 0x0001}, +{0x8554, 0x0039}, {0x8555, 0x007f}, {0x8556, 0x008f}, +{0x8557, 0x007d}, {0x8558, 0x0086}, {0x8559, 0x0004}, +{0x855a, 0x00b7}, {0x855b, 0x0012}, {0x855c, 0x0004}, +{0x855d, 0x0086}, {0x855e, 0x0008}, {0x855f, 0x00b7}, +{0x8560, 0x0012}, {0x8561, 0x0007}, {0x8562, 0x0086}, +{0x8563, 0x0010}, {0x8564, 0x00b7}, {0x8565, 0x0012}, +{0x8566, 0x000c}, {0x8567, 0x0086}, {0x8568, 0x0007}, +{0x8569, 0x00b7}, {0x856a, 0x0012}, {0x856b, 0x0006}, +{0x856c, 0x00b6}, {0x856d, 0x008f}, {0x856e, 0x007d}, +{0x856f, 0x00b7}, {0x8570, 0x0012}, {0x8571, 0x0070}, +{0x8572, 0x0086}, {0x8573, 0x0001}, {0x8574, 0x00ba}, +{0x8575, 0x0012}, {0x8576, 0x0004}, {0x8577, 0x00b7}, +{0x8578, 0x0012}, {0x8579, 0x0004}, {0x857a, 0x0001}, +{0x857b, 0x0001}, {0x857c, 0x0001}, {0x857d, 0x0001}, +{0x857e, 0x0001}, {0x857f, 0x0001}, {0x8580, 0x00b6}, +{0x8581, 0x0012}, {0x8582, 0x0004}, {0x8583, 0x0084}, +{0x8584, 0x00fe}, {0x8585, 0x008a}, {0x8586, 0x0002}, +{0x8587, 0x00b7}, {0x8588, 0x0012}, {0x8589, 0x0004}, +{0x858a, 0x0001}, {0x858b, 0x0001}, {0x858c, 0x0001}, +{0x858d, 0x0001}, {0x858e, 0x0001}, {0x858f, 0x0001}, +{0x8590, 0x0086}, {0x8591, 0x00fd}, {0x8592, 0x00b4}, +{0x8593, 0x0012}, {0x8594, 0x0004}, {0x8595, 0x00b7}, +{0x8596, 0x0012}, {0x8597, 0x0004}, {0x8598, 0x00b6}, +{0x8599, 0x0012}, {0x859a, 0x0000}, {0x859b, 0x0084}, +{0x859c, 0x0008}, {0x859d, 0x0081}, {0x859e, 0x0008}, +{0x859f, 0x0027}, {0x85a0, 0x0016}, {0x85a1, 0x00b6}, +{0x85a2, 0x008f}, {0x85a3, 0x007d}, {0x85a4, 0x0081}, +{0x85a5, 0x000c}, {0x85a6, 0x0027}, {0x85a7, 0x0008}, +{0x85a8, 0x008b}, {0x85a9, 0x0004}, {0x85aa, 0x00b7}, +{0x85ab, 0x008f}, {0x85ac, 0x007d}, {0x85ad, 0x007e}, +{0x85ae, 0x0085}, {0x85af, 0x006c}, {0x85b0, 0x0086}, +{0x85b1, 0x0003}, {0x85b2, 0x0097}, {0x85b3, 0x0040}, +{0x85b4, 0x007e}, {0x85b5, 0x0089}, {0x85b6, 0x006e}, +{0x85b7, 0x0086}, {0x85b8, 0x0007}, {0x85b9, 0x00b7}, +{0x85ba, 0x0012}, {0x85bb, 0x0006}, {0x85bc, 0x005f}, +{0x85bd, 0x00f7}, {0x85be, 0x008f}, {0x85bf, 0x0082}, +{0x85c0, 0x005f}, {0x85c1, 0x00f7}, {0x85c2, 0x008f}, +{0x85c3, 0x007f}, {0x85c4, 0x00f7}, {0x85c5, 0x008f}, +{0x85c6, 0x0070}, {0x85c7, 0x00f7}, {0x85c8, 0x008f}, +{0x85c9, 0x0071}, {0x85ca, 0x00f7}, {0x85cb, 0x008f}, +{0x85cc, 0x0072}, {0x85cd, 0x00f7}, {0x85ce, 0x008f}, +{0x85cf, 0x0073}, {0x85d0, 0x00f7}, {0x85d1, 0x008f}, +{0x85d2, 0x0074}, {0x85d3, 0x00f7}, {0x85d4, 0x008f}, +{0x85d5, 0x0075}, {0x85d6, 0x00f7}, {0x85d7, 0x008f}, +{0x85d8, 0x0076}, {0x85d9, 0x00f7}, {0x85da, 0x008f}, +{0x85db, 0x0077}, {0x85dc, 0x00f7}, {0x85dd, 0x008f}, +{0x85de, 0x0078}, {0x85df, 0x00f7}, {0x85e0, 0x008f}, +{0x85e1, 0x0079}, {0x85e2, 0x00f7}, {0x85e3, 0x008f}, +{0x85e4, 0x007a}, {0x85e5, 0x00f7}, {0x85e6, 0x008f}, +{0x85e7, 0x007b}, {0x85e8, 0x00b6}, {0x85e9, 0x0012}, +{0x85ea, 0x0004}, {0x85eb, 0x008a}, {0x85ec, 0x0010}, +{0x85ed, 0x00b7}, {0x85ee, 0x0012}, {0x85ef, 0x0004}, +{0x85f0, 0x0086}, {0x85f1, 0x00e4}, {0x85f2, 0x00b7}, +{0x85f3, 0x0012}, {0x85f4, 0x0070}, {0x85f5, 0x00b7}, +{0x85f6, 0x0012}, {0x85f7, 0x0007}, {0x85f8, 0x00f7}, +{0x85f9, 0x0012}, {0x85fa, 0x0005}, {0x85fb, 0x00f7}, +{0x85fc, 0x0012}, {0x85fd, 0x0009}, {0x85fe, 0x0086}, +{0x85ff, 0x0008}, {0x8600, 0x00ba}, {0x8601, 0x0012}, +{0x8602, 0x0004}, {0x8603, 0x00b7}, {0x8604, 0x0012}, +{0x8605, 0x0004}, {0x8606, 0x0086}, {0x8607, 0x00f7}, +{0x8608, 0x00b4}, {0x8609, 0x0012}, {0x860a, 0x0004}, +{0x860b, 0x00b7}, {0x860c, 0x0012}, {0x860d, 0x0004}, +{0x860e, 0x0001}, {0x860f, 0x0001}, {0x8610, 0x0001}, +{0x8611, 0x0001}, {0x8612, 0x0001}, {0x8613, 0x0001}, +{0x8614, 0x00b6}, {0x8615, 0x0012}, {0x8616, 0x0008}, +{0x8617, 0x0027}, {0x8618, 0x007f}, {0x8619, 0x0081}, +{0x861a, 0x0080}, {0x861b, 0x0026}, {0x861c, 0x000b}, +{0x861d, 0x0086}, {0x861e, 0x0008}, {0x861f, 0x00ce}, +{0x8620, 0x008f}, {0x8621, 0x0079}, {0x8622, 0x00bd}, +{0x8623, 0x0089}, {0x8624, 0x007b}, {0x8625, 0x007e}, +{0x8626, 0x0086}, {0x8627, 0x008e}, {0x8628, 0x0081}, +{0x8629, 0x0040}, {0x862a, 0x0026}, {0x862b, 0x000b}, +{0x862c, 0x0086}, {0x862d, 0x0004}, {0x862e, 0x00ce}, +{0x862f, 0x008f}, {0x8630, 0x0076}, {0x8631, 0x00bd}, +{0x8632, 0x0089}, {0x8633, 0x007b}, {0x8634, 0x007e}, +{0x8635, 0x0086}, {0x8636, 0x008e}, {0x8637, 0x0081}, +{0x8638, 0x0020}, {0x8639, 0x0026}, {0x863a, 0x000b}, +{0x863b, 0x0086}, {0x863c, 0x0002}, {0x863d, 0x00ce}, +{0x863e, 0x008f}, {0x863f, 0x0073}, {0x8640, 0x00bd}, +{0x8641, 0x0089}, {0x8642, 0x007b}, {0x8643, 0x007e}, +{0x8644, 0x0086}, {0x8645, 0x008e}, {0x8646, 0x0081}, +{0x8647, 0x0010}, {0x8648, 0x0026}, {0x8649, 0x000b}, +{0x864a, 0x0086}, {0x864b, 0x0001}, {0x864c, 0x00ce}, +{0x864d, 0x008f}, {0x864e, 0x0070}, {0x864f, 0x00bd}, +{0x8650, 0x0089}, {0x8651, 0x007b}, {0x8652, 0x007e}, +{0x8653, 0x0086}, {0x8654, 0x008e}, {0x8655, 0x0081}, +{0x8656, 0x0008}, {0x8657, 0x0026}, {0x8658, 0x000b}, +{0x8659, 0x0086}, {0x865a, 0x0008}, {0x865b, 0x00ce}, +{0x865c, 0x008f}, {0x865d, 0x0079}, {0x865e, 0x00bd}, +{0x865f, 0x0089}, {0x8660, 0x007f}, {0x8661, 0x007e}, +{0x8662, 0x0086}, {0x8663, 0x008e}, {0x8664, 0x0081}, +{0x8665, 0x0004}, {0x8666, 0x0026}, {0x8667, 0x000b}, +{0x8668, 0x0086}, {0x8669, 0x0004}, {0x866a, 0x00ce}, +{0x866b, 0x008f}, {0x866c, 0x0076}, {0x866d, 0x00bd}, +{0x866e, 0x0089}, {0x866f, 0x007f}, {0x8670, 0x007e}, +{0x8671, 0x0086}, {0x8672, 0x008e}, {0x8673, 0x0081}, +{0x8674, 0x0002}, {0x8675, 0x0026}, {0x8676, 0x000b}, +{0x8677, 0x008a}, {0x8678, 0x0002}, {0x8679, 0x00ce}, +{0x867a, 0x008f}, {0x867b, 0x0073}, {0x867c, 0x00bd}, +{0x867d, 0x0089}, {0x867e, 0x007f}, {0x867f, 0x007e}, +{0x8680, 0x0086}, {0x8681, 0x008e}, {0x8682, 0x0081}, +{0x8683, 0x0001}, {0x8684, 0x0026}, {0x8685, 0x0008}, +{0x8686, 0x0086}, {0x8687, 0x0001}, {0x8688, 0x00ce}, +{0x8689, 0x008f}, {0x868a, 0x0070}, {0x868b, 0x00bd}, +{0x868c, 0x0089}, {0x868d, 0x007f}, {0x868e, 0x00b6}, +{0x868f, 0x008f}, {0x8690, 0x007f}, {0x8691, 0x0081}, +{0x8692, 0x000f}, {0x8693, 0x0026}, {0x8694, 0x0003}, +{0x8695, 0x007e}, {0x8696, 0x0087}, {0x8697, 0x0047}, +{0x8698, 0x00b6}, {0x8699, 0x0012}, {0x869a, 0x0009}, +{0x869b, 0x0084}, {0x869c, 0x0003}, {0x869d, 0x0081}, +{0x869e, 0x0003}, {0x869f, 0x0027}, {0x86a0, 0x0006}, +{0x86a1, 0x007c}, {0x86a2, 0x0012}, {0x86a3, 0x0009}, +{0x86a4, 0x007e}, {0x86a5, 0x0085}, {0x86a6, 0x00fe}, +{0x86a7, 0x00b6}, {0x86a8, 0x0012}, {0x86a9, 0x0006}, +{0x86aa, 0x0084}, {0x86ab, 0x0007}, {0x86ac, 0x0081}, +{0x86ad, 0x0007}, {0x86ae, 0x0027}, {0x86af, 0x0008}, +{0x86b0, 0x008b}, {0x86b1, 0x0001}, {0x86b2, 0x00b7}, +{0x86b3, 0x0012}, {0x86b4, 0x0006}, {0x86b5, 0x007e}, +{0x86b6, 0x0086}, {0x86b7, 0x00d5}, {0x86b8, 0x00b6}, +{0x86b9, 0x008f}, {0x86ba, 0x0082}, {0x86bb, 0x0026}, +{0x86bc, 0x000a}, {0x86bd, 0x007c}, {0x86be, 0x008f}, +{0x86bf, 0x0082}, {0x86c0, 0x004f}, {0x86c1, 0x00b7}, +{0x86c2, 0x0012}, {0x86c3, 0x0006}, {0x86c4, 0x007e}, +{0x86c5, 0x0085}, {0x86c6, 0x00c0}, {0x86c7, 0x00b6}, +{0x86c8, 0x0012}, {0x86c9, 0x0006}, {0x86ca, 0x0084}, +{0x86cb, 0x003f}, {0x86cc, 0x0081}, {0x86cd, 0x003f}, +{0x86ce, 0x0027}, {0x86cf, 0x0010}, {0x86d0, 0x008b}, +{0x86d1, 0x0008}, {0x86d2, 0x00b7}, {0x86d3, 0x0012}, +{0x86d4, 0x0006}, {0x86d5, 0x00b6}, {0x86d6, 0x0012}, +{0x86d7, 0x0009}, {0x86d8, 0x0084}, {0x86d9, 0x00fc}, +{0x86da, 0x00b7}, {0x86db, 0x0012}, {0x86dc, 0x0009}, +{0x86dd, 0x007e}, {0x86de, 0x0085}, {0x86df, 0x00fe}, +{0x86e0, 0x00ce}, {0x86e1, 0x008f}, {0x86e2, 0x0070}, +{0x86e3, 0x0018}, {0x86e4, 0x00ce}, {0x86e5, 0x008f}, +{0x86e6, 0x0084}, {0x86e7, 0x00c6}, {0x86e8, 0x000c}, +{0x86e9, 0x00bd}, {0x86ea, 0x0089}, {0x86eb, 0x006f}, +{0x86ec, 0x00ce}, {0x86ed, 0x008f}, {0x86ee, 0x0084}, +{0x86ef, 0x0018}, {0x86f0, 0x00ce}, {0x86f1, 0x008f}, +{0x86f2, 0x0070}, {0x86f3, 0x00c6}, {0x86f4, 0x000c}, +{0x86f5, 0x00bd}, {0x86f6, 0x0089}, {0x86f7, 0x006f}, +{0x86f8, 0x00d6}, {0x86f9, 0x0083}, {0x86fa, 0x00c1}, +{0x86fb, 0x004f}, {0x86fc, 0x002d}, {0x86fd, 0x0003}, +{0x86fe, 0x007e}, {0x86ff, 0x0087}, {0x8700, 0x0040}, +{0x8701, 0x00b6}, {0x8702, 0x008f}, {0x8703, 0x007f}, +{0x8704, 0x0081}, {0x8705, 0x0007}, {0x8706, 0x0027}, +{0x8707, 0x000f}, {0x8708, 0x0081}, {0x8709, 0x000b}, +{0x870a, 0x0027}, {0x870b, 0x0015}, {0x870c, 0x0081}, +{0x870d, 0x000d}, {0x870e, 0x0027}, {0x870f, 0x001b}, +{0x8710, 0x0081}, {0x8711, 0x000e}, {0x8712, 0x0027}, +{0x8713, 0x0021}, {0x8714, 0x007e}, {0x8715, 0x0087}, +{0x8716, 0x0040}, {0x8717, 0x00f7}, {0x8718, 0x008f}, +{0x8719, 0x007b}, {0x871a, 0x0086}, {0x871b, 0x0002}, +{0x871c, 0x00b7}, {0x871d, 0x008f}, {0x871e, 0x007a}, +{0x871f, 0x0020}, {0x8720, 0x001c}, {0x8721, 0x00f7}, +{0x8722, 0x008f}, {0x8723, 0x0078}, {0x8724, 0x0086}, +{0x8725, 0x0002}, {0x8726, 0x00b7}, {0x8727, 0x008f}, +{0x8728, 0x0077}, {0x8729, 0x0020}, {0x872a, 0x0012}, +{0x872b, 0x00f7}, {0x872c, 0x008f}, {0x872d, 0x0075}, +{0x872e, 0x0086}, {0x872f, 0x0002}, {0x8730, 0x00b7}, +{0x8731, 0x008f}, {0x8732, 0x0074}, {0x8733, 0x0020}, +{0x8734, 0x0008}, {0x8735, 0x00f7}, {0x8736, 0x008f}, +{0x8737, 0x0072}, {0x8738, 0x0086}, {0x8739, 0x0002}, +{0x873a, 0x00b7}, {0x873b, 0x008f}, {0x873c, 0x0071}, +{0x873d, 0x007e}, {0x873e, 0x0087}, {0x873f, 0x0047}, +{0x8740, 0x0086}, {0x8741, 0x0004}, {0x8742, 0x0097}, +{0x8743, 0x0040}, {0x8744, 0x007e}, {0x8745, 0x0089}, +{0x8746, 0x006e}, {0x8747, 0x00ce}, {0x8748, 0x008f}, +{0x8749, 0x0072}, {0x874a, 0x00bd}, {0x874b, 0x0089}, +{0x874c, 0x00f7}, {0x874d, 0x00ce}, {0x874e, 0x008f}, +{0x874f, 0x0075}, {0x8750, 0x00bd}, {0x8751, 0x0089}, +{0x8752, 0x00f7}, {0x8753, 0x00ce}, {0x8754, 0x008f}, +{0x8755, 0x0078}, {0x8756, 0x00bd}, {0x8757, 0x0089}, +{0x8758, 0x00f7}, {0x8759, 0x00ce}, {0x875a, 0x008f}, +{0x875b, 0x007b}, {0x875c, 0x00bd}, {0x875d, 0x0089}, +{0x875e, 0x00f7}, {0x875f, 0x004f}, {0x8760, 0x00b7}, +{0x8761, 0x008f}, {0x8762, 0x007d}, {0x8763, 0x00b7}, +{0x8764, 0x008f}, {0x8765, 0x0081}, {0x8766, 0x00b6}, +{0x8767, 0x008f}, {0x8768, 0x0072}, {0x8769, 0x0027}, +{0x876a, 0x0047}, {0x876b, 0x007c}, {0x876c, 0x008f}, +{0x876d, 0x007d}, {0x876e, 0x00b6}, {0x876f, 0x008f}, +{0x8770, 0x0075}, {0x8771, 0x0027}, {0x8772, 0x003f}, +{0x8773, 0x007c}, {0x8774, 0x008f}, {0x8775, 0x007d}, +{0x8776, 0x00b6}, {0x8777, 0x008f}, {0x8778, 0x0078}, +{0x8779, 0x0027}, {0x877a, 0x0037}, {0x877b, 0x007c}, +{0x877c, 0x008f}, {0x877d, 0x007d}, {0x877e, 0x00b6}, +{0x877f, 0x008f}, {0x8780, 0x007b}, {0x8781, 0x0027}, +{0x8782, 0x002f}, {0x8783, 0x007f}, {0x8784, 0x008f}, +{0x8785, 0x007d}, {0x8786, 0x007c}, {0x8787, 0x008f}, +{0x8788, 0x0081}, {0x8789, 0x007a}, {0x878a, 0x008f}, +{0x878b, 0x0072}, {0x878c, 0x0027}, {0x878d, 0x001b}, +{0x878e, 0x007c}, {0x878f, 0x008f}, {0x8790, 0x007d}, +{0x8791, 0x007a}, {0x8792, 0x008f}, {0x8793, 0x0075}, +{0x8794, 0x0027}, {0x8795, 0x0016}, {0x8796, 0x007c}, +{0x8797, 0x008f}, {0x8798, 0x007d}, {0x8799, 0x007a}, +{0x879a, 0x008f}, {0x879b, 0x0078}, {0x879c, 0x0027}, +{0x879d, 0x0011}, {0x879e, 0x007c}, {0x879f, 0x008f}, +{0x87a0, 0x007d}, {0x87a1, 0x007a}, {0x87a2, 0x008f}, +{0x87a3, 0x007b}, {0x87a4, 0x0027}, {0x87a5, 0x000c}, +{0x87a6, 0x007e}, {0x87a7, 0x0087}, {0x87a8, 0x0083}, +{0x87a9, 0x007a}, {0x87aa, 0x008f}, {0x87ab, 0x0075}, +{0x87ac, 0x007a}, {0x87ad, 0x008f}, {0x87ae, 0x0078}, +{0x87af, 0x007a}, {0x87b0, 0x008f}, {0x87b1, 0x007b}, +{0x87b2, 0x00ce}, {0x87b3, 0x00c1}, {0x87b4, 0x00fc}, +{0x87b5, 0x00f6}, {0x87b6, 0x008f}, {0x87b7, 0x007d}, +{0x87b8, 0x003a}, {0x87b9, 0x00a6}, {0x87ba, 0x0000}, +{0x87bb, 0x00b7}, {0x87bc, 0x0012}, {0x87bd, 0x0070}, +{0x87be, 0x00b6}, {0x87bf, 0x008f}, {0x87c0, 0x0072}, +{0x87c1, 0x0026}, {0x87c2, 0x0003}, {0x87c3, 0x007e}, +{0x87c4, 0x0087}, {0x87c5, 0x00fa}, {0x87c6, 0x00b6}, +{0x87c7, 0x008f}, {0x87c8, 0x0075}, {0x87c9, 0x0026}, +{0x87ca, 0x000a}, {0x87cb, 0x0018}, {0x87cc, 0x00ce}, +{0x87cd, 0x008f}, {0x87ce, 0x0073}, {0x87cf, 0x00bd}, +{0x87d0, 0x0089}, {0x87d1, 0x00d5}, {0x87d2, 0x007e}, +{0x87d3, 0x0087}, {0x87d4, 0x00fa}, {0x87d5, 0x00b6}, +{0x87d6, 0x008f}, {0x87d7, 0x0078}, {0x87d8, 0x0026}, +{0x87d9, 0x000a}, {0x87da, 0x0018}, {0x87db, 0x00ce}, +{0x87dc, 0x008f}, {0x87dd, 0x0076}, {0x87de, 0x00bd}, +{0x87df, 0x0089}, {0x87e0, 0x00d5}, {0x87e1, 0x007e}, +{0x87e2, 0x0087}, {0x87e3, 0x00fa}, {0x87e4, 0x00b6}, +{0x87e5, 0x008f}, {0x87e6, 0x007b}, {0x87e7, 0x0026}, +{0x87e8, 0x000a}, {0x87e9, 0x0018}, {0x87ea, 0x00ce}, +{0x87eb, 0x008f}, {0x87ec, 0x0079}, {0x87ed, 0x00bd}, +{0x87ee, 0x0089}, {0x87ef, 0x00d5}, {0x87f0, 0x007e}, +{0x87f1, 0x0087}, {0x87f2, 0x00fa}, {0x87f3, 0x0086}, +{0x87f4, 0x0005}, {0x87f5, 0x0097}, {0x87f6, 0x0040}, +{0x87f7, 0x007e}, {0x87f8, 0x0089}, {0x87f9, 0x0000}, +{0x87fa, 0x00b6}, {0x87fb, 0x008f}, {0x87fc, 0x0075}, +{0x87fd, 0x0081}, {0x87fe, 0x0007}, {0x87ff, 0x002e}, +{0x8800, 0x00f2}, {0x8801, 0x00f6}, {0x8802, 0x0012}, +{0x8803, 0x0006}, {0x8804, 0x00c4}, {0x8805, 0x00f8}, +{0x8806, 0x001b}, {0x8807, 0x00b7}, {0x8808, 0x0012}, +{0x8809, 0x0006}, {0x880a, 0x00b6}, {0x880b, 0x008f}, +{0x880c, 0x0078}, {0x880d, 0x0081}, {0x880e, 0x0007}, +{0x880f, 0x002e}, {0x8810, 0x00e2}, {0x8811, 0x0048}, +{0x8812, 0x0048}, {0x8813, 0x0048}, {0x8814, 0x00f6}, +{0x8815, 0x0012}, {0x8816, 0x0006}, {0x8817, 0x00c4}, +{0x8818, 0x00c7}, {0x8819, 0x001b}, {0x881a, 0x00b7}, +{0x881b, 0x0012}, {0x881c, 0x0006}, {0x881d, 0x00b6}, +{0x881e, 0x008f}, {0x881f, 0x007b}, {0x8820, 0x0081}, +{0x8821, 0x0007}, {0x8822, 0x002e}, {0x8823, 0x00cf}, +{0x8824, 0x00f6}, {0x8825, 0x0012}, {0x8826, 0x0005}, +{0x8827, 0x00c4}, {0x8828, 0x00f8}, {0x8829, 0x001b}, +{0x882a, 0x00b7}, {0x882b, 0x0012}, {0x882c, 0x0005}, +{0x882d, 0x0086}, {0x882e, 0x0000}, {0x882f, 0x00f6}, +{0x8830, 0x008f}, {0x8831, 0x0071}, {0x8832, 0x00bd}, +{0x8833, 0x0089}, {0x8834, 0x0094}, {0x8835, 0x0086}, +{0x8836, 0x0001}, {0x8837, 0x00f6}, {0x8838, 0x008f}, +{0x8839, 0x0074}, {0x883a, 0x00bd}, {0x883b, 0x0089}, +{0x883c, 0x0094}, {0x883d, 0x0086}, {0x883e, 0x0002}, +{0x883f, 0x00f6}, {0x8840, 0x008f}, {0x8841, 0x0077}, +{0x8842, 0x00bd}, {0x8843, 0x0089}, {0x8844, 0x0094}, +{0x8845, 0x0086}, {0x8846, 0x0003}, {0x8847, 0x00f6}, +{0x8848, 0x008f}, {0x8849, 0x007a}, {0x884a, 0x00bd}, +{0x884b, 0x0089}, {0x884c, 0x0094}, {0x884d, 0x00ce}, +{0x884e, 0x008f}, {0x884f, 0x0070}, {0x8850, 0x00a6}, +{0x8851, 0x0001}, {0x8852, 0x0081}, {0x8853, 0x0001}, +{0x8854, 0x0027}, {0x8855, 0x0007}, {0x8856, 0x0081}, +{0x8857, 0x0003}, {0x8858, 0x0027}, {0x8859, 0x0003}, +{0x885a, 0x007e}, {0x885b, 0x0088}, {0x885c, 0x0066}, +{0x885d, 0x00a6}, {0x885e, 0x0000}, {0x885f, 0x00b8}, +{0x8860, 0x008f}, {0x8861, 0x0081}, {0x8862, 0x0084}, +{0x8863, 0x0001}, {0x8864, 0x0026}, {0x8865, 0x000b}, +{0x8866, 0x008c}, {0x8867, 0x008f}, {0x8868, 0x0079}, +{0x8869, 0x002c}, {0x886a, 0x000e}, {0x886b, 0x0008}, +{0x886c, 0x0008}, {0x886d, 0x0008}, {0x886e, 0x007e}, +{0x886f, 0x0088}, {0x8870, 0x0050}, {0x8871, 0x00b6}, +{0x8872, 0x0012}, {0x8873, 0x0004}, {0x8874, 0x008a}, +{0x8875, 0x0040}, {0x8876, 0x00b7}, {0x8877, 0x0012}, +{0x8878, 0x0004}, {0x8879, 0x00b6}, {0x887a, 0x0012}, +{0x887b, 0x0004}, {0x887c, 0x0084}, {0x887d, 0x00fb}, +{0x887e, 0x0084}, {0x887f, 0x00ef}, {0x8880, 0x00b7}, +{0x8881, 0x0012}, {0x8882, 0x0004}, {0x8883, 0x00b6}, +{0x8884, 0x0012}, {0x8885, 0x0007}, {0x8886, 0x0036}, +{0x8887, 0x00b6}, {0x8888, 0x008f}, {0x8889, 0x007c}, +{0x888a, 0x0048}, {0x888b, 0x0048}, {0x888c, 0x00b7}, +{0x888d, 0x0012}, {0x888e, 0x0007}, {0x888f, 0x0086}, +{0x8890, 0x0001}, {0x8891, 0x00ba}, {0x8892, 0x0012}, +{0x8893, 0x0004}, {0x8894, 0x00b7}, {0x8895, 0x0012}, +{0x8896, 0x0004}, {0x8897, 0x0001}, {0x8898, 0x0001}, +{0x8899, 0x0001}, {0x889a, 0x0001}, {0x889b, 0x0001}, +{0x889c, 0x0001}, {0x889d, 0x0086}, {0x889e, 0x00fe}, +{0x889f, 0x00b4}, {0x88a0, 0x0012}, {0x88a1, 0x0004}, +{0x88a2, 0x00b7}, {0x88a3, 0x0012}, {0x88a4, 0x0004}, +{0x88a5, 0x0086}, {0x88a6, 0x0002}, {0x88a7, 0x00ba}, +{0x88a8, 0x0012}, {0x88a9, 0x0004}, {0x88aa, 0x00b7}, +{0x88ab, 0x0012}, {0x88ac, 0x0004}, {0x88ad, 0x0086}, +{0x88ae, 0x00fd}, {0x88af, 0x00b4}, {0x88b0, 0x0012}, +{0x88b1, 0x0004}, {0x88b2, 0x00b7}, {0x88b3, 0x0012}, +{0x88b4, 0x0004}, {0x88b5, 0x0032}, {0x88b6, 0x00b7}, +{0x88b7, 0x0012}, {0x88b8, 0x0007}, {0x88b9, 0x00b6}, +{0x88ba, 0x0012}, {0x88bb, 0x0000}, {0x88bc, 0x0084}, +{0x88bd, 0x0008}, {0x88be, 0x0081}, {0x88bf, 0x0008}, +{0x88c0, 0x0027}, {0x88c1, 0x000f}, {0x88c2, 0x007c}, +{0x88c3, 0x0082}, {0x88c4, 0x0008}, {0x88c5, 0x0026}, +{0x88c6, 0x0007}, {0x88c7, 0x0086}, {0x88c8, 0x0076}, +{0x88c9, 0x0097}, {0x88ca, 0x0040}, {0x88cb, 0x007e}, +{0x88cc, 0x0089}, {0x88cd, 0x006e}, {0x88ce, 0x007e}, +{0x88cf, 0x0086}, {0x88d0, 0x00ec}, {0x88d1, 0x00b6}, +{0x88d2, 0x008f}, {0x88d3, 0x007f}, {0x88d4, 0x0081}, +{0x88d5, 0x000f}, {0x88d6, 0x0027}, {0x88d7, 0x003c}, +{0x88d8, 0x00bd}, {0x88d9, 0x00e6}, {0x88da, 0x00c7}, +{0x88db, 0x00b7}, {0x88dc, 0x0012}, {0x88dd, 0x000d}, +{0x88de, 0x00bd}, {0x88df, 0x00e6}, {0x88e0, 0x00cb}, +{0x88e1, 0x00b6}, {0x88e2, 0x0012}, {0x88e3, 0x0004}, +{0x88e4, 0x008a}, {0x88e5, 0x0020}, {0x88e6, 0x00b7}, +{0x88e7, 0x0012}, {0x88e8, 0x0004}, {0x88e9, 0x00ce}, +{0x88ea, 0x00ff}, {0x88eb, 0x00ff}, {0x88ec, 0x00b6}, +{0x88ed, 0x0012}, {0x88ee, 0x0000}, {0x88ef, 0x0081}, +{0x88f0, 0x000c}, {0x88f1, 0x0026}, {0x88f2, 0x0005}, +{0x88f3, 0x0009}, {0x88f4, 0x0026}, {0x88f5, 0x00f6}, +{0x88f6, 0x0027}, {0x88f7, 0x001c}, {0x88f8, 0x00b6}, +{0x88f9, 0x0012}, {0x88fa, 0x0004}, {0x88fb, 0x0084}, +{0x88fc, 0x00df}, {0x88fd, 0x00b7}, {0x88fe, 0x0012}, +{0x88ff, 0x0004}, {0x8900, 0x0096}, {0x8901, 0x0083}, +{0x8902, 0x0081}, {0x8903, 0x0007}, {0x8904, 0x002c}, +{0x8905, 0x0005}, {0x8906, 0x007c}, {0x8907, 0x0000}, +{0x8908, 0x0083}, {0x8909, 0x0020}, {0x890a, 0x0006}, +{0x890b, 0x0096}, {0x890c, 0x0083}, {0x890d, 0x008b}, +{0x890e, 0x0008}, {0x890f, 0x0097}, {0x8910, 0x0083}, +{0x8911, 0x007e}, {0x8912, 0x0085}, {0x8913, 0x0041}, +{0x8914, 0x007f}, {0x8915, 0x008f}, {0x8916, 0x007e}, +{0x8917, 0x0086}, {0x8918, 0x0080}, {0x8919, 0x00b7}, +{0x891a, 0x0012}, {0x891b, 0x000c}, {0x891c, 0x0086}, +{0x891d, 0x0001}, {0x891e, 0x00b7}, {0x891f, 0x008f}, +{0x8920, 0x007d}, {0x8921, 0x00b6}, {0x8922, 0x0012}, +{0x8923, 0x000c}, {0x8924, 0x0084}, {0x8925, 0x007f}, +{0x8926, 0x00b7}, {0x8927, 0x0012}, {0x8928, 0x000c}, +{0x8929, 0x008a}, {0x892a, 0x0080}, {0x892b, 0x00b7}, +{0x892c, 0x0012}, {0x892d, 0x000c}, {0x892e, 0x0086}, +{0x892f, 0x000a}, {0x8930, 0x00bd}, {0x8931, 0x008a}, +{0x8932, 0x0006}, {0x8933, 0x00b6}, {0x8934, 0x0012}, +{0x8935, 0x000a}, {0x8936, 0x002a}, {0x8937, 0x0009}, +{0x8938, 0x00b6}, {0x8939, 0x0012}, {0x893a, 0x000c}, +{0x893b, 0x00ba}, {0x893c, 0x008f}, {0x893d, 0x007d}, +{0x893e, 0x00b7}, {0x893f, 0x0012}, {0x8940, 0x000c}, +{0x8941, 0x00b6}, {0x8942, 0x008f}, {0x8943, 0x007e}, +{0x8944, 0x0081}, {0x8945, 0x0060}, {0x8946, 0x0027}, +{0x8947, 0x001a}, {0x8948, 0x008b}, {0x8949, 0x0020}, +{0x894a, 0x00b7}, {0x894b, 0x008f}, {0x894c, 0x007e}, +{0x894d, 0x00b6}, {0x894e, 0x0012}, {0x894f, 0x000c}, +{0x8950, 0x0084}, {0x8951, 0x009f}, {0x8952, 0x00ba}, +{0x8953, 0x008f}, {0x8954, 0x007e}, {0x8955, 0x00b7}, +{0x8956, 0x0012}, {0x8957, 0x000c}, {0x8958, 0x00b6}, +{0x8959, 0x008f}, {0x895a, 0x007d}, {0x895b, 0x0048}, +{0x895c, 0x00b7}, {0x895d, 0x008f}, {0x895e, 0x007d}, +{0x895f, 0x007e}, {0x8960, 0x0089}, {0x8961, 0x0021}, +{0x8962, 0x00b6}, {0x8963, 0x0012}, {0x8964, 0x0004}, +{0x8965, 0x008a}, {0x8966, 0x0020}, {0x8967, 0x00b7}, +{0x8968, 0x0012}, {0x8969, 0x0004}, {0x896a, 0x00bd}, +{0x896b, 0x008a}, {0x896c, 0x000a}, {0x896d, 0x004f}, +{0x896e, 0x0039}, {0x896f, 0x00a6}, {0x8970, 0x0000}, +{0x8971, 0x0018}, {0x8972, 0x00a7}, {0x8973, 0x0000}, +{0x8974, 0x0008}, {0x8975, 0x0018}, {0x8976, 0x0008}, +{0x8977, 0x005a}, {0x8978, 0x0026}, {0x8979, 0x00f5}, +{0x897a, 0x0039}, {0x897b, 0x0036}, {0x897c, 0x006c}, +{0x897d, 0x0000}, {0x897e, 0x0032}, {0x897f, 0x00ba}, +{0x8980, 0x008f}, {0x8981, 0x007f}, {0x8982, 0x00b7}, +{0x8983, 0x008f}, {0x8984, 0x007f}, {0x8985, 0x00b6}, +{0x8986, 0x0012}, {0x8987, 0x0009}, {0x8988, 0x0084}, +{0x8989, 0x0003}, {0x898a, 0x00a7}, {0x898b, 0x0001}, +{0x898c, 0x00b6}, {0x898d, 0x0012}, {0x898e, 0x0006}, +{0x898f, 0x0084}, {0x8990, 0x003f}, {0x8991, 0x00a7}, +{0x8992, 0x0002}, {0x8993, 0x0039}, {0x8994, 0x0036}, +{0x8995, 0x0086}, {0x8996, 0x0003}, {0x8997, 0x00b7}, +{0x8998, 0x008f}, {0x8999, 0x0080}, {0x899a, 0x0032}, +{0x899b, 0x00c1}, {0x899c, 0x0000}, {0x899d, 0x0026}, +{0x899e, 0x0006}, {0x899f, 0x00b7}, {0x89a0, 0x008f}, +{0x89a1, 0x007c}, {0x89a2, 0x007e}, {0x89a3, 0x0089}, +{0x89a4, 0x00c9}, {0x89a5, 0x00c1}, {0x89a6, 0x0001}, +{0x89a7, 0x0027}, {0x89a8, 0x0018}, {0x89a9, 0x00c1}, +{0x89aa, 0x0002}, {0x89ab, 0x0027}, {0x89ac, 0x000c}, +{0x89ad, 0x00c1}, {0x89ae, 0x0003}, {0x89af, 0x0027}, +{0x89b0, 0x0000}, {0x89b1, 0x00f6}, {0x89b2, 0x008f}, +{0x89b3, 0x0080}, {0x89b4, 0x0005}, {0x89b5, 0x0005}, +{0x89b6, 0x00f7}, {0x89b7, 0x008f}, {0x89b8, 0x0080}, +{0x89b9, 0x00f6}, {0x89ba, 0x008f}, {0x89bb, 0x0080}, +{0x89bc, 0x0005}, {0x89bd, 0x0005}, {0x89be, 0x00f7}, +{0x89bf, 0x008f}, {0x89c0, 0x0080}, {0x89c1, 0x00f6}, +{0x89c2, 0x008f}, {0x89c3, 0x0080}, {0x89c4, 0x0005}, +{0x89c5, 0x0005}, {0x89c6, 0x00f7}, {0x89c7, 0x008f}, +{0x89c8, 0x0080}, {0x89c9, 0x00f6}, {0x89ca, 0x008f}, +{0x89cb, 0x0080}, {0x89cc, 0x0053}, {0x89cd, 0x00f4}, +{0x89ce, 0x0012}, {0x89cf, 0x0007}, {0x89d0, 0x001b}, +{0x89d1, 0x00b7}, {0x89d2, 0x0012}, {0x89d3, 0x0007}, +{0x89d4, 0x0039}, {0x89d5, 0x00ce}, {0x89d6, 0x008f}, +{0x89d7, 0x0070}, {0x89d8, 0x00a6}, {0x89d9, 0x0000}, +{0x89da, 0x0018}, {0x89db, 0x00e6}, {0x89dc, 0x0000}, +{0x89dd, 0x0018}, {0x89de, 0x00a7}, {0x89df, 0x0000}, +{0x89e0, 0x00e7}, {0x89e1, 0x0000}, {0x89e2, 0x00a6}, +{0x89e3, 0x0001}, {0x89e4, 0x0018}, {0x89e5, 0x00e6}, +{0x89e6, 0x0001}, {0x89e7, 0x0018}, {0x89e8, 0x00a7}, +{0x89e9, 0x0001}, {0x89ea, 0x00e7}, {0x89eb, 0x0001}, +{0x89ec, 0x00a6}, {0x89ed, 0x0002}, {0x89ee, 0x0018}, +{0x89ef, 0x00e6}, {0x89f0, 0x0002}, {0x89f1, 0x0018}, +{0x89f2, 0x00a7}, {0x89f3, 0x0002}, {0x89f4, 0x00e7}, +{0x89f5, 0x0002}, {0x89f6, 0x0039}, {0x89f7, 0x00a6}, +{0x89f8, 0x0000}, {0x89f9, 0x0084}, {0x89fa, 0x0007}, +{0x89fb, 0x00e6}, {0x89fc, 0x0000}, {0x89fd, 0x00c4}, +{0x89fe, 0x0038}, {0x89ff, 0x0054}, {0x8a00, 0x0054}, +{0x8a01, 0x0054}, {0x8a02, 0x001b}, {0x8a03, 0x00a7}, +{0x8a04, 0x0000}, {0x8a05, 0x0039}, {0x8a06, 0x004a}, +{0x8a07, 0x0026}, {0x8a08, 0x00fd}, {0x8a09, 0x0039}, +{0x8a0a, 0x0096}, {0x8a0b, 0x0022}, {0x8a0c, 0x0084}, +{0x8a0d, 0x000f}, {0x8a0e, 0x0097}, {0x8a0f, 0x0022}, +{0x8a10, 0x0086}, {0x8a11, 0x0001}, {0x8a12, 0x00b7}, +{0x8a13, 0x008f}, {0x8a14, 0x0070}, {0x8a15, 0x00b6}, +{0x8a16, 0x0012}, {0x8a17, 0x0007}, {0x8a18, 0x00b7}, +{0x8a19, 0x008f}, {0x8a1a, 0x0071}, {0x8a1b, 0x00f6}, +{0x8a1c, 0x0012}, {0x8a1d, 0x000c}, {0x8a1e, 0x00c4}, +{0x8a1f, 0x000f}, {0x8a20, 0x00c8}, {0x8a21, 0x000f}, +{0x8a22, 0x00f7}, {0x8a23, 0x008f}, {0x8a24, 0x0072}, +{0x8a25, 0x00f6}, {0x8a26, 0x008f}, {0x8a27, 0x0072}, +{0x8a28, 0x00b6}, {0x8a29, 0x008f}, {0x8a2a, 0x0071}, +{0x8a2b, 0x0084}, {0x8a2c, 0x0003}, {0x8a2d, 0x0027}, +{0x8a2e, 0x0014}, {0x8a2f, 0x0081}, {0x8a30, 0x0001}, +{0x8a31, 0x0027}, {0x8a32, 0x001c}, {0x8a33, 0x0081}, +{0x8a34, 0x0002}, {0x8a35, 0x0027}, {0x8a36, 0x0024}, +{0x8a37, 0x00f4}, {0x8a38, 0x008f}, {0x8a39, 0x0070}, +{0x8a3a, 0x0027}, {0x8a3b, 0x002a}, {0x8a3c, 0x0096}, +{0x8a3d, 0x0022}, {0x8a3e, 0x008a}, {0x8a3f, 0x0080}, +{0x8a40, 0x007e}, {0x8a41, 0x008a}, {0x8a42, 0x0064}, +{0x8a43, 0x00f4}, {0x8a44, 0x008f}, {0x8a45, 0x0070}, +{0x8a46, 0x0027}, {0x8a47, 0x001e}, {0x8a48, 0x0096}, +{0x8a49, 0x0022}, {0x8a4a, 0x008a}, {0x8a4b, 0x0010}, +{0x8a4c, 0x007e}, {0x8a4d, 0x008a}, {0x8a4e, 0x0064}, +{0x8a4f, 0x00f4}, {0x8a50, 0x008f}, {0x8a51, 0x0070}, +{0x8a52, 0x0027}, {0x8a53, 0x0012}, {0x8a54, 0x0096}, +{0x8a55, 0x0022}, {0x8a56, 0x008a}, {0x8a57, 0x0020}, +{0x8a58, 0x007e}, {0x8a59, 0x008a}, {0x8a5a, 0x0064}, +{0x8a5b, 0x00f4}, {0x8a5c, 0x008f}, {0x8a5d, 0x0070}, +{0x8a5e, 0x0027}, {0x8a5f, 0x0006}, {0x8a60, 0x0096}, +{0x8a61, 0x0022}, {0x8a62, 0x008a}, {0x8a63, 0x0040}, +{0x8a64, 0x0097}, {0x8a65, 0x0022}, {0x8a66, 0x0074}, +{0x8a67, 0x008f}, {0x8a68, 0x0071}, {0x8a69, 0x0074}, +{0x8a6a, 0x008f}, {0x8a6b, 0x0071}, {0x8a6c, 0x0078}, +{0x8a6d, 0x008f}, {0x8a6e, 0x0070}, {0x8a6f, 0x00b6}, +{0x8a70, 0x008f}, {0x8a71, 0x0070}, {0x8a72, 0x0085}, +{0x8a73, 0x0010}, {0x8a74, 0x0027}, {0x8a75, 0x00af}, +{0x8a76, 0x00d6}, {0x8a77, 0x0022}, {0x8a78, 0x00c4}, +{0x8a79, 0x0010}, {0x8a7a, 0x0058}, {0x8a7b, 0x00b6}, +{0x8a7c, 0x0012}, {0x8a7d, 0x0070}, {0x8a7e, 0x0081}, +{0x8a7f, 0x00e4}, {0x8a80, 0x0027}, {0x8a81, 0x0036}, +{0x8a82, 0x0081}, {0x8a83, 0x00e1}, {0x8a84, 0x0026}, +{0x8a85, 0x000c}, {0x8a86, 0x0096}, {0x8a87, 0x0022}, +{0x8a88, 0x0084}, {0x8a89, 0x0020}, {0x8a8a, 0x0044}, +{0x8a8b, 0x001b}, {0x8a8c, 0x00d6}, {0x8a8d, 0x0022}, +{0x8a8e, 0x00c4}, {0x8a8f, 0x00cf}, {0x8a90, 0x0020}, +{0x8a91, 0x0023}, {0x8a92, 0x0058}, {0x8a93, 0x0081}, +{0x8a94, 0x00c6}, {0x8a95, 0x0026}, {0x8a96, 0x000d}, +{0x8a97, 0x0096}, {0x8a98, 0x0022}, {0x8a99, 0x0084}, +{0x8a9a, 0x0040}, {0x8a9b, 0x0044}, {0x8a9c, 0x0044}, +{0x8a9d, 0x001b}, {0x8a9e, 0x00d6}, {0x8a9f, 0x0022}, +{0x8aa0, 0x00c4}, {0x8aa1, 0x00af}, {0x8aa2, 0x0020}, +{0x8aa3, 0x0011}, {0x8aa4, 0x0058}, {0x8aa5, 0x0081}, +{0x8aa6, 0x0027}, {0x8aa7, 0x0026}, {0x8aa8, 0x000f}, +{0x8aa9, 0x0096}, {0x8aaa, 0x0022}, {0x8aab, 0x0084}, +{0x8aac, 0x0080}, {0x8aad, 0x0044}, {0x8aae, 0x0044}, +{0x8aaf, 0x0044}, {0x8ab0, 0x001b}, {0x8ab1, 0x00d6}, +{0x8ab2, 0x0022}, {0x8ab3, 0x00c4}, {0x8ab4, 0x006f}, +{0x8ab5, 0x001b}, {0x8ab6, 0x0097}, {0x8ab7, 0x0022}, +{0x8ab8, 0x0039}, {0x8ab9, 0x0027}, {0x8aba, 0x000c}, +{0x8abb, 0x007c}, {0x8abc, 0x0082}, {0x8abd, 0x0006}, +{0x8abe, 0x00bd}, {0x8abf, 0x00d9}, {0x8ac0, 0x00ed}, +{0x8ac1, 0x00b6}, {0x8ac2, 0x0082}, {0x8ac3, 0x0007}, +{0x8ac4, 0x007e}, {0x8ac5, 0x008a}, {0x8ac6, 0x00b9}, +{0x8ac7, 0x007f}, {0x8ac8, 0x0082}, {0x8ac9, 0x0006}, +{0x8aca, 0x0039}, { 0x0, 0x0 } +}; +#else +cas_saturn_patch_t cas_saturn_patch[] = { +{0x8200, 0x007e}, {0x8201, 0x0082}, {0x8202, 0x0009}, +{0x8203, 0x0000}, {0x8204, 0x0000}, {0x8205, 0x0000}, +{0x8206, 0x0000}, {0x8207, 0x0000}, {0x8208, 0x0000}, +{0x8209, 0x008e}, {0x820a, 0x008e}, {0x820b, 0x00ff}, +{0x820c, 0x00ce}, {0x820d, 0x0082}, {0x820e, 0x0025}, +{0x820f, 0x00ff}, {0x8210, 0x0001}, {0x8211, 0x000f}, +{0x8212, 0x00ce}, {0x8213, 0x0084}, {0x8214, 0x0026}, +{0x8215, 0x00ff}, {0x8216, 0x0001}, {0x8217, 0x0011}, +{0x8218, 0x00ce}, {0x8219, 0x0085}, {0x821a, 0x003d}, +{0x821b, 0x00df}, {0x821c, 0x00e5}, {0x821d, 0x0086}, +{0x821e, 0x0039}, {0x821f, 0x00b7}, {0x8220, 0x008f}, +{0x8221, 0x00f8}, {0x8222, 0x007e}, {0x8223, 0x00c3}, +{0x8224, 0x00c2}, {0x8225, 0x0096}, {0x8226, 0x0047}, +{0x8227, 0x0084}, {0x8228, 0x00f3}, {0x8229, 0x008a}, +{0x822a, 0x0000}, {0x822b, 0x0097}, {0x822c, 0x0047}, +{0x822d, 0x00ce}, {0x822e, 0x0082}, {0x822f, 0x0033}, +{0x8230, 0x00ff}, {0x8231, 0x0001}, {0x8232, 0x000f}, +{0x8233, 0x0096}, {0x8234, 0x0046}, {0x8235, 0x0084}, +{0x8236, 0x000c}, {0x8237, 0x0081}, {0x8238, 0x0004}, +{0x8239, 0x0027}, {0x823a, 0x000b}, {0x823b, 0x0096}, +{0x823c, 0x0046}, {0x823d, 0x0084}, {0x823e, 0x000c}, +{0x823f, 0x0081}, {0x8240, 0x0008}, {0x8241, 0x0027}, +{0x8242, 0x0057}, {0x8243, 0x007e}, {0x8244, 0x0084}, +{0x8245, 0x0025}, {0x8246, 0x0096}, {0x8247, 0x0047}, +{0x8248, 0x0084}, {0x8249, 0x00f3}, {0x824a, 0x008a}, +{0x824b, 0x0004}, {0x824c, 0x0097}, {0x824d, 0x0047}, +{0x824e, 0x00ce}, {0x824f, 0x0082}, {0x8250, 0x0054}, +{0x8251, 0x00ff}, {0x8252, 0x0001}, {0x8253, 0x000f}, +{0x8254, 0x0096}, {0x8255, 0x0046}, {0x8256, 0x0084}, +{0x8257, 0x000c}, {0x8258, 0x0081}, {0x8259, 0x0004}, +{0x825a, 0x0026}, {0x825b, 0x0038}, {0x825c, 0x00b6}, +{0x825d, 0x0012}, {0x825e, 0x0020}, {0x825f, 0x0084}, +{0x8260, 0x0020}, {0x8261, 0x0026}, {0x8262, 0x0003}, +{0x8263, 0x007e}, {0x8264, 0x0084}, {0x8265, 0x0025}, +{0x8266, 0x0096}, {0x8267, 0x007b}, {0x8268, 0x00d6}, +{0x8269, 0x007c}, {0x826a, 0x00fe}, {0x826b, 0x008f}, +{0x826c, 0x0056}, {0x826d, 0x00bd}, {0x826e, 0x00f7}, +{0x826f, 0x00b6}, {0x8270, 0x00fe}, {0x8271, 0x008f}, +{0x8272, 0x004e}, {0x8273, 0x00bd}, {0x8274, 0x00ec}, +{0x8275, 0x008e}, {0x8276, 0x00bd}, {0x8277, 0x00fa}, +{0x8278, 0x00f7}, {0x8279, 0x00bd}, {0x827a, 0x00f7}, +{0x827b, 0x0028}, {0x827c, 0x00ce}, {0x827d, 0x0082}, +{0x827e, 0x0082}, {0x827f, 0x00ff}, {0x8280, 0x0001}, +{0x8281, 0x000f}, {0x8282, 0x0096}, {0x8283, 0x0046}, +{0x8284, 0x0084}, {0x8285, 0x000c}, {0x8286, 0x0081}, +{0x8287, 0x0004}, {0x8288, 0x0026}, {0x8289, 0x000a}, +{0x828a, 0x00b6}, {0x828b, 0x0012}, {0x828c, 0x0020}, +{0x828d, 0x0084}, {0x828e, 0x0020}, {0x828f, 0x0027}, +{0x8290, 0x00b5}, {0x8291, 0x007e}, {0x8292, 0x0084}, +{0x8293, 0x0025}, {0x8294, 0x00bd}, {0x8295, 0x00f7}, +{0x8296, 0x001f}, {0x8297, 0x007e}, {0x8298, 0x0084}, +{0x8299, 0x001f}, {0x829a, 0x0096}, {0x829b, 0x0047}, +{0x829c, 0x0084}, {0x829d, 0x00f3}, {0x829e, 0x008a}, +{0x829f, 0x0008}, {0x82a0, 0x0097}, {0x82a1, 0x0047}, +{0x82a2, 0x00de}, {0x82a3, 0x00e1}, {0x82a4, 0x00ad}, +{0x82a5, 0x0000}, {0x82a6, 0x00ce}, {0x82a7, 0x0082}, +{0x82a8, 0x00af}, {0x82a9, 0x00ff}, {0x82aa, 0x0001}, +{0x82ab, 0x000f}, {0x82ac, 0x007e}, {0x82ad, 0x0084}, +{0x82ae, 0x0025}, {0x82af, 0x0096}, {0x82b0, 0x0041}, +{0x82b1, 0x0085}, {0x82b2, 0x0010}, {0x82b3, 0x0026}, +{0x82b4, 0x0006}, {0x82b5, 0x0096}, {0x82b6, 0x0023}, +{0x82b7, 0x0085}, {0x82b8, 0x0040}, {0x82b9, 0x0027}, +{0x82ba, 0x0006}, {0x82bb, 0x00bd}, {0x82bc, 0x00ed}, +{0x82bd, 0x0000}, {0x82be, 0x007e}, {0x82bf, 0x0083}, +{0x82c0, 0x00a2}, {0x82c1, 0x00de}, {0x82c2, 0x0042}, +{0x82c3, 0x00bd}, {0x82c4, 0x00eb}, {0x82c5, 0x008e}, +{0x82c6, 0x0096}, {0x82c7, 0x0024}, {0x82c8, 0x0084}, +{0x82c9, 0x0008}, {0x82ca, 0x0027}, {0x82cb, 0x0003}, +{0x82cc, 0x007e}, {0x82cd, 0x0083}, {0x82ce, 0x00df}, +{0x82cf, 0x0096}, {0x82d0, 0x007b}, {0x82d1, 0x00d6}, +{0x82d2, 0x007c}, {0x82d3, 0x00fe}, {0x82d4, 0x008f}, +{0x82d5, 0x0056}, {0x82d6, 0x00bd}, {0x82d7, 0x00f7}, +{0x82d8, 0x00b6}, {0x82d9, 0x00fe}, {0x82da, 0x008f}, +{0x82db, 0x0050}, {0x82dc, 0x00bd}, {0x82dd, 0x00ec}, +{0x82de, 0x008e}, {0x82df, 0x00bd}, {0x82e0, 0x00fa}, +{0x82e1, 0x00f7}, {0x82e2, 0x0086}, {0x82e3, 0x0011}, +{0x82e4, 0x00c6}, {0x82e5, 0x0049}, {0x82e6, 0x00bd}, +{0x82e7, 0x00e4}, {0x82e8, 0x0012}, {0x82e9, 0x00ce}, +{0x82ea, 0x0082}, {0x82eb, 0x00ef}, {0x82ec, 0x00ff}, +{0x82ed, 0x0001}, {0x82ee, 0x000f}, {0x82ef, 0x0096}, +{0x82f0, 0x0046}, {0x82f1, 0x0084}, {0x82f2, 0x000c}, +{0x82f3, 0x0081}, {0x82f4, 0x0000}, {0x82f5, 0x0027}, +{0x82f6, 0x0017}, {0x82f7, 0x00c6}, {0x82f8, 0x0049}, +{0x82f9, 0x00bd}, {0x82fa, 0x00e4}, {0x82fb, 0x0091}, +{0x82fc, 0x0024}, {0x82fd, 0x000d}, {0x82fe, 0x00b6}, +{0x82ff, 0x0012}, {0x8300, 0x0020}, {0x8301, 0x0085}, +{0x8302, 0x0020}, {0x8303, 0x0026}, {0x8304, 0x000c}, +{0x8305, 0x00ce}, {0x8306, 0x0082}, {0x8307, 0x00c1}, +{0x8308, 0x00ff}, {0x8309, 0x0001}, {0x830a, 0x000f}, +{0x830b, 0x007e}, {0x830c, 0x0084}, {0x830d, 0x0025}, +{0x830e, 0x007e}, {0x830f, 0x0084}, {0x8310, 0x0016}, +{0x8311, 0x00fe}, {0x8312, 0x008f}, {0x8313, 0x0052}, +{0x8314, 0x00bd}, {0x8315, 0x00ec}, {0x8316, 0x008e}, +{0x8317, 0x00bd}, {0x8318, 0x00fa}, {0x8319, 0x00f7}, +{0x831a, 0x0086}, {0x831b, 0x006a}, {0x831c, 0x00c6}, +{0x831d, 0x0049}, {0x831e, 0x00bd}, {0x831f, 0x00e4}, +{0x8320, 0x0012}, {0x8321, 0x00ce}, {0x8322, 0x0083}, +{0x8323, 0x0027}, {0x8324, 0x00ff}, {0x8325, 0x0001}, +{0x8326, 0x000f}, {0x8327, 0x0096}, {0x8328, 0x0046}, +{0x8329, 0x0084}, {0x832a, 0x000c}, {0x832b, 0x0081}, +{0x832c, 0x0000}, {0x832d, 0x0027}, {0x832e, 0x000a}, +{0x832f, 0x00c6}, {0x8330, 0x0049}, {0x8331, 0x00bd}, +{0x8332, 0x00e4}, {0x8333, 0x0091}, {0x8334, 0x0025}, +{0x8335, 0x0006}, {0x8336, 0x007e}, {0x8337, 0x0084}, +{0x8338, 0x0025}, {0x8339, 0x007e}, {0x833a, 0x0084}, +{0x833b, 0x0016}, {0x833c, 0x00b6}, {0x833d, 0x0018}, +{0x833e, 0x0070}, {0x833f, 0x00bb}, {0x8340, 0x0019}, +{0x8341, 0x0070}, {0x8342, 0x002a}, {0x8343, 0x0004}, +{0x8344, 0x0081}, {0x8345, 0x00af}, {0x8346, 0x002e}, +{0x8347, 0x0019}, {0x8348, 0x0096}, {0x8349, 0x007b}, +{0x834a, 0x00f6}, {0x834b, 0x0020}, {0x834c, 0x0007}, +{0x834d, 0x00fa}, {0x834e, 0x0020}, {0x834f, 0x0027}, +{0x8350, 0x00c4}, {0x8351, 0x0038}, {0x8352, 0x0081}, +{0x8353, 0x0038}, {0x8354, 0x0027}, {0x8355, 0x000b}, +{0x8356, 0x00f6}, {0x8357, 0x0020}, {0x8358, 0x0007}, +{0x8359, 0x00fa}, {0x835a, 0x0020}, {0x835b, 0x0027}, +{0x835c, 0x00cb}, {0x835d, 0x0008}, {0x835e, 0x007e}, +{0x835f, 0x0082}, {0x8360, 0x00d3}, {0x8361, 0x00bd}, +{0x8362, 0x00f7}, {0x8363, 0x0066}, {0x8364, 0x0086}, +{0x8365, 0x0074}, {0x8366, 0x00c6}, {0x8367, 0x0049}, +{0x8368, 0x00bd}, {0x8369, 0x00e4}, {0x836a, 0x0012}, +{0x836b, 0x00ce}, {0x836c, 0x0083}, {0x836d, 0x0071}, +{0x836e, 0x00ff}, {0x836f, 0x0001}, {0x8370, 0x000f}, +{0x8371, 0x0096}, {0x8372, 0x0046}, {0x8373, 0x0084}, +{0x8374, 0x000c}, {0x8375, 0x0081}, {0x8376, 0x0008}, +{0x8377, 0x0026}, {0x8378, 0x000a}, {0x8379, 0x00c6}, +{0x837a, 0x0049}, {0x837b, 0x00bd}, {0x837c, 0x00e4}, +{0x837d, 0x0091}, {0x837e, 0x0025}, {0x837f, 0x0006}, +{0x8380, 0x007e}, {0x8381, 0x0084}, {0x8382, 0x0025}, +{0x8383, 0x007e}, {0x8384, 0x0084}, {0x8385, 0x0016}, +{0x8386, 0x00bd}, {0x8387, 0x00f7}, {0x8388, 0x003e}, +{0x8389, 0x0026}, {0x838a, 0x000e}, {0x838b, 0x00bd}, +{0x838c, 0x00e5}, {0x838d, 0x0009}, {0x838e, 0x0026}, +{0x838f, 0x0006}, {0x8390, 0x00ce}, {0x8391, 0x0082}, +{0x8392, 0x00c1}, {0x8393, 0x00ff}, {0x8394, 0x0001}, +{0x8395, 0x000f}, {0x8396, 0x007e}, {0x8397, 0x0084}, +{0x8398, 0x0025}, {0x8399, 0x00fe}, {0x839a, 0x008f}, +{0x839b, 0x0054}, {0x839c, 0x00bd}, {0x839d, 0x00ec}, +{0x839e, 0x008e}, {0x839f, 0x00bd}, {0x83a0, 0x00fa}, +{0x83a1, 0x00f7}, {0x83a2, 0x00bd}, {0x83a3, 0x00f7}, +{0x83a4, 0x0033}, {0x83a5, 0x0086}, {0x83a6, 0x000f}, +{0x83a7, 0x00c6}, {0x83a8, 0x0051}, {0x83a9, 0x00bd}, +{0x83aa, 0x00e4}, {0x83ab, 0x0012}, {0x83ac, 0x00ce}, +{0x83ad, 0x0083}, {0x83ae, 0x00b2}, {0x83af, 0x00ff}, +{0x83b0, 0x0001}, {0x83b1, 0x000f}, {0x83b2, 0x0096}, +{0x83b3, 0x0046}, {0x83b4, 0x0084}, {0x83b5, 0x000c}, +{0x83b6, 0x0081}, {0x83b7, 0x0008}, {0x83b8, 0x0026}, +{0x83b9, 0x005c}, {0x83ba, 0x00b6}, {0x83bb, 0x0012}, +{0x83bc, 0x0020}, {0x83bd, 0x0084}, {0x83be, 0x003f}, +{0x83bf, 0x0081}, {0x83c0, 0x003a}, {0x83c1, 0x0027}, +{0x83c2, 0x001c}, {0x83c3, 0x0096}, {0x83c4, 0x0023}, +{0x83c5, 0x0085}, {0x83c6, 0x0040}, {0x83c7, 0x0027}, +{0x83c8, 0x0003}, {0x83c9, 0x007e}, {0x83ca, 0x0084}, +{0x83cb, 0x0025}, {0x83cc, 0x00c6}, {0x83cd, 0x0051}, +{0x83ce, 0x00bd}, {0x83cf, 0x00e4}, {0x83d0, 0x0091}, +{0x83d1, 0x0025}, {0x83d2, 0x0003}, {0x83d3, 0x007e}, +{0x83d4, 0x0084}, {0x83d5, 0x0025}, {0x83d6, 0x00ce}, +{0x83d7, 0x0082}, {0x83d8, 0x00c1}, {0x83d9, 0x00ff}, +{0x83da, 0x0001}, {0x83db, 0x000f}, {0x83dc, 0x007e}, +{0x83dd, 0x0084}, {0x83de, 0x0025}, {0x83df, 0x00bd}, +{0x83e0, 0x00f8}, {0x83e1, 0x0037}, {0x83e2, 0x007c}, +{0x83e3, 0x0000}, {0x83e4, 0x007a}, {0x83e5, 0x00ce}, +{0x83e6, 0x0083}, {0x83e7, 0x00ee}, {0x83e8, 0x00ff}, +{0x83e9, 0x0001}, {0x83ea, 0x000f}, {0x83eb, 0x007e}, +{0x83ec, 0x0084}, {0x83ed, 0x0025}, {0x83ee, 0x0096}, +{0x83ef, 0x0046}, {0x83f0, 0x0084}, {0x83f1, 0x000c}, +{0x83f2, 0x0081}, {0x83f3, 0x0008}, {0x83f4, 0x0026}, +{0x83f5, 0x0020}, {0x83f6, 0x0096}, {0x83f7, 0x0024}, +{0x83f8, 0x0084}, {0x83f9, 0x0008}, {0x83fa, 0x0026}, +{0x83fb, 0x0029}, {0x83fc, 0x00b6}, {0x83fd, 0x0018}, +{0x83fe, 0x0082}, {0x83ff, 0x00bb}, {0x8400, 0x0019}, +{0x8401, 0x0082}, {0x8402, 0x00b1}, {0x8403, 0x0001}, +{0x8404, 0x003b}, {0x8405, 0x0022}, {0x8406, 0x0009}, +{0x8407, 0x00b6}, {0x8408, 0x0012}, {0x8409, 0x0020}, +{0x840a, 0x0084}, {0x840b, 0x0037}, {0x840c, 0x0081}, +{0x840d, 0x0032}, {0x840e, 0x0027}, {0x840f, 0x0015}, +{0x8410, 0x00bd}, {0x8411, 0x00f8}, {0x8412, 0x0044}, +{0x8413, 0x007e}, {0x8414, 0x0082}, {0x8415, 0x00c1}, +{0x8416, 0x00bd}, {0x8417, 0x00f7}, {0x8418, 0x001f}, +{0x8419, 0x00bd}, {0x841a, 0x00f8}, {0x841b, 0x0044}, +{0x841c, 0x00bd}, {0x841d, 0x00fc}, {0x841e, 0x0029}, +{0x841f, 0x00ce}, {0x8420, 0x0082}, {0x8421, 0x0025}, +{0x8422, 0x00ff}, {0x8423, 0x0001}, {0x8424, 0x000f}, +{0x8425, 0x0039}, {0x8426, 0x0096}, {0x8427, 0x0047}, +{0x8428, 0x0084}, {0x8429, 0x00fc}, {0x842a, 0x008a}, +{0x842b, 0x0000}, {0x842c, 0x0097}, {0x842d, 0x0047}, +{0x842e, 0x00ce}, {0x842f, 0x0084}, {0x8430, 0x0034}, +{0x8431, 0x00ff}, {0x8432, 0x0001}, {0x8433, 0x0011}, +{0x8434, 0x0096}, {0x8435, 0x0046}, {0x8436, 0x0084}, +{0x8437, 0x0003}, {0x8438, 0x0081}, {0x8439, 0x0002}, +{0x843a, 0x0027}, {0x843b, 0x0003}, {0x843c, 0x007e}, +{0x843d, 0x0085}, {0x843e, 0x001e}, {0x843f, 0x0096}, +{0x8440, 0x0047}, {0x8441, 0x0084}, {0x8442, 0x00fc}, +{0x8443, 0x008a}, {0x8444, 0x0002}, {0x8445, 0x0097}, +{0x8446, 0x0047}, {0x8447, 0x00de}, {0x8448, 0x00e1}, +{0x8449, 0x00ad}, {0x844a, 0x0000}, {0x844b, 0x0086}, +{0x844c, 0x0001}, {0x844d, 0x00b7}, {0x844e, 0x0012}, +{0x844f, 0x0051}, {0x8450, 0x00bd}, {0x8451, 0x00f7}, +{0x8452, 0x0014}, {0x8453, 0x00b6}, {0x8454, 0x0010}, +{0x8455, 0x0031}, {0x8456, 0x0084}, {0x8457, 0x00fd}, +{0x8458, 0x00b7}, {0x8459, 0x0010}, {0x845a, 0x0031}, +{0x845b, 0x00bd}, {0x845c, 0x00f8}, {0x845d, 0x001e}, +{0x845e, 0x0096}, {0x845f, 0x0081}, {0x8460, 0x00d6}, +{0x8461, 0x0082}, {0x8462, 0x00fe}, {0x8463, 0x008f}, +{0x8464, 0x005a}, {0x8465, 0x00bd}, {0x8466, 0x00f7}, +{0x8467, 0x00b6}, {0x8468, 0x00fe}, {0x8469, 0x008f}, +{0x846a, 0x005c}, {0x846b, 0x00bd}, {0x846c, 0x00ec}, +{0x846d, 0x008e}, {0x846e, 0x00bd}, {0x846f, 0x00fa}, +{0x8470, 0x00f7}, {0x8471, 0x0086}, {0x8472, 0x0008}, +{0x8473, 0x00d6}, {0x8474, 0x0000}, {0x8475, 0x00c5}, +{0x8476, 0x0010}, {0x8477, 0x0026}, {0x8478, 0x0002}, +{0x8479, 0x008b}, {0x847a, 0x0020}, {0x847b, 0x00c6}, +{0x847c, 0x0051}, {0x847d, 0x00bd}, {0x847e, 0x00e4}, +{0x847f, 0x0012}, {0x8480, 0x00ce}, {0x8481, 0x0084}, +{0x8482, 0x0086}, {0x8483, 0x00ff}, {0x8484, 0x0001}, +{0x8485, 0x0011}, {0x8486, 0x0096}, {0x8487, 0x0046}, +{0x8488, 0x0084}, {0x8489, 0x0003}, {0x848a, 0x0081}, +{0x848b, 0x0002}, {0x848c, 0x0027}, {0x848d, 0x0003}, +{0x848e, 0x007e}, {0x848f, 0x0085}, {0x8490, 0x000f}, +{0x8491, 0x00c6}, {0x8492, 0x0051}, {0x8493, 0x00bd}, +{0x8494, 0x00e4}, {0x8495, 0x0091}, {0x8496, 0x0025}, +{0x8497, 0x0003}, {0x8498, 0x007e}, {0x8499, 0x0085}, +{0x849a, 0x001e}, {0x849b, 0x0096}, {0x849c, 0x0044}, +{0x849d, 0x0085}, {0x849e, 0x0010}, {0x849f, 0x0026}, +{0x84a0, 0x000a}, {0x84a1, 0x00b6}, {0x84a2, 0x0012}, +{0x84a3, 0x0050}, {0x84a4, 0x00ba}, {0x84a5, 0x0001}, +{0x84a6, 0x003c}, {0x84a7, 0x0085}, {0x84a8, 0x0010}, +{0x84a9, 0x0027}, {0x84aa, 0x00a8}, {0x84ab, 0x00bd}, +{0x84ac, 0x00f7}, {0x84ad, 0x0066}, {0x84ae, 0x00ce}, +{0x84af, 0x0084}, {0x84b0, 0x00b7}, {0x84b1, 0x00ff}, +{0x84b2, 0x0001}, {0x84b3, 0x0011}, {0x84b4, 0x007e}, +{0x84b5, 0x0085}, {0x84b6, 0x001e}, {0x84b7, 0x0096}, +{0x84b8, 0x0046}, {0x84b9, 0x0084}, {0x84ba, 0x0003}, +{0x84bb, 0x0081}, {0x84bc, 0x0002}, {0x84bd, 0x0026}, +{0x84be, 0x0050}, {0x84bf, 0x00b6}, {0x84c0, 0x0012}, +{0x84c1, 0x0030}, {0x84c2, 0x0084}, {0x84c3, 0x0003}, +{0x84c4, 0x0081}, {0x84c5, 0x0001}, {0x84c6, 0x0027}, +{0x84c7, 0x0003}, {0x84c8, 0x007e}, {0x84c9, 0x0085}, +{0x84ca, 0x001e}, {0x84cb, 0x0096}, {0x84cc, 0x0044}, +{0x84cd, 0x0085}, {0x84ce, 0x0010}, {0x84cf, 0x0026}, +{0x84d0, 0x0013}, {0x84d1, 0x00b6}, {0x84d2, 0x0012}, +{0x84d3, 0x0050}, {0x84d4, 0x00ba}, {0x84d5, 0x0001}, +{0x84d6, 0x003c}, {0x84d7, 0x0085}, {0x84d8, 0x0010}, +{0x84d9, 0x0026}, {0x84da, 0x0009}, {0x84db, 0x00ce}, +{0x84dc, 0x0084}, {0x84dd, 0x0053}, {0x84de, 0x00ff}, +{0x84df, 0x0001}, {0x84e0, 0x0011}, {0x84e1, 0x007e}, +{0x84e2, 0x0085}, {0x84e3, 0x001e}, {0x84e4, 0x00b6}, +{0x84e5, 0x0010}, {0x84e6, 0x0031}, {0x84e7, 0x008a}, +{0x84e8, 0x0002}, {0x84e9, 0x00b7}, {0x84ea, 0x0010}, +{0x84eb, 0x0031}, {0x84ec, 0x00bd}, {0x84ed, 0x0085}, +{0x84ee, 0x001f}, {0x84ef, 0x00bd}, {0x84f0, 0x00f8}, +{0x84f1, 0x0037}, {0x84f2, 0x007c}, {0x84f3, 0x0000}, +{0x84f4, 0x0080}, {0x84f5, 0x00ce}, {0x84f6, 0x0084}, +{0x84f7, 0x00fe}, {0x84f8, 0x00ff}, {0x84f9, 0x0001}, +{0x84fa, 0x0011}, {0x84fb, 0x007e}, {0x84fc, 0x0085}, +{0x84fd, 0x001e}, {0x84fe, 0x0096}, {0x84ff, 0x0046}, +{0x8500, 0x0084}, {0x8501, 0x0003}, {0x8502, 0x0081}, +{0x8503, 0x0002}, {0x8504, 0x0026}, {0x8505, 0x0009}, +{0x8506, 0x00b6}, {0x8507, 0x0012}, {0x8508, 0x0030}, +{0x8509, 0x0084}, {0x850a, 0x0003}, {0x850b, 0x0081}, +{0x850c, 0x0001}, {0x850d, 0x0027}, {0x850e, 0x000f}, +{0x850f, 0x00bd}, {0x8510, 0x00f8}, {0x8511, 0x0044}, +{0x8512, 0x00bd}, {0x8513, 0x00f7}, {0x8514, 0x000b}, +{0x8515, 0x00bd}, {0x8516, 0x00fc}, {0x8517, 0x0029}, +{0x8518, 0x00ce}, {0x8519, 0x0084}, {0x851a, 0x0026}, +{0x851b, 0x00ff}, {0x851c, 0x0001}, {0x851d, 0x0011}, +{0x851e, 0x0039}, {0x851f, 0x00d6}, {0x8520, 0x0022}, +{0x8521, 0x00c4}, {0x8522, 0x000f}, {0x8523, 0x00b6}, +{0x8524, 0x0012}, {0x8525, 0x0030}, {0x8526, 0x00ba}, +{0x8527, 0x0012}, {0x8528, 0x0032}, {0x8529, 0x0084}, +{0x852a, 0x0004}, {0x852b, 0x0027}, {0x852c, 0x000d}, +{0x852d, 0x0096}, {0x852e, 0x0022}, {0x852f, 0x0085}, +{0x8530, 0x0004}, {0x8531, 0x0027}, {0x8532, 0x0005}, +{0x8533, 0x00ca}, {0x8534, 0x0010}, {0x8535, 0x007e}, +{0x8536, 0x0085}, {0x8537, 0x003a}, {0x8538, 0x00ca}, +{0x8539, 0x0020}, {0x853a, 0x00d7}, {0x853b, 0x0022}, +{0x853c, 0x0039}, {0x853d, 0x0086}, {0x853e, 0x0000}, +{0x853f, 0x0097}, {0x8540, 0x0083}, {0x8541, 0x0018}, +{0x8542, 0x00ce}, {0x8543, 0x001c}, {0x8544, 0x0000}, +{0x8545, 0x00bd}, {0x8546, 0x00eb}, {0x8547, 0x0046}, +{0x8548, 0x0096}, {0x8549, 0x0057}, {0x854a, 0x0085}, +{0x854b, 0x0001}, {0x854c, 0x0027}, {0x854d, 0x0002}, +{0x854e, 0x004f}, {0x854f, 0x0039}, {0x8550, 0x0085}, +{0x8551, 0x0002}, {0x8552, 0x0027}, {0x8553, 0x0001}, +{0x8554, 0x0039}, {0x8555, 0x007f}, {0x8556, 0x008f}, +{0x8557, 0x007d}, {0x8558, 0x0086}, {0x8559, 0x0004}, +{0x855a, 0x00b7}, {0x855b, 0x0012}, {0x855c, 0x0004}, +{0x855d, 0x0086}, {0x855e, 0x0008}, {0x855f, 0x00b7}, +{0x8560, 0x0012}, {0x8561, 0x0007}, {0x8562, 0x0086}, +{0x8563, 0x0010}, {0x8564, 0x00b7}, {0x8565, 0x0012}, +{0x8566, 0x000c}, {0x8567, 0x0086}, {0x8568, 0x0007}, +{0x8569, 0x00b7}, {0x856a, 0x0012}, {0x856b, 0x0006}, +{0x856c, 0x00b6}, {0x856d, 0x008f}, {0x856e, 0x007d}, +{0x856f, 0x00b7}, {0x8570, 0x0012}, {0x8571, 0x0070}, +{0x8572, 0x0086}, {0x8573, 0x0001}, {0x8574, 0x00ba}, +{0x8575, 0x0012}, {0x8576, 0x0004}, {0x8577, 0x00b7}, +{0x8578, 0x0012}, {0x8579, 0x0004}, {0x857a, 0x0001}, +{0x857b, 0x0001}, {0x857c, 0x0001}, {0x857d, 0x0001}, +{0x857e, 0x0001}, {0x857f, 0x0001}, {0x8580, 0x00b6}, +{0x8581, 0x0012}, {0x8582, 0x0004}, {0x8583, 0x0084}, +{0x8584, 0x00fe}, {0x8585, 0x008a}, {0x8586, 0x0002}, +{0x8587, 0x00b7}, {0x8588, 0x0012}, {0x8589, 0x0004}, +{0x858a, 0x0001}, {0x858b, 0x0001}, {0x858c, 0x0001}, +{0x858d, 0x0001}, {0x858e, 0x0001}, {0x858f, 0x0001}, +{0x8590, 0x0086}, {0x8591, 0x00fd}, {0x8592, 0x00b4}, +{0x8593, 0x0012}, {0x8594, 0x0004}, {0x8595, 0x00b7}, +{0x8596, 0x0012}, {0x8597, 0x0004}, {0x8598, 0x00b6}, +{0x8599, 0x0012}, {0x859a, 0x0000}, {0x859b, 0x0084}, +{0x859c, 0x0008}, {0x859d, 0x0081}, {0x859e, 0x0008}, +{0x859f, 0x0027}, {0x85a0, 0x0016}, {0x85a1, 0x00b6}, +{0x85a2, 0x008f}, {0x85a3, 0x007d}, {0x85a4, 0x0081}, +{0x85a5, 0x000c}, {0x85a6, 0x0027}, {0x85a7, 0x0008}, +{0x85a8, 0x008b}, {0x85a9, 0x0004}, {0x85aa, 0x00b7}, +{0x85ab, 0x008f}, {0x85ac, 0x007d}, {0x85ad, 0x007e}, +{0x85ae, 0x0085}, {0x85af, 0x006c}, {0x85b0, 0x0086}, +{0x85b1, 0x0003}, {0x85b2, 0x0097}, {0x85b3, 0x0040}, +{0x85b4, 0x007e}, {0x85b5, 0x0089}, {0x85b6, 0x006e}, +{0x85b7, 0x0086}, {0x85b8, 0x0007}, {0x85b9, 0x00b7}, +{0x85ba, 0x0012}, {0x85bb, 0x0006}, {0x85bc, 0x005f}, +{0x85bd, 0x00f7}, {0x85be, 0x008f}, {0x85bf, 0x0082}, +{0x85c0, 0x005f}, {0x85c1, 0x00f7}, {0x85c2, 0x008f}, +{0x85c3, 0x007f}, {0x85c4, 0x00f7}, {0x85c5, 0x008f}, +{0x85c6, 0x0070}, {0x85c7, 0x00f7}, {0x85c8, 0x008f}, +{0x85c9, 0x0071}, {0x85ca, 0x00f7}, {0x85cb, 0x008f}, +{0x85cc, 0x0072}, {0x85cd, 0x00f7}, {0x85ce, 0x008f}, +{0x85cf, 0x0073}, {0x85d0, 0x00f7}, {0x85d1, 0x008f}, +{0x85d2, 0x0074}, {0x85d3, 0x00f7}, {0x85d4, 0x008f}, +{0x85d5, 0x0075}, {0x85d6, 0x00f7}, {0x85d7, 0x008f}, +{0x85d8, 0x0076}, {0x85d9, 0x00f7}, {0x85da, 0x008f}, +{0x85db, 0x0077}, {0x85dc, 0x00f7}, {0x85dd, 0x008f}, +{0x85de, 0x0078}, {0x85df, 0x00f7}, {0x85e0, 0x008f}, +{0x85e1, 0x0079}, {0x85e2, 0x00f7}, {0x85e3, 0x008f}, +{0x85e4, 0x007a}, {0x85e5, 0x00f7}, {0x85e6, 0x008f}, +{0x85e7, 0x007b}, {0x85e8, 0x00b6}, {0x85e9, 0x0012}, +{0x85ea, 0x0004}, {0x85eb, 0x008a}, {0x85ec, 0x0010}, +{0x85ed, 0x00b7}, {0x85ee, 0x0012}, {0x85ef, 0x0004}, +{0x85f0, 0x0086}, {0x85f1, 0x00e4}, {0x85f2, 0x00b7}, +{0x85f3, 0x0012}, {0x85f4, 0x0070}, {0x85f5, 0x00b7}, +{0x85f6, 0x0012}, {0x85f7, 0x0007}, {0x85f8, 0x00f7}, +{0x85f9, 0x0012}, {0x85fa, 0x0005}, {0x85fb, 0x00f7}, +{0x85fc, 0x0012}, {0x85fd, 0x0009}, {0x85fe, 0x0086}, +{0x85ff, 0x0008}, {0x8600, 0x00ba}, {0x8601, 0x0012}, +{0x8602, 0x0004}, {0x8603, 0x00b7}, {0x8604, 0x0012}, +{0x8605, 0x0004}, {0x8606, 0x0086}, {0x8607, 0x00f7}, +{0x8608, 0x00b4}, {0x8609, 0x0012}, {0x860a, 0x0004}, +{0x860b, 0x00b7}, {0x860c, 0x0012}, {0x860d, 0x0004}, +{0x860e, 0x0001}, {0x860f, 0x0001}, {0x8610, 0x0001}, +{0x8611, 0x0001}, {0x8612, 0x0001}, {0x8613, 0x0001}, +{0x8614, 0x00b6}, {0x8615, 0x0012}, {0x8616, 0x0008}, +{0x8617, 0x0027}, {0x8618, 0x007f}, {0x8619, 0x0081}, +{0x861a, 0x0080}, {0x861b, 0x0026}, {0x861c, 0x000b}, +{0x861d, 0x0086}, {0x861e, 0x0008}, {0x861f, 0x00ce}, +{0x8620, 0x008f}, {0x8621, 0x0079}, {0x8622, 0x00bd}, +{0x8623, 0x0089}, {0x8624, 0x007b}, {0x8625, 0x007e}, +{0x8626, 0x0086}, {0x8627, 0x008e}, {0x8628, 0x0081}, +{0x8629, 0x0040}, {0x862a, 0x0026}, {0x862b, 0x000b}, +{0x862c, 0x0086}, {0x862d, 0x0004}, {0x862e, 0x00ce}, +{0x862f, 0x008f}, {0x8630, 0x0076}, {0x8631, 0x00bd}, +{0x8632, 0x0089}, {0x8633, 0x007b}, {0x8634, 0x007e}, +{0x8635, 0x0086}, {0x8636, 0x008e}, {0x8637, 0x0081}, +{0x8638, 0x0020}, {0x8639, 0x0026}, {0x863a, 0x000b}, +{0x863b, 0x0086}, {0x863c, 0x0002}, {0x863d, 0x00ce}, +{0x863e, 0x008f}, {0x863f, 0x0073}, {0x8640, 0x00bd}, +{0x8641, 0x0089}, {0x8642, 0x007b}, {0x8643, 0x007e}, +{0x8644, 0x0086}, {0x8645, 0x008e}, {0x8646, 0x0081}, +{0x8647, 0x0010}, {0x8648, 0x0026}, {0x8649, 0x000b}, +{0x864a, 0x0086}, {0x864b, 0x0001}, {0x864c, 0x00ce}, +{0x864d, 0x008f}, {0x864e, 0x0070}, {0x864f, 0x00bd}, +{0x8650, 0x0089}, {0x8651, 0x007b}, {0x8652, 0x007e}, +{0x8653, 0x0086}, {0x8654, 0x008e}, {0x8655, 0x0081}, +{0x8656, 0x0008}, {0x8657, 0x0026}, {0x8658, 0x000b}, +{0x8659, 0x0086}, {0x865a, 0x0008}, {0x865b, 0x00ce}, +{0x865c, 0x008f}, {0x865d, 0x0079}, {0x865e, 0x00bd}, +{0x865f, 0x0089}, {0x8660, 0x007f}, {0x8661, 0x007e}, +{0x8662, 0x0086}, {0x8663, 0x008e}, {0x8664, 0x0081}, +{0x8665, 0x0004}, {0x8666, 0x0026}, {0x8667, 0x000b}, +{0x8668, 0x0086}, {0x8669, 0x0004}, {0x866a, 0x00ce}, +{0x866b, 0x008f}, {0x866c, 0x0076}, {0x866d, 0x00bd}, +{0x866e, 0x0089}, {0x866f, 0x007f}, {0x8670, 0x007e}, +{0x8671, 0x0086}, {0x8672, 0x008e}, {0x8673, 0x0081}, +{0x8674, 0x0002}, {0x8675, 0x0026}, {0x8676, 0x000b}, +{0x8677, 0x008a}, {0x8678, 0x0002}, {0x8679, 0x00ce}, +{0x867a, 0x008f}, {0x867b, 0x0073}, {0x867c, 0x00bd}, +{0x867d, 0x0089}, {0x867e, 0x007f}, {0x867f, 0x007e}, +{0x8680, 0x0086}, {0x8681, 0x008e}, {0x8682, 0x0081}, +{0x8683, 0x0001}, {0x8684, 0x0026}, {0x8685, 0x0008}, +{0x8686, 0x0086}, {0x8687, 0x0001}, {0x8688, 0x00ce}, +{0x8689, 0x008f}, {0x868a, 0x0070}, {0x868b, 0x00bd}, +{0x868c, 0x0089}, {0x868d, 0x007f}, {0x868e, 0x00b6}, +{0x868f, 0x008f}, {0x8690, 0x007f}, {0x8691, 0x0081}, +{0x8692, 0x000f}, {0x8693, 0x0026}, {0x8694, 0x0003}, +{0x8695, 0x007e}, {0x8696, 0x0087}, {0x8697, 0x0047}, +{0x8698, 0x00b6}, {0x8699, 0x0012}, {0x869a, 0x0009}, +{0x869b, 0x0084}, {0x869c, 0x0003}, {0x869d, 0x0081}, +{0x869e, 0x0003}, {0x869f, 0x0027}, {0x86a0, 0x0006}, +{0x86a1, 0x007c}, {0x86a2, 0x0012}, {0x86a3, 0x0009}, +{0x86a4, 0x007e}, {0x86a5, 0x0085}, {0x86a6, 0x00fe}, +{0x86a7, 0x00b6}, {0x86a8, 0x0012}, {0x86a9, 0x0006}, +{0x86aa, 0x0084}, {0x86ab, 0x0007}, {0x86ac, 0x0081}, +{0x86ad, 0x0007}, {0x86ae, 0x0027}, {0x86af, 0x0008}, +{0x86b0, 0x008b}, {0x86b1, 0x0001}, {0x86b2, 0x00b7}, +{0x86b3, 0x0012}, {0x86b4, 0x0006}, {0x86b5, 0x007e}, +{0x86b6, 0x0086}, {0x86b7, 0x00d5}, {0x86b8, 0x00b6}, +{0x86b9, 0x008f}, {0x86ba, 0x0082}, {0x86bb, 0x0026}, +{0x86bc, 0x000a}, {0x86bd, 0x007c}, {0x86be, 0x008f}, +{0x86bf, 0x0082}, {0x86c0, 0x004f}, {0x86c1, 0x00b7}, +{0x86c2, 0x0012}, {0x86c3, 0x0006}, {0x86c4, 0x007e}, +{0x86c5, 0x0085}, {0x86c6, 0x00c0}, {0x86c7, 0x00b6}, +{0x86c8, 0x0012}, {0x86c9, 0x0006}, {0x86ca, 0x0084}, +{0x86cb, 0x003f}, {0x86cc, 0x0081}, {0x86cd, 0x003f}, +{0x86ce, 0x0027}, {0x86cf, 0x0010}, {0x86d0, 0x008b}, +{0x86d1, 0x0008}, {0x86d2, 0x00b7}, {0x86d3, 0x0012}, +{0x86d4, 0x0006}, {0x86d5, 0x00b6}, {0x86d6, 0x0012}, +{0x86d7, 0x0009}, {0x86d8, 0x0084}, {0x86d9, 0x00fc}, +{0x86da, 0x00b7}, {0x86db, 0x0012}, {0x86dc, 0x0009}, +{0x86dd, 0x007e}, {0x86de, 0x0085}, {0x86df, 0x00fe}, +{0x86e0, 0x00ce}, {0x86e1, 0x008f}, {0x86e2, 0x0070}, +{0x86e3, 0x0018}, {0x86e4, 0x00ce}, {0x86e5, 0x008f}, +{0x86e6, 0x0084}, {0x86e7, 0x00c6}, {0x86e8, 0x000c}, +{0x86e9, 0x00bd}, {0x86ea, 0x0089}, {0x86eb, 0x006f}, +{0x86ec, 0x00ce}, {0x86ed, 0x008f}, {0x86ee, 0x0084}, +{0x86ef, 0x0018}, {0x86f0, 0x00ce}, {0x86f1, 0x008f}, +{0x86f2, 0x0070}, {0x86f3, 0x00c6}, {0x86f4, 0x000c}, +{0x86f5, 0x00bd}, {0x86f6, 0x0089}, {0x86f7, 0x006f}, +{0x86f8, 0x00d6}, {0x86f9, 0x0083}, {0x86fa, 0x00c1}, +{0x86fb, 0x004f}, {0x86fc, 0x002d}, {0x86fd, 0x0003}, +{0x86fe, 0x007e}, {0x86ff, 0x0087}, {0x8700, 0x0040}, +{0x8701, 0x00b6}, {0x8702, 0x008f}, {0x8703, 0x007f}, +{0x8704, 0x0081}, {0x8705, 0x0007}, {0x8706, 0x0027}, +{0x8707, 0x000f}, {0x8708, 0x0081}, {0x8709, 0x000b}, +{0x870a, 0x0027}, {0x870b, 0x0015}, {0x870c, 0x0081}, +{0x870d, 0x000d}, {0x870e, 0x0027}, {0x870f, 0x001b}, +{0x8710, 0x0081}, {0x8711, 0x000e}, {0x8712, 0x0027}, +{0x8713, 0x0021}, {0x8714, 0x007e}, {0x8715, 0x0087}, +{0x8716, 0x0040}, {0x8717, 0x00f7}, {0x8718, 0x008f}, +{0x8719, 0x007b}, {0x871a, 0x0086}, {0x871b, 0x0002}, +{0x871c, 0x00b7}, {0x871d, 0x008f}, {0x871e, 0x007a}, +{0x871f, 0x0020}, {0x8720, 0x001c}, {0x8721, 0x00f7}, +{0x8722, 0x008f}, {0x8723, 0x0078}, {0x8724, 0x0086}, +{0x8725, 0x0002}, {0x8726, 0x00b7}, {0x8727, 0x008f}, +{0x8728, 0x0077}, {0x8729, 0x0020}, {0x872a, 0x0012}, +{0x872b, 0x00f7}, {0x872c, 0x008f}, {0x872d, 0x0075}, +{0x872e, 0x0086}, {0x872f, 0x0002}, {0x8730, 0x00b7}, +{0x8731, 0x008f}, {0x8732, 0x0074}, {0x8733, 0x0020}, +{0x8734, 0x0008}, {0x8735, 0x00f7}, {0x8736, 0x008f}, +{0x8737, 0x0072}, {0x8738, 0x0086}, {0x8739, 0x0002}, +{0x873a, 0x00b7}, {0x873b, 0x008f}, {0x873c, 0x0071}, +{0x873d, 0x007e}, {0x873e, 0x0087}, {0x873f, 0x0047}, +{0x8740, 0x0086}, {0x8741, 0x0004}, {0x8742, 0x0097}, +{0x8743, 0x0040}, {0x8744, 0x007e}, {0x8745, 0x0089}, +{0x8746, 0x006e}, {0x8747, 0x00ce}, {0x8748, 0x008f}, +{0x8749, 0x0072}, {0x874a, 0x00bd}, {0x874b, 0x0089}, +{0x874c, 0x00f7}, {0x874d, 0x00ce}, {0x874e, 0x008f}, +{0x874f, 0x0075}, {0x8750, 0x00bd}, {0x8751, 0x0089}, +{0x8752, 0x00f7}, {0x8753, 0x00ce}, {0x8754, 0x008f}, +{0x8755, 0x0078}, {0x8756, 0x00bd}, {0x8757, 0x0089}, +{0x8758, 0x00f7}, {0x8759, 0x00ce}, {0x875a, 0x008f}, +{0x875b, 0x007b}, {0x875c, 0x00bd}, {0x875d, 0x0089}, +{0x875e, 0x00f7}, {0x875f, 0x004f}, {0x8760, 0x00b7}, +{0x8761, 0x008f}, {0x8762, 0x007d}, {0x8763, 0x00b7}, +{0x8764, 0x008f}, {0x8765, 0x0081}, {0x8766, 0x00b6}, +{0x8767, 0x008f}, {0x8768, 0x0072}, {0x8769, 0x0027}, +{0x876a, 0x0047}, {0x876b, 0x007c}, {0x876c, 0x008f}, +{0x876d, 0x007d}, {0x876e, 0x00b6}, {0x876f, 0x008f}, +{0x8770, 0x0075}, {0x8771, 0x0027}, {0x8772, 0x003f}, +{0x8773, 0x007c}, {0x8774, 0x008f}, {0x8775, 0x007d}, +{0x8776, 0x00b6}, {0x8777, 0x008f}, {0x8778, 0x0078}, +{0x8779, 0x0027}, {0x877a, 0x0037}, {0x877b, 0x007c}, +{0x877c, 0x008f}, {0x877d, 0x007d}, {0x877e, 0x00b6}, +{0x877f, 0x008f}, {0x8780, 0x007b}, {0x8781, 0x0027}, +{0x8782, 0x002f}, {0x8783, 0x007f}, {0x8784, 0x008f}, +{0x8785, 0x007d}, {0x8786, 0x007c}, {0x8787, 0x008f}, +{0x8788, 0x0081}, {0x8789, 0x007a}, {0x878a, 0x008f}, +{0x878b, 0x0072}, {0x878c, 0x0027}, {0x878d, 0x001b}, +{0x878e, 0x007c}, {0x878f, 0x008f}, {0x8790, 0x007d}, +{0x8791, 0x007a}, {0x8792, 0x008f}, {0x8793, 0x0075}, +{0x8794, 0x0027}, {0x8795, 0x0016}, {0x8796, 0x007c}, +{0x8797, 0x008f}, {0x8798, 0x007d}, {0x8799, 0x007a}, +{0x879a, 0x008f}, {0x879b, 0x0078}, {0x879c, 0x0027}, +{0x879d, 0x0011}, {0x879e, 0x007c}, {0x879f, 0x008f}, +{0x87a0, 0x007d}, {0x87a1, 0x007a}, {0x87a2, 0x008f}, +{0x87a3, 0x007b}, {0x87a4, 0x0027}, {0x87a5, 0x000c}, +{0x87a6, 0x007e}, {0x87a7, 0x0087}, {0x87a8, 0x0083}, +{0x87a9, 0x007a}, {0x87aa, 0x008f}, {0x87ab, 0x0075}, +{0x87ac, 0x007a}, {0x87ad, 0x008f}, {0x87ae, 0x0078}, +{0x87af, 0x007a}, {0x87b0, 0x008f}, {0x87b1, 0x007b}, +{0x87b2, 0x00ce}, {0x87b3, 0x00c1}, {0x87b4, 0x00fc}, +{0x87b5, 0x00f6}, {0x87b6, 0x008f}, {0x87b7, 0x007d}, +{0x87b8, 0x003a}, {0x87b9, 0x00a6}, {0x87ba, 0x0000}, +{0x87bb, 0x00b7}, {0x87bc, 0x0012}, {0x87bd, 0x0070}, +{0x87be, 0x00b6}, {0x87bf, 0x008f}, {0x87c0, 0x0072}, +{0x87c1, 0x0026}, {0x87c2, 0x0003}, {0x87c3, 0x007e}, +{0x87c4, 0x0087}, {0x87c5, 0x00fa}, {0x87c6, 0x00b6}, +{0x87c7, 0x008f}, {0x87c8, 0x0075}, {0x87c9, 0x0026}, +{0x87ca, 0x000a}, {0x87cb, 0x0018}, {0x87cc, 0x00ce}, +{0x87cd, 0x008f}, {0x87ce, 0x0073}, {0x87cf, 0x00bd}, +{0x87d0, 0x0089}, {0x87d1, 0x00d5}, {0x87d2, 0x007e}, +{0x87d3, 0x0087}, {0x87d4, 0x00fa}, {0x87d5, 0x00b6}, +{0x87d6, 0x008f}, {0x87d7, 0x0078}, {0x87d8, 0x0026}, +{0x87d9, 0x000a}, {0x87da, 0x0018}, {0x87db, 0x00ce}, +{0x87dc, 0x008f}, {0x87dd, 0x0076}, {0x87de, 0x00bd}, +{0x87df, 0x0089}, {0x87e0, 0x00d5}, {0x87e1, 0x007e}, +{0x87e2, 0x0087}, {0x87e3, 0x00fa}, {0x87e4, 0x00b6}, +{0x87e5, 0x008f}, {0x87e6, 0x007b}, {0x87e7, 0x0026}, +{0x87e8, 0x000a}, {0x87e9, 0x0018}, {0x87ea, 0x00ce}, +{0x87eb, 0x008f}, {0x87ec, 0x0079}, {0x87ed, 0x00bd}, +{0x87ee, 0x0089}, {0x87ef, 0x00d5}, {0x87f0, 0x007e}, +{0x87f1, 0x0087}, {0x87f2, 0x00fa}, {0x87f3, 0x0086}, +{0x87f4, 0x0005}, {0x87f5, 0x0097}, {0x87f6, 0x0040}, +{0x87f7, 0x007e}, {0x87f8, 0x0089}, {0x87f9, 0x006e}, +{0x87fa, 0x00b6}, {0x87fb, 0x008f}, {0x87fc, 0x0075}, +{0x87fd, 0x0081}, {0x87fe, 0x0007}, {0x87ff, 0x002e}, +{0x8800, 0x00f2}, {0x8801, 0x00f6}, {0x8802, 0x0012}, +{0x8803, 0x0006}, {0x8804, 0x00c4}, {0x8805, 0x00f8}, +{0x8806, 0x001b}, {0x8807, 0x00b7}, {0x8808, 0x0012}, +{0x8809, 0x0006}, {0x880a, 0x00b6}, {0x880b, 0x008f}, +{0x880c, 0x0078}, {0x880d, 0x0081}, {0x880e, 0x0007}, +{0x880f, 0x002e}, {0x8810, 0x00e2}, {0x8811, 0x0048}, +{0x8812, 0x0048}, {0x8813, 0x0048}, {0x8814, 0x00f6}, +{0x8815, 0x0012}, {0x8816, 0x0006}, {0x8817, 0x00c4}, +{0x8818, 0x00c7}, {0x8819, 0x001b}, {0x881a, 0x00b7}, +{0x881b, 0x0012}, {0x881c, 0x0006}, {0x881d, 0x00b6}, +{0x881e, 0x008f}, {0x881f, 0x007b}, {0x8820, 0x0081}, +{0x8821, 0x0007}, {0x8822, 0x002e}, {0x8823, 0x00cf}, +{0x8824, 0x00f6}, {0x8825, 0x0012}, {0x8826, 0x0005}, +{0x8827, 0x00c4}, {0x8828, 0x00f8}, {0x8829, 0x001b}, +{0x882a, 0x00b7}, {0x882b, 0x0012}, {0x882c, 0x0005}, +{0x882d, 0x0086}, {0x882e, 0x0000}, {0x882f, 0x00f6}, +{0x8830, 0x008f}, {0x8831, 0x0071}, {0x8832, 0x00bd}, +{0x8833, 0x0089}, {0x8834, 0x0094}, {0x8835, 0x0086}, +{0x8836, 0x0001}, {0x8837, 0x00f6}, {0x8838, 0x008f}, +{0x8839, 0x0074}, {0x883a, 0x00bd}, {0x883b, 0x0089}, +{0x883c, 0x0094}, {0x883d, 0x0086}, {0x883e, 0x0002}, +{0x883f, 0x00f6}, {0x8840, 0x008f}, {0x8841, 0x0077}, +{0x8842, 0x00bd}, {0x8843, 0x0089}, {0x8844, 0x0094}, +{0x8845, 0x0086}, {0x8846, 0x0003}, {0x8847, 0x00f6}, +{0x8848, 0x008f}, {0x8849, 0x007a}, {0x884a, 0x00bd}, +{0x884b, 0x0089}, {0x884c, 0x0094}, {0x884d, 0x00ce}, +{0x884e, 0x008f}, {0x884f, 0x0070}, {0x8850, 0x00a6}, +{0x8851, 0x0001}, {0x8852, 0x0081}, {0x8853, 0x0001}, +{0x8854, 0x0027}, {0x8855, 0x0007}, {0x8856, 0x0081}, +{0x8857, 0x0003}, {0x8858, 0x0027}, {0x8859, 0x0003}, +{0x885a, 0x007e}, {0x885b, 0x0088}, {0x885c, 0x0066}, +{0x885d, 0x00a6}, {0x885e, 0x0000}, {0x885f, 0x00b8}, +{0x8860, 0x008f}, {0x8861, 0x0081}, {0x8862, 0x0084}, +{0x8863, 0x0001}, {0x8864, 0x0026}, {0x8865, 0x000b}, +{0x8866, 0x008c}, {0x8867, 0x008f}, {0x8868, 0x0079}, +{0x8869, 0x002c}, {0x886a, 0x000e}, {0x886b, 0x0008}, +{0x886c, 0x0008}, {0x886d, 0x0008}, {0x886e, 0x007e}, +{0x886f, 0x0088}, {0x8870, 0x0050}, {0x8871, 0x00b6}, +{0x8872, 0x0012}, {0x8873, 0x0004}, {0x8874, 0x008a}, +{0x8875, 0x0040}, {0x8876, 0x00b7}, {0x8877, 0x0012}, +{0x8878, 0x0004}, {0x8879, 0x00b6}, {0x887a, 0x0012}, +{0x887b, 0x0004}, {0x887c, 0x0084}, {0x887d, 0x00fb}, +{0x887e, 0x0084}, {0x887f, 0x00ef}, {0x8880, 0x00b7}, +{0x8881, 0x0012}, {0x8882, 0x0004}, {0x8883, 0x00b6}, +{0x8884, 0x0012}, {0x8885, 0x0007}, {0x8886, 0x0036}, +{0x8887, 0x00b6}, {0x8888, 0x008f}, {0x8889, 0x007c}, +{0x888a, 0x0048}, {0x888b, 0x0048}, {0x888c, 0x00b7}, +{0x888d, 0x0012}, {0x888e, 0x0007}, {0x888f, 0x0086}, +{0x8890, 0x0001}, {0x8891, 0x00ba}, {0x8892, 0x0012}, +{0x8893, 0x0004}, {0x8894, 0x00b7}, {0x8895, 0x0012}, +{0x8896, 0x0004}, {0x8897, 0x0001}, {0x8898, 0x0001}, +{0x8899, 0x0001}, {0x889a, 0x0001}, {0x889b, 0x0001}, +{0x889c, 0x0001}, {0x889d, 0x0086}, {0x889e, 0x00fe}, +{0x889f, 0x00b4}, {0x88a0, 0x0012}, {0x88a1, 0x0004}, +{0x88a2, 0x00b7}, {0x88a3, 0x0012}, {0x88a4, 0x0004}, +{0x88a5, 0x0086}, {0x88a6, 0x0002}, {0x88a7, 0x00ba}, +{0x88a8, 0x0012}, {0x88a9, 0x0004}, {0x88aa, 0x00b7}, +{0x88ab, 0x0012}, {0x88ac, 0x0004}, {0x88ad, 0x0086}, +{0x88ae, 0x00fd}, {0x88af, 0x00b4}, {0x88b0, 0x0012}, +{0x88b1, 0x0004}, {0x88b2, 0x00b7}, {0x88b3, 0x0012}, +{0x88b4, 0x0004}, {0x88b5, 0x0032}, {0x88b6, 0x00b7}, +{0x88b7, 0x0012}, {0x88b8, 0x0007}, {0x88b9, 0x00b6}, +{0x88ba, 0x0012}, {0x88bb, 0x0000}, {0x88bc, 0x0084}, +{0x88bd, 0x0008}, {0x88be, 0x0081}, {0x88bf, 0x0008}, +{0x88c0, 0x0027}, {0x88c1, 0x000f}, {0x88c2, 0x007c}, +{0x88c3, 0x0082}, {0x88c4, 0x0008}, {0x88c5, 0x0026}, +{0x88c6, 0x0007}, {0x88c7, 0x0086}, {0x88c8, 0x0076}, +{0x88c9, 0x0097}, {0x88ca, 0x0040}, {0x88cb, 0x007e}, +{0x88cc, 0x0089}, {0x88cd, 0x006e}, {0x88ce, 0x007e}, +{0x88cf, 0x0086}, {0x88d0, 0x00ec}, {0x88d1, 0x00b6}, +{0x88d2, 0x008f}, {0x88d3, 0x007f}, {0x88d4, 0x0081}, +{0x88d5, 0x000f}, {0x88d6, 0x0027}, {0x88d7, 0x003c}, +{0x88d8, 0x00bd}, {0x88d9, 0x00e6}, {0x88da, 0x00c7}, +{0x88db, 0x00b7}, {0x88dc, 0x0012}, {0x88dd, 0x000d}, +{0x88de, 0x00bd}, {0x88df, 0x00e6}, {0x88e0, 0x00cb}, +{0x88e1, 0x00b6}, {0x88e2, 0x0012}, {0x88e3, 0x0004}, +{0x88e4, 0x008a}, {0x88e5, 0x0020}, {0x88e6, 0x00b7}, +{0x88e7, 0x0012}, {0x88e8, 0x0004}, {0x88e9, 0x00ce}, +{0x88ea, 0x00ff}, {0x88eb, 0x00ff}, {0x88ec, 0x00b6}, +{0x88ed, 0x0012}, {0x88ee, 0x0000}, {0x88ef, 0x0081}, +{0x88f0, 0x000c}, {0x88f1, 0x0026}, {0x88f2, 0x0005}, +{0x88f3, 0x0009}, {0x88f4, 0x0026}, {0x88f5, 0x00f6}, +{0x88f6, 0x0027}, {0x88f7, 0x001c}, {0x88f8, 0x00b6}, +{0x88f9, 0x0012}, {0x88fa, 0x0004}, {0x88fb, 0x0084}, +{0x88fc, 0x00df}, {0x88fd, 0x00b7}, {0x88fe, 0x0012}, +{0x88ff, 0x0004}, {0x8900, 0x0096}, {0x8901, 0x0083}, +{0x8902, 0x0081}, {0x8903, 0x0007}, {0x8904, 0x002c}, +{0x8905, 0x0005}, {0x8906, 0x007c}, {0x8907, 0x0000}, +{0x8908, 0x0083}, {0x8909, 0x0020}, {0x890a, 0x0006}, +{0x890b, 0x0096}, {0x890c, 0x0083}, {0x890d, 0x008b}, +{0x890e, 0x0008}, {0x890f, 0x0097}, {0x8910, 0x0083}, +{0x8911, 0x007e}, {0x8912, 0x0085}, {0x8913, 0x0041}, +{0x8914, 0x007f}, {0x8915, 0x008f}, {0x8916, 0x007e}, +{0x8917, 0x0086}, {0x8918, 0x0080}, {0x8919, 0x00b7}, +{0x891a, 0x0012}, {0x891b, 0x000c}, {0x891c, 0x0086}, +{0x891d, 0x0001}, {0x891e, 0x00b7}, {0x891f, 0x008f}, +{0x8920, 0x007d}, {0x8921, 0x00b6}, {0x8922, 0x0012}, +{0x8923, 0x000c}, {0x8924, 0x0084}, {0x8925, 0x007f}, +{0x8926, 0x00b7}, {0x8927, 0x0012}, {0x8928, 0x000c}, +{0x8929, 0x008a}, {0x892a, 0x0080}, {0x892b, 0x00b7}, +{0x892c, 0x0012}, {0x892d, 0x000c}, {0x892e, 0x0086}, +{0x892f, 0x000a}, {0x8930, 0x00bd}, {0x8931, 0x008a}, +{0x8932, 0x0006}, {0x8933, 0x00b6}, {0x8934, 0x0012}, +{0x8935, 0x000a}, {0x8936, 0x002a}, {0x8937, 0x0009}, +{0x8938, 0x00b6}, {0x8939, 0x0012}, {0x893a, 0x000c}, +{0x893b, 0x00ba}, {0x893c, 0x008f}, {0x893d, 0x007d}, +{0x893e, 0x00b7}, {0x893f, 0x0012}, {0x8940, 0x000c}, +{0x8941, 0x00b6}, {0x8942, 0x008f}, {0x8943, 0x007e}, +{0x8944, 0x0081}, {0x8945, 0x0060}, {0x8946, 0x0027}, +{0x8947, 0x001a}, {0x8948, 0x008b}, {0x8949, 0x0020}, +{0x894a, 0x00b7}, {0x894b, 0x008f}, {0x894c, 0x007e}, +{0x894d, 0x00b6}, {0x894e, 0x0012}, {0x894f, 0x000c}, +{0x8950, 0x0084}, {0x8951, 0x009f}, {0x8952, 0x00ba}, +{0x8953, 0x008f}, {0x8954, 0x007e}, {0x8955, 0x00b7}, +{0x8956, 0x0012}, {0x8957, 0x000c}, {0x8958, 0x00b6}, +{0x8959, 0x008f}, {0x895a, 0x007d}, {0x895b, 0x0048}, +{0x895c, 0x00b7}, {0x895d, 0x008f}, {0x895e, 0x007d}, +{0x895f, 0x007e}, {0x8960, 0x0089}, {0x8961, 0x0021}, +{0x8962, 0x00b6}, {0x8963, 0x0012}, {0x8964, 0x0004}, +{0x8965, 0x008a}, {0x8966, 0x0020}, {0x8967, 0x00b7}, +{0x8968, 0x0012}, {0x8969, 0x0004}, {0x896a, 0x00bd}, +{0x896b, 0x008a}, {0x896c, 0x000a}, {0x896d, 0x004f}, +{0x896e, 0x0039}, {0x896f, 0x00a6}, {0x8970, 0x0000}, +{0x8971, 0x0018}, {0x8972, 0x00a7}, {0x8973, 0x0000}, +{0x8974, 0x0008}, {0x8975, 0x0018}, {0x8976, 0x0008}, +{0x8977, 0x005a}, {0x8978, 0x0026}, {0x8979, 0x00f5}, +{0x897a, 0x0039}, {0x897b, 0x0036}, {0x897c, 0x006c}, +{0x897d, 0x0000}, {0x897e, 0x0032}, {0x897f, 0x00ba}, +{0x8980, 0x008f}, {0x8981, 0x007f}, {0x8982, 0x00b7}, +{0x8983, 0x008f}, {0x8984, 0x007f}, {0x8985, 0x00b6}, +{0x8986, 0x0012}, {0x8987, 0x0009}, {0x8988, 0x0084}, +{0x8989, 0x0003}, {0x898a, 0x00a7}, {0x898b, 0x0001}, +{0x898c, 0x00b6}, {0x898d, 0x0012}, {0x898e, 0x0006}, +{0x898f, 0x0084}, {0x8990, 0x003f}, {0x8991, 0x00a7}, +{0x8992, 0x0002}, {0x8993, 0x0039}, {0x8994, 0x0036}, +{0x8995, 0x0086}, {0x8996, 0x0003}, {0x8997, 0x00b7}, +{0x8998, 0x008f}, {0x8999, 0x0080}, {0x899a, 0x0032}, +{0x899b, 0x00c1}, {0x899c, 0x0000}, {0x899d, 0x0026}, +{0x899e, 0x0006}, {0x899f, 0x00b7}, {0x89a0, 0x008f}, +{0x89a1, 0x007c}, {0x89a2, 0x007e}, {0x89a3, 0x0089}, +{0x89a4, 0x00c9}, {0x89a5, 0x00c1}, {0x89a6, 0x0001}, +{0x89a7, 0x0027}, {0x89a8, 0x0018}, {0x89a9, 0x00c1}, +{0x89aa, 0x0002}, {0x89ab, 0x0027}, {0x89ac, 0x000c}, +{0x89ad, 0x00c1}, {0x89ae, 0x0003}, {0x89af, 0x0027}, +{0x89b0, 0x0000}, {0x89b1, 0x00f6}, {0x89b2, 0x008f}, +{0x89b3, 0x0080}, {0x89b4, 0x0005}, {0x89b5, 0x0005}, +{0x89b6, 0x00f7}, {0x89b7, 0x008f}, {0x89b8, 0x0080}, +{0x89b9, 0x00f6}, {0x89ba, 0x008f}, {0x89bb, 0x0080}, +{0x89bc, 0x0005}, {0x89bd, 0x0005}, {0x89be, 0x00f7}, +{0x89bf, 0x008f}, {0x89c0, 0x0080}, {0x89c1, 0x00f6}, +{0x89c2, 0x008f}, {0x89c3, 0x0080}, {0x89c4, 0x0005}, +{0x89c5, 0x0005}, {0x89c6, 0x00f7}, {0x89c7, 0x008f}, +{0x89c8, 0x0080}, {0x89c9, 0x00f6}, {0x89ca, 0x008f}, +{0x89cb, 0x0080}, {0x89cc, 0x0053}, {0x89cd, 0x00f4}, +{0x89ce, 0x0012}, {0x89cf, 0x0007}, {0x89d0, 0x001b}, +{0x89d1, 0x00b7}, {0x89d2, 0x0012}, {0x89d3, 0x0007}, +{0x89d4, 0x0039}, {0x89d5, 0x00ce}, {0x89d6, 0x008f}, +{0x89d7, 0x0070}, {0x89d8, 0x00a6}, {0x89d9, 0x0000}, +{0x89da, 0x0018}, {0x89db, 0x00e6}, {0x89dc, 0x0000}, +{0x89dd, 0x0018}, {0x89de, 0x00a7}, {0x89df, 0x0000}, +{0x89e0, 0x00e7}, {0x89e1, 0x0000}, {0x89e2, 0x00a6}, +{0x89e3, 0x0001}, {0x89e4, 0x0018}, {0x89e5, 0x00e6}, +{0x89e6, 0x0001}, {0x89e7, 0x0018}, {0x89e8, 0x00a7}, +{0x89e9, 0x0001}, {0x89ea, 0x00e7}, {0x89eb, 0x0001}, +{0x89ec, 0x00a6}, {0x89ed, 0x0002}, {0x89ee, 0x0018}, +{0x89ef, 0x00e6}, {0x89f0, 0x0002}, {0x89f1, 0x0018}, +{0x89f2, 0x00a7}, {0x89f3, 0x0002}, {0x89f4, 0x00e7}, +{0x89f5, 0x0002}, {0x89f6, 0x0039}, {0x89f7, 0x00a6}, +{0x89f8, 0x0000}, {0x89f9, 0x0084}, {0x89fa, 0x0007}, +{0x89fb, 0x00e6}, {0x89fc, 0x0000}, {0x89fd, 0x00c4}, +{0x89fe, 0x0038}, {0x89ff, 0x0054}, {0x8a00, 0x0054}, +{0x8a01, 0x0054}, {0x8a02, 0x001b}, {0x8a03, 0x00a7}, +{0x8a04, 0x0000}, {0x8a05, 0x0039}, {0x8a06, 0x004a}, +{0x8a07, 0x0026}, {0x8a08, 0x00fd}, {0x8a09, 0x0039}, +{0x8a0a, 0x0096}, {0x8a0b, 0x0022}, {0x8a0c, 0x0084}, +{0x8a0d, 0x000f}, {0x8a0e, 0x0097}, {0x8a0f, 0x0022}, +{0x8a10, 0x0086}, {0x8a11, 0x0001}, {0x8a12, 0x00b7}, +{0x8a13, 0x008f}, {0x8a14, 0x0070}, {0x8a15, 0x00b6}, +{0x8a16, 0x0012}, {0x8a17, 0x0007}, {0x8a18, 0x00b7}, +{0x8a19, 0x008f}, {0x8a1a, 0x0071}, {0x8a1b, 0x00f6}, +{0x8a1c, 0x0012}, {0x8a1d, 0x000c}, {0x8a1e, 0x00c4}, +{0x8a1f, 0x000f}, {0x8a20, 0x00c8}, {0x8a21, 0x000f}, +{0x8a22, 0x00f7}, {0x8a23, 0x008f}, {0x8a24, 0x0072}, +{0x8a25, 0x00f6}, {0x8a26, 0x008f}, {0x8a27, 0x0072}, +{0x8a28, 0x00b6}, {0x8a29, 0x008f}, {0x8a2a, 0x0071}, +{0x8a2b, 0x0084}, {0x8a2c, 0x0003}, {0x8a2d, 0x0027}, +{0x8a2e, 0x0014}, {0x8a2f, 0x0081}, {0x8a30, 0x0001}, +{0x8a31, 0x0027}, {0x8a32, 0x001c}, {0x8a33, 0x0081}, +{0x8a34, 0x0002}, {0x8a35, 0x0027}, {0x8a36, 0x0024}, +{0x8a37, 0x00f4}, {0x8a38, 0x008f}, {0x8a39, 0x0070}, +{0x8a3a, 0x0027}, {0x8a3b, 0x002a}, {0x8a3c, 0x0096}, +{0x8a3d, 0x0022}, {0x8a3e, 0x008a}, {0x8a3f, 0x0080}, +{0x8a40, 0x007e}, {0x8a41, 0x008a}, {0x8a42, 0x0064}, +{0x8a43, 0x00f4}, {0x8a44, 0x008f}, {0x8a45, 0x0070}, +{0x8a46, 0x0027}, {0x8a47, 0x001e}, {0x8a48, 0x0096}, +{0x8a49, 0x0022}, {0x8a4a, 0x008a}, {0x8a4b, 0x0010}, +{0x8a4c, 0x007e}, {0x8a4d, 0x008a}, {0x8a4e, 0x0064}, +{0x8a4f, 0x00f4}, {0x8a50, 0x008f}, {0x8a51, 0x0070}, +{0x8a52, 0x0027}, {0x8a53, 0x0012}, {0x8a54, 0x0096}, +{0x8a55, 0x0022}, {0x8a56, 0x008a}, {0x8a57, 0x0020}, +{0x8a58, 0x007e}, {0x8a59, 0x008a}, {0x8a5a, 0x0064}, +{0x8a5b, 0x00f4}, {0x8a5c, 0x008f}, {0x8a5d, 0x0070}, +{0x8a5e, 0x0027}, {0x8a5f, 0x0006}, {0x8a60, 0x0096}, +{0x8a61, 0x0022}, {0x8a62, 0x008a}, {0x8a63, 0x0040}, +{0x8a64, 0x0097}, {0x8a65, 0x0022}, {0x8a66, 0x0074}, +{0x8a67, 0x008f}, {0x8a68, 0x0071}, {0x8a69, 0x0074}, +{0x8a6a, 0x008f}, {0x8a6b, 0x0071}, {0x8a6c, 0x0078}, +{0x8a6d, 0x008f}, {0x8a6e, 0x0070}, {0x8a6f, 0x00b6}, +{0x8a70, 0x008f}, {0x8a71, 0x0070}, {0x8a72, 0x0085}, +{0x8a73, 0x0010}, {0x8a74, 0x0027}, {0x8a75, 0x00af}, +{0x8a76, 0x00d6}, {0x8a77, 0x0022}, {0x8a78, 0x00c4}, +{0x8a79, 0x0010}, {0x8a7a, 0x0058}, {0x8a7b, 0x00b6}, +{0x8a7c, 0x0012}, {0x8a7d, 0x0070}, {0x8a7e, 0x0081}, +{0x8a7f, 0x00e4}, {0x8a80, 0x0027}, {0x8a81, 0x0036}, +{0x8a82, 0x0081}, {0x8a83, 0x00e1}, {0x8a84, 0x0026}, +{0x8a85, 0x000c}, {0x8a86, 0x0096}, {0x8a87, 0x0022}, +{0x8a88, 0x0084}, {0x8a89, 0x0020}, {0x8a8a, 0x0044}, +{0x8a8b, 0x001b}, {0x8a8c, 0x00d6}, {0x8a8d, 0x0022}, +{0x8a8e, 0x00c4}, {0x8a8f, 0x00cf}, {0x8a90, 0x0020}, +{0x8a91, 0x0023}, {0x8a92, 0x0058}, {0x8a93, 0x0081}, +{0x8a94, 0x00c6}, {0x8a95, 0x0026}, {0x8a96, 0x000d}, +{0x8a97, 0x0096}, {0x8a98, 0x0022}, {0x8a99, 0x0084}, +{0x8a9a, 0x0040}, {0x8a9b, 0x0044}, {0x8a9c, 0x0044}, +{0x8a9d, 0x001b}, {0x8a9e, 0x00d6}, {0x8a9f, 0x0022}, +{0x8aa0, 0x00c4}, {0x8aa1, 0x00af}, {0x8aa2, 0x0020}, +{0x8aa3, 0x0011}, {0x8aa4, 0x0058}, {0x8aa5, 0x0081}, +{0x8aa6, 0x0027}, {0x8aa7, 0x0026}, {0x8aa8, 0x000f}, +{0x8aa9, 0x0096}, {0x8aaa, 0x0022}, {0x8aab, 0x0084}, +{0x8aac, 0x0080}, {0x8aad, 0x0044}, {0x8aae, 0x0044}, +{0x8aaf, 0x0044}, {0x8ab0, 0x001b}, {0x8ab1, 0x00d6}, +{0x8ab2, 0x0022}, {0x8ab3, 0x00c4}, {0x8ab4, 0x006f}, +{0x8ab5, 0x001b}, {0x8ab6, 0x0097}, {0x8ab7, 0x0022}, +{0x8ab8, 0x0039}, {0x8ab9, 0x0027}, {0x8aba, 0x000c}, +{0x8abb, 0x007c}, {0x8abc, 0x0082}, {0x8abd, 0x0006}, +{0x8abe, 0x00bd}, {0x8abf, 0x00d9}, {0x8ac0, 0x00ed}, +{0x8ac1, 0x00b6}, {0x8ac2, 0x0082}, {0x8ac3, 0x0007}, +{0x8ac4, 0x007e}, {0x8ac5, 0x008a}, {0x8ac6, 0x00b9}, +{0x8ac7, 0x007f}, {0x8ac8, 0x0082}, {0x8ac9, 0x0006}, +{0x8aca, 0x0039}, { 0x0, 0x0 } +}; +#endif + + +/* phy types */ +#define CAS_PHY_UNKNOWN 0x00 +#define CAS_PHY_SERDES 0x01 +#define CAS_PHY_MII_MDIO0 0x02 +#define CAS_PHY_MII_MDIO1 0x04 +#define CAS_PHY_MII(x) ((x) & (CAS_PHY_MII_MDIO0 | CAS_PHY_MII_MDIO1)) + +/* _RING_INDEX is the index for the ring sizes to be used. _RING_SIZE + * is the actual size. the default index for the various rings is + * 8. NOTE: there a bunch of alignment constraints for the rings. to + * deal with that, i just allocate rings to create the desired + * alignment. here are the constraints: + * RX DESC and COMP rings must be 8KB aligned + * TX DESC must be 2KB aligned. + * if you change the numbers, be cognizant of how the alignment will change + * in INIT_BLOCK as well. + */ + +#define DESC_RING_I_TO_S(x) (32*(1 << (x))) +#define COMP_RING_I_TO_S(x) (128*(1 << (x))) +#define TX_DESC_RING_INDEX 4 /* 512 = 8k */ +#define RX_DESC_RING_INDEX 4 /* 512 = 8k */ +#define RX_COMP_RING_INDEX 4 /* 2048 = 64k: should be 4x rx ring size */ + +#if (TX_DESC_RING_INDEX > 8) || (TX_DESC_RING_INDEX < 0) +#error TX_DESC_RING_INDEX must be between 0 and 8 +#endif + +#if (RX_DESC_RING_INDEX > 8) || (RX_DESC_RING_INDEX < 0) +#error RX_DESC_RING_INDEX must be between 0 and 8 +#endif + +#if (RX_COMP_RING_INDEX > 8) || (RX_COMP_RING_INDEX < 0) +#error RX_COMP_RING_INDEX must be between 0 and 8 +#endif + +#define N_TX_RINGS MAX_TX_RINGS /* for QoS */ +#define N_TX_RINGS_MASK MAX_TX_RINGS_MASK +#define N_RX_DESC_RINGS MAX_RX_DESC_RINGS /* 1 for ipsec */ +#define N_RX_COMP_RINGS 0x1 /* for mult. PCI interrupts */ + +/* number of flows that can go through re-assembly */ +#define N_RX_FLOWS 64 + +#define TX_DESC_RING_SIZE DESC_RING_I_TO_S(TX_DESC_RING_INDEX) +#define RX_DESC_RING_SIZE DESC_RING_I_TO_S(RX_DESC_RING_INDEX) +#define RX_COMP_RING_SIZE COMP_RING_I_TO_S(RX_COMP_RING_INDEX) +#define TX_DESC_RINGN_INDEX(x) TX_DESC_RING_INDEX +#define RX_DESC_RINGN_INDEX(x) RX_DESC_RING_INDEX +#define RX_COMP_RINGN_INDEX(x) RX_COMP_RING_INDEX +#define TX_DESC_RINGN_SIZE(x) TX_DESC_RING_SIZE +#define RX_DESC_RINGN_SIZE(x) RX_DESC_RING_SIZE +#define RX_COMP_RINGN_SIZE(x) RX_COMP_RING_SIZE + +/* convert values */ +#define CAS_BASE(x, y) (((y) << (x ## _SHIFT)) & (x ## _MASK)) +#define CAS_VAL(x, y) (((y) & (x ## _MASK)) >> (x ## _SHIFT)) +#define CAS_TX_RINGN_BASE(y) ((TX_DESC_RINGN_INDEX(y) << \ + TX_CFG_DESC_RINGN_SHIFT(y)) & \ + TX_CFG_DESC_RINGN_MASK(y)) + +/* min is 2k, but we can't do jumbo frames unless it's at least 8k */ +#define CAS_MIN_PAGE_SHIFT 11 /* 2048 */ +#define CAS_JUMBO_PAGE_SHIFT 13 /* 8192 */ +#define CAS_MAX_PAGE_SHIFT 14 /* 16384 */ + +#define TX_DESC_BUFLEN_MASK 0x0000000000003FFFULL /* buffer length in + bytes. 0 - 9256 */ +#define TX_DESC_BUFLEN_SHIFT 0 +#define TX_DESC_CSUM_START_MASK 0x00000000001F8000ULL /* checksum start. # + of bytes to be + skipped before + csum calc begins. + value must be + even */ +#define TX_DESC_CSUM_START_SHIFT 15 +#define TX_DESC_CSUM_STUFF_MASK 0x000000001FE00000ULL /* checksum stuff. + byte offset w/in + the pkt for the + 1st csum byte. + must be > 8 */ +#define TX_DESC_CSUM_STUFF_SHIFT 21 +#define TX_DESC_CSUM_EN 0x0000000020000000ULL /* enable checksum */ +#define TX_DESC_EOF 0x0000000040000000ULL /* end of frame */ +#define TX_DESC_SOF 0x0000000080000000ULL /* start of frame */ +#define TX_DESC_INTME 0x0000000100000000ULL /* interrupt me */ +#define TX_DESC_NO_CRC 0x0000000200000000ULL /* debugging only. + CRC will not be + inserted into + outgoing frame. */ +struct cas_tx_desc { + u64 control; + u64 buffer; +}; + +/* descriptor ring for free buffers contains page-sized buffers. the index + * value is not used by the hw in any way. it's just stored and returned in + * the completion ring. + */ +struct cas_rx_desc { + u64 index; + u64 buffer; +}; + +/* received packets are put on the completion ring. */ +/* word 1 */ +#define RX_COMP1_DATA_SIZE_MASK 0x0000000007FFE000ULL +#define RX_COMP1_DATA_SIZE_SHIFT 13 +#define RX_COMP1_DATA_OFF_MASK 0x000001FFF8000000ULL +#define RX_COMP1_DATA_OFF_SHIFT 27 +#define RX_COMP1_DATA_INDEX_MASK 0x007FFE0000000000ULL +#define RX_COMP1_DATA_INDEX_SHIFT 41 +#define RX_COMP1_SKIP_MASK 0x0180000000000000ULL +#define RX_COMP1_SKIP_SHIFT 55 +#define RX_COMP1_RELEASE_NEXT 0x0200000000000000ULL +#define RX_COMP1_SPLIT_PKT 0x0400000000000000ULL +#define RX_COMP1_RELEASE_FLOW 0x0800000000000000ULL +#define RX_COMP1_RELEASE_DATA 0x1000000000000000ULL +#define RX_COMP1_RELEASE_HDR 0x2000000000000000ULL +#define RX_COMP1_TYPE_MASK 0xC000000000000000ULL +#define RX_COMP1_TYPE_SHIFT 62 + +/* word 2 */ +#define RX_COMP2_NEXT_INDEX_MASK 0x00000007FFE00000ULL +#define RX_COMP2_NEXT_INDEX_SHIFT 21 +#define RX_COMP2_HDR_SIZE_MASK 0x00000FF800000000ULL +#define RX_COMP2_HDR_SIZE_SHIFT 35 +#define RX_COMP2_HDR_OFF_MASK 0x0003F00000000000ULL +#define RX_COMP2_HDR_OFF_SHIFT 44 +#define RX_COMP2_HDR_INDEX_MASK 0xFFFC000000000000ULL +#define RX_COMP2_HDR_INDEX_SHIFT 50 + +/* word 3 */ +#define RX_COMP3_SMALL_PKT 0x0000000000000001ULL +#define RX_COMP3_JUMBO_PKT 0x0000000000000002ULL +#define RX_COMP3_JUMBO_HDR_SPLIT_EN 0x0000000000000004ULL +#define RX_COMP3_CSUM_START_MASK 0x000000000007F000ULL +#define RX_COMP3_CSUM_START_SHIFT 12 +#define RX_COMP3_FLOWID_MASK 0x0000000001F80000ULL +#define RX_COMP3_FLOWID_SHIFT 19 +#define RX_COMP3_OPCODE_MASK 0x000000000E000000ULL +#define RX_COMP3_OPCODE_SHIFT 25 +#define RX_COMP3_FORCE_FLAG 0x0000000010000000ULL +#define RX_COMP3_NO_ASSIST 0x0000000020000000ULL +#define RX_COMP3_LOAD_BAL_MASK 0x000001F800000000ULL +#define RX_COMP3_LOAD_BAL_SHIFT 35 +#define RX_PLUS_COMP3_ENC_PKT 0x0000020000000000ULL /* cas+ */ +#define RX_COMP3_L3_HEAD_OFF_MASK 0x0000FE0000000000ULL /* cas */ +#define RX_COMP3_L3_HEAD_OFF_SHIFT 41 +#define RX_PLUS_COMP_L3_HEAD_OFF_MASK 0x0000FC0000000000ULL /* cas+ */ +#define RX_PLUS_COMP_L3_HEAD_OFF_SHIFT 42 +#define RX_COMP3_SAP_MASK 0xFFFF000000000000ULL +#define RX_COMP3_SAP_SHIFT 48 + +/* word 4 */ +#define RX_COMP4_TCP_CSUM_MASK 0x000000000000FFFFULL +#define RX_COMP4_TCP_CSUM_SHIFT 0 +#define RX_COMP4_PKT_LEN_MASK 0x000000003FFF0000ULL +#define RX_COMP4_PKT_LEN_SHIFT 16 +#define RX_COMP4_PERFECT_MATCH_MASK 0x00000003C0000000ULL +#define RX_COMP4_PERFECT_MATCH_SHIFT 30 +#define RX_COMP4_ZERO 0x0000080000000000ULL +#define RX_COMP4_HASH_VAL_MASK 0x0FFFF00000000000ULL +#define RX_COMP4_HASH_VAL_SHIFT 44 +#define RX_COMP4_HASH_PASS 0x1000000000000000ULL +#define RX_COMP4_BAD 0x4000000000000000ULL +#define RX_COMP4_LEN_MISMATCH 0x8000000000000000ULL + +/* we encode the following: ring/index/release. only 14 bits + * are usable. + * NOTE: the encoding is dependent upon RX_DESC_RING_SIZE and + * MAX_RX_DESC_RINGS. */ +#define RX_INDEX_NUM_MASK 0x0000000000000FFFULL +#define RX_INDEX_NUM_SHIFT 0 +#define RX_INDEX_RING_MASK 0x0000000000001000ULL +#define RX_INDEX_RING_SHIFT 12 +#define RX_INDEX_RELEASE 0x0000000000002000ULL + +struct cas_rx_comp { + u64 word1; + u64 word2; + u64 word3; + u64 word4; +}; + +enum link_state { + link_down = 0, /* No link, will retry */ + link_aneg, /* Autoneg in progress */ + link_force_try, /* Try Forced link speed */ + link_force_ret, /* Forced mode worked, retrying autoneg */ + link_force_ok, /* Stay in forced mode */ + link_up /* Link is up */ +}; + +typedef struct cas_page { + struct list_head list; + struct page *buffer; + dma_addr_t dma_addr; + int used; +} cas_page_t; + + +/* some alignment constraints: + * TX DESC, RX DESC, and RX COMP must each be 8K aligned. + * TX COMPWB must be 8-byte aligned. + * to accomplish this, here's what we do: + * + * INIT_BLOCK_RX_COMP = 64k (already aligned) + * INIT_BLOCK_RX_DESC = 8k + * INIT_BLOCK_TX = 8k + * INIT_BLOCK_RX1_DESC = 8k + * TX COMPWB + */ +#define INIT_BLOCK_TX (TX_DESC_RING_SIZE) +#define INIT_BLOCK_RX_DESC (RX_DESC_RING_SIZE) +#define INIT_BLOCK_RX_COMP (RX_COMP_RING_SIZE) + +struct cas_init_block { + struct cas_rx_comp rxcs[N_RX_COMP_RINGS][INIT_BLOCK_RX_COMP]; + struct cas_rx_desc rxds[N_RX_DESC_RINGS][INIT_BLOCK_RX_DESC]; + struct cas_tx_desc txds[N_TX_RINGS][INIT_BLOCK_TX]; + u64 tx_compwb; +}; + +/* tiny buffers to deal with target abort issue. we allocate a bit + * over so that we don't have target abort issues with these buffers + * as well. + */ +#define TX_TINY_BUF_LEN 0x100 +#define TX_TINY_BUF_BLOCK ((INIT_BLOCK_TX + 1)*TX_TINY_BUF_LEN) + +struct cas_tiny_count { + int nbufs; + int used; +}; + +struct cas { + spinlock_t lock; /* for most bits */ + spinlock_t tx_lock[N_TX_RINGS]; /* tx bits */ + spinlock_t stat_lock[N_TX_RINGS + 1]; /* for stat gathering */ + spinlock_t rx_inuse_lock; /* rx inuse list */ + spinlock_t rx_spare_lock; /* rx spare list */ + + void __iomem *regs; + int tx_new[N_TX_RINGS], tx_old[N_TX_RINGS]; + int rx_old[N_RX_DESC_RINGS]; + int rx_cur[N_RX_COMP_RINGS], rx_new[N_RX_COMP_RINGS]; + int rx_last[N_RX_DESC_RINGS]; + + /* Set when chip is actually in operational state + * (ie. not power managed) */ + int hw_running; + int opened; + struct semaphore pm_sem; /* open/close/suspend/resume */ + + struct cas_init_block *init_block; + struct cas_tx_desc *init_txds[MAX_TX_RINGS]; + struct cas_rx_desc *init_rxds[MAX_RX_DESC_RINGS]; + struct cas_rx_comp *init_rxcs[MAX_RX_COMP_RINGS]; + + /* we use sk_buffs for tx and pages for rx. the rx skbuffs + * are there for flow re-assembly. */ + struct sk_buff *tx_skbs[N_TX_RINGS][TX_DESC_RING_SIZE]; + struct sk_buff_head rx_flows[N_RX_FLOWS]; + cas_page_t *rx_pages[N_RX_DESC_RINGS][RX_DESC_RING_SIZE]; + struct list_head rx_spare_list, rx_inuse_list; + int rx_spares_needed; + + /* for small packets when copying would be quicker than + mapping */ + struct cas_tiny_count tx_tiny_use[N_TX_RINGS][TX_DESC_RING_SIZE]; + u8 *tx_tiny_bufs[N_TX_RINGS]; + + u32 msg_enable; + + /* N_TX_RINGS must be >= N_RX_DESC_RINGS */ + struct net_device_stats net_stats[N_TX_RINGS + 1]; + + u32 pci_cfg[64 >> 2]; + u8 pci_revision; + + int phy_type; + int phy_addr; + u32 phy_id; +#define CAS_FLAG_1000MB_CAP 0x00000001 +#define CAS_FLAG_REG_PLUS 0x00000002 +#define CAS_FLAG_TARGET_ABORT 0x00000004 +#define CAS_FLAG_SATURN 0x00000008 +#define CAS_FLAG_RXD_POST_MASK 0x000000F0 +#define CAS_FLAG_RXD_POST_SHIFT 4 +#define CAS_FLAG_RXD_POST(x) ((1 << (CAS_FLAG_RXD_POST_SHIFT + (x))) & \ + CAS_FLAG_RXD_POST_MASK) +#define CAS_FLAG_ENTROPY_DEV 0x00000100 +#define CAS_FLAG_NO_HW_CSUM 0x00000200 + u32 cas_flags; + int packet_min; /* minimum packet size */ + int tx_fifo_size; + int rx_fifo_size; + int rx_pause_off; + int rx_pause_on; + int crc_size; /* 4 if half-duplex */ + + int pci_irq_INTC; + int min_frame_size; /* for tx fifo workaround */ + + /* page size allocation */ + int page_size; + int page_order; + int mtu_stride; + + u32 mac_rx_cfg; + + /* Autoneg & PHY control */ + int link_cntl; + int link_fcntl; + enum link_state lstate; + struct timer_list link_timer; + int timer_ticks; + struct work_struct reset_task; +#if 0 + atomic_t reset_task_pending; +#else + atomic_t reset_task_pending; + atomic_t reset_task_pending_mtu; + atomic_t reset_task_pending_spare; + atomic_t reset_task_pending_all; +#endif + +#ifdef CONFIG_CASSINI_QGE_DEBUG + atomic_t interrupt_seen; /* 1 if any interrupts are getting through */ +#endif + + /* Link-down problem workaround */ +#define LINK_TRANSITION_UNKNOWN 0 +#define LINK_TRANSITION_ON_FAILURE 1 +#define LINK_TRANSITION_STILL_FAILED 2 +#define LINK_TRANSITION_LINK_UP 3 +#define LINK_TRANSITION_LINK_CONFIG 4 +#define LINK_TRANSITION_LINK_DOWN 5 +#define LINK_TRANSITION_REQUESTED_RESET 6 + int link_transition; + int link_transition_jiffies_valid; + unsigned long link_transition_jiffies; + + /* Tuning */ + u8 orig_cacheline_size; /* value when loaded */ +#define CAS_PREF_CACHELINE_SIZE 0x20 /* Minimum desired */ + + /* Diagnostic counters and state. */ + int casreg_len; /* reg-space size for dumping */ + u64 pause_entered; + u16 pause_last_time_recvd; + + dma_addr_t block_dvma, tx_tiny_dvma[N_TX_RINGS]; + struct pci_dev *pdev; + struct net_device *dev; +}; + +#define TX_DESC_NEXT(r, x) (((x) + 1) & (TX_DESC_RINGN_SIZE(r) - 1)) +#define RX_DESC_ENTRY(r, x) ((x) & (RX_DESC_RINGN_SIZE(r) - 1)) +#define RX_COMP_ENTRY(r, x) ((x) & (RX_COMP_RINGN_SIZE(r) - 1)) + +#define TX_BUFF_COUNT(r, x, y) ((x) <= (y) ? ((y) - (x)) : \ + (TX_DESC_RINGN_SIZE(r) - (x) + (y))) + +#define TX_BUFFS_AVAIL(cp, i) ((cp)->tx_old[(i)] <= (cp)->tx_new[(i)] ? \ + (cp)->tx_old[(i)] + (TX_DESC_RINGN_SIZE(i) - 1) - (cp)->tx_new[(i)] : \ + (cp)->tx_old[(i)] - (cp)->tx_new[(i)] - 1) + +#define CAS_ALIGN(addr, align) \ + (((unsigned long) (addr) + ((align) - 1UL)) & ~((align) - 1)) + +#define RX_FIFO_SIZE 16384 +#define EXPANSION_ROM_SIZE 65536 + +#define CAS_MC_EXACT_MATCH_SIZE 15 +#define CAS_MC_HASH_SIZE 256 +#define CAS_MC_HASH_MAX (CAS_MC_EXACT_MATCH_SIZE + \ + CAS_MC_HASH_SIZE) + +#define TX_TARGET_ABORT_LEN 0x20 +#define RX_SWIVEL_OFF_VAL 0x2 +#define RX_AE_FREEN_VAL(x) (RX_DESC_RINGN_SIZE(x) >> 1) +#define RX_AE_COMP_VAL (RX_COMP_RING_SIZE >> 1) +#define RX_BLANK_INTR_PKT_VAL 0x05 +#define RX_BLANK_INTR_TIME_VAL 0x0F +#define HP_TCP_THRESH_VAL 1530 /* reduce to enable reassembly */ + +#define RX_SPARE_COUNT (RX_DESC_RING_SIZE >> 1) +#define RX_SPARE_RECOVER_VAL (RX_SPARE_COUNT >> 2) + +#endif /* _CASSINI_H */ diff --git a/include/linux/pci_ids.h b/include/linux/pci_ids.h index 68f11ac1a31..eb36fd293b4 100644 --- a/include/linux/pci_ids.h +++ b/include/linux/pci_ids.h @@ -392,6 +392,7 @@ #define PCI_DEVICE_ID_NS_87560_USB 0x0012 #define PCI_DEVICE_ID_NS_83815 0x0020 #define PCI_DEVICE_ID_NS_83820 0x0022 +#define PCI_DEVICE_ID_NS_SATURN 0x0035 #define PCI_DEVICE_ID_NS_SCx200_BRIDGE 0x0500 #define PCI_DEVICE_ID_NS_SCx200_SMI 0x0501 #define PCI_DEVICE_ID_NS_SCx200_IDE 0x0502 @@ -983,6 +984,7 @@ #define PCI_DEVICE_ID_SUN_SABRE 0xa000 #define PCI_DEVICE_ID_SUN_HUMMINGBIRD 0xa001 #define PCI_DEVICE_ID_SUN_TOMATILLO 0xa801 +#define PCI_DEVICE_ID_SUN_CASSINI 0xabba #define PCI_VENDOR_ID_CMD 0x1095 #define PCI_DEVICE_ID_CMD_640 0x0640 -- cgit v1.2.3 From c3c4ed652e8f2c348ebdd3f2e45664a0e238ee52 Mon Sep 17 00:00:00 2001 From: Alexey Dobriyan Date: Tue, 27 Sep 2005 15:42:58 -0700 Subject: [ROSE]: do proto_unregister() on exit paths Signed-off-by: Alexey Dobriyan Signed-off-by: David S. Miller --- net/rose/af_rose.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/net/rose/af_rose.c b/net/rose/af_rose.c index 5acb1680524..a190eaee702 100644 --- a/net/rose/af_rose.c +++ b/net/rose/af_rose.c @@ -1481,12 +1481,14 @@ static int __init rose_proto_init(void) if (rose_ndevs > 0x7FFFFFFF/sizeof(struct net_device *)) { printk(KERN_ERR "ROSE: rose_proto_init - rose_ndevs parameter to large\n"); + proto_unregister(&rose_proto); return -1; } dev_rose = kmalloc(rose_ndevs * sizeof(struct net_device *), GFP_KERNEL); if (dev_rose == NULL) { printk(KERN_ERR "ROSE: rose_proto_init - unable to allocate device structure\n"); + proto_unregister(&rose_proto); return -1; } -- cgit v1.2.3 From 70ff3b66d79c5110e533f3f2aea1a5b2fc5f8d90 Mon Sep 17 00:00:00 2001 From: Alexey Dobriyan Date: Tue, 27 Sep 2005 15:43:46 -0700 Subject: [ROSE]: return sane -E* from rose_proto_init() Signed-off-by: Alexey Dobriyan Signed-off-by: David S. Miller --- net/rose/af_rose.c | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/net/rose/af_rose.c b/net/rose/af_rose.c index a190eaee702..dbfb0e3dc79 100644 --- a/net/rose/af_rose.c +++ b/net/rose/af_rose.c @@ -1482,14 +1482,14 @@ static int __init rose_proto_init(void) if (rose_ndevs > 0x7FFFFFFF/sizeof(struct net_device *)) { printk(KERN_ERR "ROSE: rose_proto_init - rose_ndevs parameter to large\n"); proto_unregister(&rose_proto); - return -1; + return -EINVAL; } dev_rose = kmalloc(rose_ndevs * sizeof(struct net_device *), GFP_KERNEL); if (dev_rose == NULL) { printk(KERN_ERR "ROSE: rose_proto_init - unable to allocate device structure\n"); proto_unregister(&rose_proto); - return -1; + return -ENOMEM; } memset(dev_rose, 0x00, rose_ndevs * sizeof(struct net_device*)); @@ -1502,9 +1502,11 @@ static int __init rose_proto_init(void) name, rose_setup); if (!dev) { printk(KERN_ERR "ROSE: rose_proto_init - unable to allocate memory\n"); + rc = -ENOMEM; goto fail; } - if (register_netdev(dev)) { + rc = register_netdev(dev); + if (rc) { printk(KERN_ERR "ROSE: netdevice regeistration failed\n"); free_netdev(dev); goto fail; @@ -1539,7 +1541,7 @@ fail: } kfree(dev_rose); proto_unregister(&rose_proto); - return -ENOMEM; + goto out; } module_init(rose_proto_init); -- cgit v1.2.3 From a83cd2cc90bd9390cf03cd40bba204d9ed520633 Mon Sep 17 00:00:00 2001 From: Alexey Dobriyan Date: Tue, 27 Sep 2005 15:44:36 -0700 Subject: [ROSE]: check rose_ndevs earlier * Don't bother with proto registering if rose_ndevs is bad. * Make escape structure more coherent. Signed-off-by: Alexey Dobriyan Signed-off-by: David S. Miller --- net/rose/af_rose.c | 20 +++++++++++--------- 1 file changed, 11 insertions(+), 9 deletions(-) diff --git a/net/rose/af_rose.c b/net/rose/af_rose.c index dbfb0e3dc79..0f96565a64e 100644 --- a/net/rose/af_rose.c +++ b/net/rose/af_rose.c @@ -1472,24 +1472,25 @@ static const char banner[] = KERN_INFO "F6FBB/G4KLX ROSE for Linux. Version 0.62 static int __init rose_proto_init(void) { int i; - int rc = proto_register(&rose_proto, 0); + int rc; + if (rose_ndevs > 0x7FFFFFFF/sizeof(struct net_device *)) { + printk(KERN_ERR "ROSE: rose_proto_init - rose_ndevs parameter to large\n"); + rc = -EINVAL; + goto out; + } + + rc = proto_register(&rose_proto, 0); if (rc != 0) goto out; rose_callsign = null_ax25_address; - if (rose_ndevs > 0x7FFFFFFF/sizeof(struct net_device *)) { - printk(KERN_ERR "ROSE: rose_proto_init - rose_ndevs parameter to large\n"); - proto_unregister(&rose_proto); - return -EINVAL; - } - dev_rose = kmalloc(rose_ndevs * sizeof(struct net_device *), GFP_KERNEL); if (dev_rose == NULL) { printk(KERN_ERR "ROSE: rose_proto_init - unable to allocate device structure\n"); - proto_unregister(&rose_proto); - return -ENOMEM; + rc = -ENOMEM; + goto out_proto_unregister; } memset(dev_rose, 0x00, rose_ndevs * sizeof(struct net_device*)); @@ -1540,6 +1541,7 @@ fail: free_netdev(dev_rose[i]); } kfree(dev_rose); +out_proto_unregister: proto_unregister(&rose_proto); goto out; } -- cgit v1.2.3 From 520d1b830a93086c1f9e969d98f7ef01f0356493 Mon Sep 17 00:00:00 2001 From: Alexey Dobriyan Date: Tue, 27 Sep 2005 15:45:15 -0700 Subject: [ROSE]: fix typo (regeistration) Signed-off-by: Alexey Dobriyan Signed-off-by: David S. Miller --- net/rose/af_rose.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/rose/af_rose.c b/net/rose/af_rose.c index 0f96565a64e..829fdbc4400 100644 --- a/net/rose/af_rose.c +++ b/net/rose/af_rose.c @@ -1508,7 +1508,7 @@ static int __init rose_proto_init(void) } rc = register_netdev(dev); if (rc) { - printk(KERN_ERR "ROSE: netdevice regeistration failed\n"); + printk(KERN_ERR "ROSE: netdevice registration failed\n"); free_netdev(dev); goto fail; } -- cgit v1.2.3 From 2fab35d78f32fc107e1af4b1ec23f557fa20d911 Mon Sep 17 00:00:00 2001 From: Ben Dooks Date: Tue, 27 Sep 2005 15:59:43 -0700 Subject: [NET]: Fix GCC4 compile error: sysctl in linux/if_ether.h The following is generated when compiling a recent (2.6.14-rc2-git5) kernel configured for ARM, with GCC4. CC init/main.o In file included from include/linux/netdevice.h:29, from include/net/sock.h:48, from init/main.c:50: include/linux/if_ether.h:114: error: array type has incomplete element type It seems that if CONFIG_SYSCTL is not set, then the compiler will throw an error due to the definition of the ether_table[] array Attached is a solution to the problem Signed-off-by: Ben Dooks Signed-off-by: David S. Miller --- include/linux/if_ether.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/include/linux/if_ether.h b/include/linux/if_ether.h index fc2d4c8225a..d21c305c6c6 100644 --- a/include/linux/if_ether.h +++ b/include/linux/if_ether.h @@ -111,7 +111,9 @@ static inline struct ethhdr *eth_hdr(const struct sk_buff *skb) return (struct ethhdr *)skb->mac.raw; } +#ifdef CONFIG_SYSCTL extern struct ctl_table ether_table[]; #endif +#endif #endif /* _LINUX_IF_ETHER_H */ -- cgit v1.2.3 From ba645c16026ed733a51f904df34756f61bc155fc Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Tue, 27 Sep 2005 16:03:05 -0700 Subject: [NET]: Slightly optimize ethernet address comparison. We know the thing is at least 2-byte aligned, so take advantage of that instead of invoking memcmp() which results in truly horrifically inefficient code because it can't assume anything about alignment. Signed-off-by: David S. Miller --- net/ethernet/eth.c | 31 +++++++++++++++++++++---------- 1 file changed, 21 insertions(+), 10 deletions(-) diff --git a/net/ethernet/eth.c b/net/ethernet/eth.c index 87a052a9a84..8b299cc8206 100644 --- a/net/ethernet/eth.c +++ b/net/ethernet/eth.c @@ -146,6 +146,19 @@ int eth_rebuild_header(struct sk_buff *skb) return 0; } +static inline unsigned int compare_eth_addr(const unsigned char *__a, const unsigned char *__b) +{ + const unsigned short *dest = (unsigned short *) __a; + const unsigned short *devaddr = (unsigned short *) __b; + unsigned int res; + + BUILD_BUG_ON(ETH_ALEN != 6); + res = ((dest[0] ^ devaddr[0]) | + (dest[1] ^ devaddr[1]) | + (dest[2] ^ devaddr[2])) != 0; + + return res; +} /* * Determine the packet's protocol ID. The rule here is that we @@ -158,16 +171,15 @@ __be16 eth_type_trans(struct sk_buff *skb, struct net_device *dev) struct ethhdr *eth; unsigned char *rawp; - skb->mac.raw=skb->data; + skb->mac.raw = skb->data; skb_pull(skb,ETH_HLEN); eth = eth_hdr(skb); - if(*eth->h_dest&1) - { - if(memcmp(eth->h_dest,dev->broadcast, ETH_ALEN)==0) - skb->pkt_type=PACKET_BROADCAST; + if (*eth->h_dest&1) { + if (!compare_eth_addr(eth->h_dest, dev->broadcast)) + skb->pkt_type = PACKET_BROADCAST; else - skb->pkt_type=PACKET_MULTICAST; + skb->pkt_type = PACKET_MULTICAST; } /* @@ -178,10 +190,9 @@ __be16 eth_type_trans(struct sk_buff *skb, struct net_device *dev) * seems to set IFF_PROMISC. */ - else if(1 /*dev->flags&IFF_PROMISC*/) - { - if(memcmp(eth->h_dest,dev->dev_addr, ETH_ALEN)) - skb->pkt_type=PACKET_OTHERHOST; + else if(1 /*dev->flags&IFF_PROMISC*/) { + if (unlikely(!compare_eth_addr(eth->h_dest, dev->dev_addr))) + skb->pkt_type = PACKET_OTHERHOST; } if (ntohs(eth->h_proto) >= 1536) -- cgit v1.2.3 From 64233bffbb50f12e576c61d1698a573c8033004a Mon Sep 17 00:00:00 2001 From: Oliver Dawid Date: Tue, 27 Sep 2005 16:11:29 -0700 Subject: [APPLETALK]: Fix broadcast bug. From: Oliver Dawid we found a bug in net/appletalk/ddp.c concerning broadcast packets. In kernel 2.4 it was working fine. The bug first occured 4 years ago when switching to new SNAP layer handling. This bug can be splitted up into a sending(1) and reception(2) problem: Sending(1) In kernel 2.4 broadcast packets were sent to a matching ethernet device and atalk_rcv() was called to receive it as "loopback" (so loopback packets were shortcutted and handled in DDP layer). When switching to the new SNAP structure, this shortcut was removed and the loopback packet was send to SNAP layer. The author forgot to replace the remote device pointer by the loopback device pointer before sending the packet to SNAP layer (by calling ddp_dl->request() ) therfor the packet was not sent back by underlying layers to ddp's atalk_rcv(). Reception(2) In atalk_rcv() a packet received by this loopback mechanism contains now the (rigth) loopback device pointer (in Kernel 2.4 it was the (wrong) remote ethernet device pointer) and therefor no matching socket will be found to deliver this packet to. Because a broadcast packet should be send to the first matching socket (as it is done in many other protocols (?)), we removed the network comparison in broadcast case. Below you will find a patch to correct this bug. Its diffed to kernel 2.6.14-rc1 Signed-off-by: Arnaldo Carvalho de Melo Signed-off-by: David S. Miller --- net/appletalk/ddp.c | 31 ++++++++++++++++++++++--------- 1 file changed, 22 insertions(+), 9 deletions(-) diff --git a/net/appletalk/ddp.c b/net/appletalk/ddp.c index 1d31b3a3f1e..7982656b9c8 100644 --- a/net/appletalk/ddp.c +++ b/net/appletalk/ddp.c @@ -100,8 +100,7 @@ static struct sock *atalk_search_socket(struct sockaddr_at *to, continue; if (to->sat_addr.s_net == ATADDR_ANYNET && - to->sat_addr.s_node == ATADDR_BCAST && - at->src_net == atif->address.s_net) + to->sat_addr.s_node == ATADDR_BCAST) goto found; if (to->sat_addr.s_net == at->src_net && @@ -1443,8 +1442,10 @@ static int atalk_rcv(struct sk_buff *skb, struct net_device *dev, else atif = atalk_find_interface(ddp->deh_dnet, ddp->deh_dnode); - /* Not ours, so we route the packet via the correct AppleTalk iface */ if (!atif) { + /* Not ours, so we route the packet via the correct + * AppleTalk iface + */ atalk_route_packet(skb, dev, ddp, &ddphv, origlen); goto out; } @@ -1592,9 +1593,6 @@ static int atalk_sendmsg(struct kiocb *iocb, struct socket *sock, struct msghdr if (usat->sat_addr.s_net || usat->sat_addr.s_node == ATADDR_ANYNODE) { rt = atrtr_find(&usat->sat_addr); - if (!rt) - return -ENETUNREACH; - dev = rt->dev; } else { struct atalk_addr at_hint; @@ -1603,11 +1601,12 @@ static int atalk_sendmsg(struct kiocb *iocb, struct socket *sock, struct msghdr at_hint.s_net = at->src_net; rt = atrtr_find(&at_hint); - if (!rt) - return -ENETUNREACH; - dev = rt->dev; } + if (!rt) + return -ENETUNREACH; + + dev = rt->dev; SOCK_DEBUG(sk, "SK %p: Size needed %d, device %s\n", sk, size, dev->name); @@ -1677,6 +1676,20 @@ static int atalk_sendmsg(struct kiocb *iocb, struct socket *sock, struct msghdr SOCK_DEBUG(sk, "SK %p: Loop back.\n", sk); /* loop back */ skb_orphan(skb); + if (ddp->deh_dnode == ATADDR_BCAST) { + struct atalk_addr at_lo; + + at_lo.s_node = 0; + at_lo.s_net = 0; + + rt = atrtr_find(&at_lo); + if (!rt) { + kfree_skb(skb); + return -ENETUNREACH; + } + dev = rt->dev; + skb->dev = dev; + } ddp_dl->request(ddp_dl, skb, dev->dev_addr); } else { SOCK_DEBUG(sk, "SK %p: send out.\n", sk); -- cgit v1.2.3 From f16af555cc46a724507da371fbac94b430c93315 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Tue, 27 Sep 2005 22:37:08 -0700 Subject: [SPARC64]: Add defines for 32MB/256MB PTE page size on Ultra-IV+. Signed-off-by: David S. Miller --- include/asm-sparc64/pgtable.h | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/include/asm-sparc64/pgtable.h b/include/asm-sparc64/pgtable.h index 43cbb089cde..53d612aba8d 100644 --- a/include/asm-sparc64/pgtable.h +++ b/include/asm-sparc64/pgtable.h @@ -98,7 +98,9 @@ #define _PAGE_NFO _AC(0x1000000000000000,UL) /* No Fault Only */ #define _PAGE_IE _AC(0x0800000000000000,UL) /* Invert Endianness */ #define _PAGE_SOFT2 _AC(0x07FC000000000000,UL) /* Software bits, set 2 */ -#define _PAGE_RES1 _AC(0x0003000000000000,UL) /* Reserved */ +#define _PAGE_RES1 _AC(0x0002000000000000,UL) /* Reserved */ +#define _PAGE_SZ32MB _AC(0x0001000000000000,UL) /* (Panther) 32MB page */ +#define _PAGE_SZ256MB _AC(0x2001000000000000,UL) /* (Panther) 256MB page */ #define _PAGE_SN _AC(0x0000800000000000,UL) /* (Cheetah) Snoop */ #define _PAGE_RES2 _AC(0x0000780000000000,UL) /* Reserved */ #define _PAGE_PADDR_SF _AC(0x000001FFFFFFE000,UL) /* (Spitfire) paddr[40:13]*/ -- cgit v1.2.3 From d2212bc7db13268bef0799d9ff4b2e511c284885 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Tue, 27 Sep 2005 22:50:06 -0700 Subject: [SPARC64]: Add missing IDs for newer cpus. Also, the us3_cpufreq driver can work on Ultra-IV and IV+. They use the SAFARI bus register to control the clock divider just like Ultra-III and III+ do. Signed-off-by: David S. Miller --- arch/sparc64/kernel/cpu.c | 4 ++++ arch/sparc64/kernel/us3_cpufreq.c | 5 ++++- include/asm-sparc64/head.h | 9 ++++++--- 3 files changed, 14 insertions(+), 4 deletions(-) diff --git a/arch/sparc64/kernel/cpu.c b/arch/sparc64/kernel/cpu.c index 48756958116..77ef5df4e5a 100644 --- a/arch/sparc64/kernel/cpu.c +++ b/arch/sparc64/kernel/cpu.c @@ -39,6 +39,8 @@ struct cpu_fp_info linux_sparc_fpu[] = { { 0x3e, 0x15, 0, "UltraSparc III+ integrated FPU"}, { 0x3e, 0x16, 0, "UltraSparc IIIi integrated FPU"}, { 0x3e, 0x18, 0, "UltraSparc IV integrated FPU"}, + { 0x3e, 0x19, 0, "UltraSparc IV+ integrated FPU"}, + { 0x3e, 0x22, 0, "UltraSparc IIIi+ integrated FPU"}, }; #define NSPARCFPU (sizeof(linux_sparc_fpu)/sizeof(struct cpu_fp_info)) @@ -53,6 +55,8 @@ struct cpu_iu_info linux_sparc_chips[] = { { 0x3e, 0x15, "TI UltraSparc III+ (Cheetah+)"}, { 0x3e, 0x16, "TI UltraSparc IIIi (Jalapeno)"}, { 0x3e, 0x18, "TI UltraSparc IV (Jaguar)"}, + { 0x3e, 0x19, "TI UltraSparc IV+ (Panther)"}, + { 0x3e, 0x22, "TI UltraSparc IIIi+ (Serrano)"}, }; #define NSPARCCHIPS (sizeof(linux_sparc_chips)/sizeof(struct cpu_iu_info)) diff --git a/arch/sparc64/kernel/us3_cpufreq.c b/arch/sparc64/kernel/us3_cpufreq.c index 9080e7cd4bb..0340041f614 100644 --- a/arch/sparc64/kernel/us3_cpufreq.c +++ b/arch/sparc64/kernel/us3_cpufreq.c @@ -208,7 +208,10 @@ static int __init us3_freq_init(void) impl = ((ver >> 32) & 0xffff); if (manuf == CHEETAH_MANUF && - (impl == CHEETAH_IMPL || impl == CHEETAH_PLUS_IMPL)) { + (impl == CHEETAH_IMPL || + impl == CHEETAH_PLUS_IMPL || + impl == JAGUAR_IMPL || + impl == PANTHER_IMPL)) { struct cpufreq_driver *driver; ret = -ENOMEM; diff --git a/include/asm-sparc64/head.h b/include/asm-sparc64/head.h index b63a33cf497..0abd3a674e8 100644 --- a/include/asm-sparc64/head.h +++ b/include/asm-sparc64/head.h @@ -12,9 +12,12 @@ #define __JALAPENO_ID 0x003e0016 #define CHEETAH_MANUF 0x003e -#define CHEETAH_IMPL 0x0014 -#define CHEETAH_PLUS_IMPL 0x0015 -#define JALAPENO_IMPL 0x0016 +#define CHEETAH_IMPL 0x0014 /* Ultra-III */ +#define CHEETAH_PLUS_IMPL 0x0015 /* Ultra-III+ */ +#define JALAPENO_IMPL 0x0016 /* Ultra-IIIi */ +#define JAGUAR_IMPL 0x0018 /* Ultra-IV */ +#define PANTHER_IMPL 0x0019 /* Ultra-IV+ */ +#define SERRANO_IMPL 0x0022 /* Ultra-IIIi+ */ #define BRANCH_IF_CHEETAH_BASE(tmp1,tmp2,label) \ rdpr %ver, %tmp1; \ -- cgit v1.2.3 From 1146bc743e074760ef0dd08b3457f35a68069a54 Mon Sep 17 00:00:00 2001 From: Dominik Brodowski Date: Wed, 28 Sep 2005 19:28:37 +0200 Subject: [PATCH] pcmcia: allow one port excludes Allow for excluding only one port in /etc/pcmcia/config.otps Signed-off-by: Dominik Brodowski --- drivers/pcmcia/rsrc_nonstatic.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/drivers/pcmcia/rsrc_nonstatic.c b/drivers/pcmcia/rsrc_nonstatic.c index c42455d20eb..7e1b7fcd833 100644 --- a/drivers/pcmcia/rsrc_nonstatic.c +++ b/drivers/pcmcia/rsrc_nonstatic.c @@ -691,7 +691,7 @@ static int adjust_memory(struct pcmcia_socket *s, unsigned int action, unsigned unsigned long size = end - start + 1; int ret = 0; - if (end <= start) + if (end < start) return -EINVAL; down(&rsrc_sem); @@ -724,7 +724,7 @@ static int adjust_io(struct pcmcia_socket *s, unsigned int action, unsigned long unsigned long size = end - start + 1; int ret = 0; - if (end <= start) + if (end < start) return -EINVAL; if (end > IO_SPACE_LIMIT) @@ -925,7 +925,7 @@ static ssize_t store_io_db(struct class_device *class_dev, const char *buf, size return -EINVAL; } } - if (end_addr <= start_addr) + if (end_addr < start_addr) return -EINVAL; ret = adjust_io(s, add, start_addr, end_addr); @@ -977,7 +977,7 @@ static ssize_t store_mem_db(struct class_device *class_dev, const char *buf, siz return -EINVAL; } } - if (end_addr <= start_addr) + if (end_addr < start_addr) return -EINVAL; ret = adjust_memory(s, add, start_addr, end_addr); -- cgit v1.2.3 From 54bb5675a6e966a58755ac44e3407f8ec2272b82 Mon Sep 17 00:00:00 2001 From: Dominik Brodowski Date: Wed, 28 Sep 2005 19:29:59 +0200 Subject: [PATCH] pcmcia: only start up nonstatic sockets if both mem and io are available Only start up nonstatic sockets if both IO and MEM resources are available. Thanks to Russell King and Matthew Wilcox for tracking this down. Signed-off-by: Dominik Brodowski --- drivers/pcmcia/rsrc_nonstatic.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/pcmcia/rsrc_nonstatic.c b/drivers/pcmcia/rsrc_nonstatic.c index 7e1b7fcd833..f9a5c70284b 100644 --- a/drivers/pcmcia/rsrc_nonstatic.c +++ b/drivers/pcmcia/rsrc_nonstatic.c @@ -817,7 +817,7 @@ static int nonstatic_autoadd_resources(struct pcmcia_socket *s) /* if we got at least one of IO, and one of MEM, we can be glad and * activate the PCMCIA subsystem */ - if (done & (IORESOURCE_MEM | IORESOURCE_IO)) + if (done == (IORESOURCE_MEM | IORESOURCE_IO)) s->resource_setup_done = 1; return 0; -- cgit v1.2.3 From 6b251858d377196b8cea20e65cae60f584a42735 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Wed, 28 Sep 2005 16:31:48 -0700 Subject: [TCP]: Fix init_cwnd calculations in tcp_select_initial_window() Match it up to what RFC2414 really specifies. Noticed by Rick Jones. Signed-off-by: David S. Miller --- net/ipv4/tcp_output.c | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/net/ipv4/tcp_output.c b/net/ipv4/tcp_output.c index d6e3d269e90..caf2e2cff29 100644 --- a/net/ipv4/tcp_output.c +++ b/net/ipv4/tcp_output.c @@ -190,15 +190,16 @@ void tcp_select_initial_window(int __space, __u32 mss, } /* Set initial window to value enough for senders, - * following RFC1414. Senders, not following this RFC, + * following RFC2414. Senders, not following this RFC, * will be satisfied with 2. */ if (mss > (1<<*rcv_wscale)) { - int init_cwnd = 4; - if (mss > 1460*3) + int init_cwnd; + + if (mss > 1460) init_cwnd = 2; - else if (mss > 1460) - init_cwnd = 3; + else + init_cwnd = (mss > 1095) ? 3 : 4; if (*rcv_wnd > init_cwnd*mss) *rcv_wnd = init_cwnd*mss; } -- cgit v1.2.3 From e2c4b72158a9f1286df41dee478e774f1b94e93a Mon Sep 17 00:00:00 2001 From: Roman Kagan Date: Wed, 28 Sep 2005 16:34:24 -0700 Subject: [ATM]: net/atm/ioctl.c: autoload pppoatm and br2684 Signed-off-by: Roman Kagan Signed-off-by: Chas Williams --- net/atm/ioctl.c | 34 ++++++++++++++++++++++++++-------- 1 file changed, 26 insertions(+), 8 deletions(-) diff --git a/net/atm/ioctl.c b/net/atm/ioctl.c index d89056ec44d..a150198b05a 100644 --- a/net/atm/ioctl.c +++ b/net/atm/ioctl.c @@ -105,17 +105,35 @@ int vcc_ioctl(struct socket *sock, unsigned int cmd, unsigned long arg) if (!error) sock->state = SS_CONNECTED; goto done; - default: + case ATM_SETBACKEND: + case ATM_NEWBACKENDIF: + { + atm_backend_t backend; + error = get_user(backend, (atm_backend_t __user *) argp); + if (error) + goto done; + switch (backend) { + case ATM_BACKEND_PPP: + request_module("pppoatm"); + break; + case ATM_BACKEND_BR2684: + request_module("br2684"); + break; + } + } + break; + case ATMMPC_CTRL: + case ATMMPC_DATA: + request_module("mpoa"); + break; + case ATMARPD_CTRL: + request_module("clip"); + break; + case ATMLEC_CTRL: + request_module("lec"); break; } - if (cmd == ATMMPC_CTRL || cmd == ATMMPC_DATA) - request_module("mpoa"); - if (cmd == ATMARPD_CTRL) - request_module("clip"); - if (cmd == ATMLEC_CTRL) - request_module("lec"); - error = -ENOIOCTLCMD; down(&ioctl_mutex); -- cgit v1.2.3 From 9301e320e98ff19a0e48881b038d0c24ca76e6c0 Mon Sep 17 00:00:00 2001 From: Chas Williams Date: Wed, 28 Sep 2005 16:35:01 -0700 Subject: [ATM]: track and close listen sockets when sigd exits Signed-off-by: Chas Williams --- net/atm/common.c | 4 ++-- net/atm/signaling.c | 8 ++++---- net/atm/svc.c | 1 + 3 files changed, 7 insertions(+), 6 deletions(-) diff --git a/net/atm/common.c b/net/atm/common.c index e93e838069e..801a5813ec6 100644 --- a/net/atm/common.c +++ b/net/atm/common.c @@ -178,8 +178,6 @@ static void vcc_destroy_socket(struct sock *sk) if (vcc->push) vcc->push(vcc, NULL); /* atmarpd has no push */ - vcc_remove_socket(sk); /* no more receive */ - while ((skb = skb_dequeue(&sk->sk_receive_queue)) != NULL) { atm_return(vcc,skb->truesize); kfree_skb(skb); @@ -188,6 +186,8 @@ static void vcc_destroy_socket(struct sock *sk) module_put(vcc->dev->ops->owner); atm_dev_put(vcc->dev); } + + vcc_remove_socket(sk); } diff --git a/net/atm/signaling.c b/net/atm/signaling.c index f7c449ac180..e7211a7f382 100644 --- a/net/atm/signaling.c +++ b/net/atm/signaling.c @@ -217,8 +217,9 @@ void sigd_enq(struct atm_vcc *vcc,enum atmsvc_msg_type type, static void purge_vcc(struct atm_vcc *vcc) { if (sk_atm(vcc)->sk_family == PF_ATMSVC && - !test_bit(ATM_VF_META,&vcc->flags)) { - set_bit(ATM_VF_RELEASED,&vcc->flags); + !test_bit(ATM_VF_META, &vcc->flags)) { + set_bit(ATM_VF_RELEASED, &vcc->flags); + clear_bit(ATM_VF_REGIS, &vcc->flags); vcc_release_async(vcc, -EUNATCH); } } @@ -243,8 +244,7 @@ static void sigd_close(struct atm_vcc *vcc) sk_for_each(s, node, head) { struct atm_vcc *vcc = atm_sk(s); - if (vcc->dev) - purge_vcc(vcc); + purge_vcc(vcc); } } read_unlock(&vcc_sklist_lock); diff --git a/net/atm/svc.c b/net/atm/svc.c index 08e46052a3e..d7b266136bf 100644 --- a/net/atm/svc.c +++ b/net/atm/svc.c @@ -302,6 +302,7 @@ static int svc_listen(struct socket *sock,int backlog) error = -EINVAL; goto out; } + vcc_insert_socket(sk); set_bit(ATM_VF_WAITING, &vcc->flags); prepare_to_wait(sk->sk_sleep, &wait, TASK_UNINTERRUPTIBLE); sigd_enq(vcc,as_listen,NULL,NULL,&vcc->local); -- cgit v1.2.3 From 735631a9196db42631b8817892605ee72e13a58b Mon Sep 17 00:00:00 2001 From: Martin Whitaker Date: Wed, 28 Sep 2005 16:35:22 -0700 Subject: [ATM]: fix bug in atm address list handling From: Martin Whitaker Signed-off-by: Chas Williams --- net/atm/addr.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/net/atm/addr.c b/net/atm/addr.c index 1c8867f7f54..a30d0bf4806 100644 --- a/net/atm/addr.c +++ b/net/atm/addr.c @@ -50,8 +50,10 @@ void atm_reset_addr(struct atm_dev *dev) struct atm_dev_addr *this, *p; spin_lock_irqsave(&dev->lock, flags); - list_for_each_entry_safe(this, p, &dev->local, entry) - kfree(this); + list_for_each_entry_safe(this, p, &dev->local, entry) { + list_del(&this->entry); + kfree(this); + } spin_unlock_irqrestore(&dev->lock, flags); notify_sigd(dev); } -- cgit v1.2.3 From 705747ab87c96f1b4b8e73ba617c323d9087f6ac Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Wed, 28 Sep 2005 16:48:40 -0700 Subject: [SPARC64]: Fix bug in unaligned load endianness swapping The in-memory value was being swapped, not the value we loaded into the register. Signed-off-by: David S. Miller --- arch/sparc64/kernel/unaligned.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/arch/sparc64/kernel/unaligned.c b/arch/sparc64/kernel/unaligned.c index 42718f6a7d3..02af08ffec8 100644 --- a/arch/sparc64/kernel/unaligned.c +++ b/arch/sparc64/kernel/unaligned.c @@ -294,7 +294,7 @@ asmlinkage void kernel_unaligned_trap(struct pt_regs *regs, unsigned int insn, u kernel_mna_trap_fault(); } else { - unsigned long addr; + unsigned long addr, *reg_addr; int orig_asi, asi; addr = compute_effective_address(regs, insn, @@ -319,11 +319,11 @@ asmlinkage void kernel_unaligned_trap(struct pt_regs *regs, unsigned int insn, u }; switch (dir) { case load: - do_int_load(fetch_reg_addr(((insn>>25)&0x1f), regs), - size, (unsigned long *) addr, + reg_addr = fetch_reg_addr(((insn>>25)&0x1f), regs); + do_int_load(reg_addr, size, (unsigned long *) addr, decode_signedness(insn), asi); if (unlikely(asi != orig_asi)) { - unsigned long val_in = *(unsigned long *) addr; + unsigned long val_in = *reg_addr; switch (size) { case 2: val_in = swab16(val_in); @@ -339,7 +339,7 @@ asmlinkage void kernel_unaligned_trap(struct pt_regs *regs, unsigned int insn, u BUG(); break; }; - *(unsigned long *) addr = val_in; + *reg_addr = val_in; } break; -- cgit v1.2.3 From d70ed6075f15bdbb0548d162394bf10332769c88 Mon Sep 17 00:00:00 2001 From: Roland Dreier Date: Wed, 28 Sep 2005 19:56:57 -0700 Subject: [IPoIB] Rename IPoIB's path_lookup() to avoid name clashes Rename IPoIB driver's path_lookup() to ipoib_path_lookup() to avoid a clashes with the kernel global path_lookup(). We don't hit this with the current kernel source, but some external patches seem to trigger this, and it's cleaner to avoid clashing with global names anyway. Signed-off-by: Roland Dreier refs/heads/for-linus --- drivers/infiniband/ulp/ipoib/ipoib_main.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/infiniband/ulp/ipoib/ipoib_main.c b/drivers/infiniband/ulp/ipoib/ipoib_main.c index 704f48e0b6a..6c5bf07489f 100644 --- a/drivers/infiniband/ulp/ipoib/ipoib_main.c +++ b/drivers/infiniband/ulp/ipoib/ipoib_main.c @@ -474,7 +474,7 @@ err: spin_unlock(&priv->lock); } -static void path_lookup(struct sk_buff *skb, struct net_device *dev) +static void ipoib_path_lookup(struct sk_buff *skb, struct net_device *dev) { struct ipoib_dev_priv *priv = netdev_priv(skb->dev); @@ -569,7 +569,7 @@ static int ipoib_start_xmit(struct sk_buff *skb, struct net_device *dev) if (skb->dst && skb->dst->neighbour) { if (unlikely(!*to_ipoib_neigh(skb->dst->neighbour))) { - path_lookup(skb, dev); + ipoib_path_lookup(skb, dev); goto out; } -- cgit v1.2.3 From 8cf14af0a740fb7e9f94a203b5a989beb875d58f Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Wed, 28 Sep 2005 20:21:11 -0700 Subject: [SPARC64]: Convert to use generic exception table support. The funny "range" exception table entries we had were only used by the compat layer socketcall assembly, and it wasn't even needed there. For free we now get proper exception table sorting and fast binary searching. Signed-off-by: David S. Miller --- arch/sparc64/kernel/sys32.S | 145 ++++++++++++++++++++++------------------ arch/sparc64/kernel/traps.c | 24 +++---- arch/sparc64/kernel/unaligned.c | 9 ++- arch/sparc64/mm/Makefile | 2 +- arch/sparc64/mm/extable.c | 80 ---------------------- arch/sparc64/mm/fault.c | 10 +-- include/asm-sparc64/uaccess.h | 17 +---- 7 files changed, 101 insertions(+), 186 deletions(-) delete mode 100644 arch/sparc64/mm/extable.c diff --git a/arch/sparc64/kernel/sys32.S b/arch/sparc64/kernel/sys32.S index 5f9e4fae612..4fb99e0bc7c 100644 --- a/arch/sparc64/kernel/sys32.S +++ b/arch/sparc64/kernel/sys32.S @@ -158,163 +158,163 @@ sys32_socketcall: /* %o0=call, %o1=args */ jmpl %g2 + %o0, %g0 nop - /* Each entry is exactly 32 bytes. */ .align 32 __socketcall_table_begin: + + /* Each entry is exactly 32 bytes. */ do_sys_socket: /* sys_socket(int, int, int) */ - ldswa [%o1 + 0x0] %asi, %o0 +1: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_socket), %g1 - ldswa [%o1 + 0x8] %asi, %o2 +2: ldswa [%o1 + 0x8] %asi, %o2 jmpl %g1 + %lo(sys_socket), %g0 - ldswa [%o1 + 0x4] %asi, %o1 +3: ldswa [%o1 + 0x4] %asi, %o1 nop nop nop do_sys_bind: /* sys_bind(int fd, struct sockaddr *, int) */ - ldswa [%o1 + 0x0] %asi, %o0 +4: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_bind), %g1 - ldswa [%o1 + 0x8] %asi, %o2 +5: ldswa [%o1 + 0x8] %asi, %o2 jmpl %g1 + %lo(sys_bind), %g0 - lduwa [%o1 + 0x4] %asi, %o1 +6: lduwa [%o1 + 0x4] %asi, %o1 nop nop nop do_sys_connect: /* sys_connect(int, struct sockaddr *, int) */ - ldswa [%o1 + 0x0] %asi, %o0 +7: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_connect), %g1 - ldswa [%o1 + 0x8] %asi, %o2 +8: ldswa [%o1 + 0x8] %asi, %o2 jmpl %g1 + %lo(sys_connect), %g0 - lduwa [%o1 + 0x4] %asi, %o1 +9: lduwa [%o1 + 0x4] %asi, %o1 nop nop nop do_sys_listen: /* sys_listen(int, int) */ - ldswa [%o1 + 0x0] %asi, %o0 +10: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_listen), %g1 jmpl %g1 + %lo(sys_listen), %g0 - ldswa [%o1 + 0x4] %asi, %o1 +11: ldswa [%o1 + 0x4] %asi, %o1 nop nop nop nop do_sys_accept: /* sys_accept(int, struct sockaddr *, int *) */ - ldswa [%o1 + 0x0] %asi, %o0 +12: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_accept), %g1 - lduwa [%o1 + 0x8] %asi, %o2 +13: lduwa [%o1 + 0x8] %asi, %o2 jmpl %g1 + %lo(sys_accept), %g0 - lduwa [%o1 + 0x4] %asi, %o1 +14: lduwa [%o1 + 0x4] %asi, %o1 nop nop nop do_sys_getsockname: /* sys_getsockname(int, struct sockaddr *, int *) */ - ldswa [%o1 + 0x0] %asi, %o0 +15: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_getsockname), %g1 - lduwa [%o1 + 0x8] %asi, %o2 +16: lduwa [%o1 + 0x8] %asi, %o2 jmpl %g1 + %lo(sys_getsockname), %g0 - lduwa [%o1 + 0x4] %asi, %o1 +17: lduwa [%o1 + 0x4] %asi, %o1 nop nop nop do_sys_getpeername: /* sys_getpeername(int, struct sockaddr *, int *) */ - ldswa [%o1 + 0x0] %asi, %o0 +18: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_getpeername), %g1 - lduwa [%o1 + 0x8] %asi, %o2 +19: lduwa [%o1 + 0x8] %asi, %o2 jmpl %g1 + %lo(sys_getpeername), %g0 - lduwa [%o1 + 0x4] %asi, %o1 +20: lduwa [%o1 + 0x4] %asi, %o1 nop nop nop do_sys_socketpair: /* sys_socketpair(int, int, int, int *) */ - ldswa [%o1 + 0x0] %asi, %o0 +21: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_socketpair), %g1 - ldswa [%o1 + 0x8] %asi, %o2 - lduwa [%o1 + 0xc] %asi, %o3 +22: ldswa [%o1 + 0x8] %asi, %o2 +23: lduwa [%o1 + 0xc] %asi, %o3 jmpl %g1 + %lo(sys_socketpair), %g0 - ldswa [%o1 + 0x4] %asi, %o1 +24: ldswa [%o1 + 0x4] %asi, %o1 nop nop do_sys_send: /* sys_send(int, void *, size_t, unsigned int) */ - ldswa [%o1 + 0x0] %asi, %o0 +25: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_send), %g1 - lduwa [%o1 + 0x8] %asi, %o2 - lduwa [%o1 + 0xc] %asi, %o3 +26: lduwa [%o1 + 0x8] %asi, %o2 +27: lduwa [%o1 + 0xc] %asi, %o3 jmpl %g1 + %lo(sys_send), %g0 - lduwa [%o1 + 0x4] %asi, %o1 +28: lduwa [%o1 + 0x4] %asi, %o1 nop nop do_sys_recv: /* sys_recv(int, void *, size_t, unsigned int) */ - ldswa [%o1 + 0x0] %asi, %o0 +29: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_recv), %g1 - lduwa [%o1 + 0x8] %asi, %o2 - lduwa [%o1 + 0xc] %asi, %o3 +30: lduwa [%o1 + 0x8] %asi, %o2 +31: lduwa [%o1 + 0xc] %asi, %o3 jmpl %g1 + %lo(sys_recv), %g0 - lduwa [%o1 + 0x4] %asi, %o1 +32: lduwa [%o1 + 0x4] %asi, %o1 nop nop do_sys_sendto: /* sys_sendto(int, u32, compat_size_t, unsigned int, u32, int) */ - ldswa [%o1 + 0x0] %asi, %o0 +33: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_sendto), %g1 - lduwa [%o1 + 0x8] %asi, %o2 - lduwa [%o1 + 0xc] %asi, %o3 - lduwa [%o1 + 0x10] %asi, %o4 - ldswa [%o1 + 0x14] %asi, %o5 +34: lduwa [%o1 + 0x8] %asi, %o2 +35: lduwa [%o1 + 0xc] %asi, %o3 +36: lduwa [%o1 + 0x10] %asi, %o4 +37: ldswa [%o1 + 0x14] %asi, %o5 jmpl %g1 + %lo(sys_sendto), %g0 - lduwa [%o1 + 0x4] %asi, %o1 +38: lduwa [%o1 + 0x4] %asi, %o1 do_sys_recvfrom: /* sys_recvfrom(int, u32, compat_size_t, unsigned int, u32, u32) */ - ldswa [%o1 + 0x0] %asi, %o0 +39: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_recvfrom), %g1 - lduwa [%o1 + 0x8] %asi, %o2 - lduwa [%o1 + 0xc] %asi, %o3 - lduwa [%o1 + 0x10] %asi, %o4 - lduwa [%o1 + 0x14] %asi, %o5 +40: lduwa [%o1 + 0x8] %asi, %o2 +41: lduwa [%o1 + 0xc] %asi, %o3 +42: lduwa [%o1 + 0x10] %asi, %o4 +43: lduwa [%o1 + 0x14] %asi, %o5 jmpl %g1 + %lo(sys_recvfrom), %g0 - lduwa [%o1 + 0x4] %asi, %o1 +44: lduwa [%o1 + 0x4] %asi, %o1 do_sys_shutdown: /* sys_shutdown(int, int) */ - ldswa [%o1 + 0x0] %asi, %o0 +45: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(sys_shutdown), %g1 jmpl %g1 + %lo(sys_shutdown), %g0 - ldswa [%o1 + 0x4] %asi, %o1 +46: ldswa [%o1 + 0x4] %asi, %o1 nop nop nop nop do_sys_setsockopt: /* compat_sys_setsockopt(int, int, int, char *, int) */ - ldswa [%o1 + 0x0] %asi, %o0 +47: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(compat_sys_setsockopt), %g1 - ldswa [%o1 + 0x8] %asi, %o2 - lduwa [%o1 + 0xc] %asi, %o3 - ldswa [%o1 + 0x10] %asi, %o4 +48: ldswa [%o1 + 0x8] %asi, %o2 +49: lduwa [%o1 + 0xc] %asi, %o3 +50: ldswa [%o1 + 0x10] %asi, %o4 jmpl %g1 + %lo(compat_sys_setsockopt), %g0 - ldswa [%o1 + 0x4] %asi, %o1 +51: ldswa [%o1 + 0x4] %asi, %o1 nop do_sys_getsockopt: /* compat_sys_getsockopt(int, int, int, u32, u32) */ - ldswa [%o1 + 0x0] %asi, %o0 +52: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(compat_sys_getsockopt), %g1 - ldswa [%o1 + 0x8] %asi, %o2 - lduwa [%o1 + 0xc] %asi, %o3 - lduwa [%o1 + 0x10] %asi, %o4 +53: ldswa [%o1 + 0x8] %asi, %o2 +54: lduwa [%o1 + 0xc] %asi, %o3 +55: lduwa [%o1 + 0x10] %asi, %o4 jmpl %g1 + %lo(compat_sys_getsockopt), %g0 - ldswa [%o1 + 0x4] %asi, %o1 +56: ldswa [%o1 + 0x4] %asi, %o1 nop do_sys_sendmsg: /* compat_sys_sendmsg(int, struct compat_msghdr *, unsigned int) */ - ldswa [%o1 + 0x0] %asi, %o0 +57: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(compat_sys_sendmsg), %g1 - lduwa [%o1 + 0x8] %asi, %o2 +58: lduwa [%o1 + 0x8] %asi, %o2 jmpl %g1 + %lo(compat_sys_sendmsg), %g0 - lduwa [%o1 + 0x4] %asi, %o1 +59: lduwa [%o1 + 0x4] %asi, %o1 nop nop nop do_sys_recvmsg: /* compat_sys_recvmsg(int, struct compat_msghdr *, unsigned int) */ - ldswa [%o1 + 0x0] %asi, %o0 +60: ldswa [%o1 + 0x0] %asi, %o0 sethi %hi(compat_sys_recvmsg), %g1 - lduwa [%o1 + 0x8] %asi, %o2 +61: lduwa [%o1 + 0x8] %asi, %o2 jmpl %g1 + %lo(compat_sys_recvmsg), %g0 - lduwa [%o1 + 0x4] %asi, %o1 +62: lduwa [%o1 + 0x4] %asi, %o1 nop nop nop -__socketcall_table_end: do_einval: retl @@ -325,5 +325,20 @@ do_efault: .section __ex_table .align 4 - .word __socketcall_table_begin, 0, __socketcall_table_end, do_efault + .word 1b, do_efault, 2b, do_efault, 3b, do_efault, 4b, do_efault + .word 5b, do_efault, 6b, do_efault, 7b, do_efault, 8b, do_efault + .word 9b, do_efault, 10b, do_efault, 11b, do_efault, 12b, do_efault + .word 13b, do_efault, 14b, do_efault, 15b, do_efault, 16b, do_efault + .word 17b, do_efault, 18b, do_efault, 19b, do_efault, 20b, do_efault + .word 21b, do_efault, 22b, do_efault, 23b, do_efault, 24b, do_efault + .word 25b, do_efault, 26b, do_efault, 27b, do_efault, 28b, do_efault + .word 29b, do_efault, 30b, do_efault, 31b, do_efault, 32b, do_efault + .word 33b, do_efault, 34b, do_efault, 35b, do_efault, 36b, do_efault + .word 37b, do_efault, 38b, do_efault, 39b, do_efault, 40b, do_efault + .word 41b, do_efault, 42b, do_efault, 43b, do_efault, 44b, do_efault + .word 45b, do_efault, 46b, do_efault, 47b, do_efault, 48b, do_efault + .word 49b, do_efault, 50b, do_efault, 51b, do_efault, 52b, do_efault + .word 53b, do_efault, 54b, do_efault, 55b, do_efault, 56b, do_efault + .word 57b, do_efault, 58b, do_efault, 59b, do_efault, 60b, do_efault + .word 61b, do_efault, 62b, do_efault .previous diff --git a/arch/sparc64/kernel/traps.c b/arch/sparc64/kernel/traps.c index f8e7005fede..1aa15990f5a 100644 --- a/arch/sparc64/kernel/traps.c +++ b/arch/sparc64/kernel/traps.c @@ -189,19 +189,18 @@ void spitfire_data_access_exception(struct pt_regs *regs, unsigned long sfsr, un if (regs->tstate & TSTATE_PRIV) { /* Test if this comes from uaccess places. */ - unsigned long fixup; - unsigned long g2 = regs->u_regs[UREG_G2]; + const struct exception_table_entry *entry; - if ((fixup = search_extables_range(regs->tpc, &g2))) { - /* Ouch, somebody is trying ugly VM hole tricks on us... */ + entry = search_exception_tables(regs->tpc); + if (entry) { + /* Ouch, somebody is trying VM hole tricks on us... */ #ifdef DEBUG_EXCEPTIONS printk("Exception: PC<%016lx> faddr\n", regs->tpc); - printk("EX_TABLE: insn<%016lx> fixup<%016lx> " - "g2<%016lx>\n", regs->tpc, fixup, g2); + printk("EX_TABLE: insn<%016lx> fixup<%016lx>\n", + regs->tpc, entry->fixup); #endif - regs->tpc = fixup; + regs->tpc = entry->fixup; regs->tnpc = regs->tpc + 4; - regs->u_regs[UREG_G2] = g2; return; } /* Shit... */ @@ -1610,10 +1609,10 @@ void cheetah_deferred_handler(struct pt_regs *regs, unsigned long afsr, unsigned /* OK, usermode access. */ recoverable = 1; } else { - unsigned long g2 = regs->u_regs[UREG_G2]; - unsigned long fixup = search_extables_range(regs->tpc, &g2); + const struct exception_table_entry *entry; - if (fixup != 0UL) { + entry = search_exception_tables(regs->tpc); + if (entry) { /* OK, kernel access to userspace. */ recoverable = 1; @@ -1632,9 +1631,8 @@ void cheetah_deferred_handler(struct pt_regs *regs, unsigned long afsr, unsigned * recoverable condition. */ if (recoverable) { - regs->tpc = fixup; + regs->tpc = entry->fixup; regs->tnpc = regs->tpc + 4; - regs->u_regs[UREG_G2] = g2; } } } diff --git a/arch/sparc64/kernel/unaligned.c b/arch/sparc64/kernel/unaligned.c index 02af08ffec8..9d6be20f412 100644 --- a/arch/sparc64/kernel/unaligned.c +++ b/arch/sparc64/kernel/unaligned.c @@ -246,10 +246,10 @@ void kernel_mna_trap_fault(void) { struct pt_regs *regs = current_thread_info()->kern_una_regs; unsigned int insn = current_thread_info()->kern_una_insn; - unsigned long g2 = regs->u_regs[UREG_G2]; - unsigned long fixup = search_extables_range(regs->tpc, &g2); + const struct exception_table_entry *entry; - if (!fixup) { + entry = search_exception_tables(regs->tpc); + if (!entry) { unsigned long address; address = compute_effective_address(regs, insn, @@ -270,9 +270,8 @@ void kernel_mna_trap_fault(void) die_if_kernel("Oops", regs); /* Not reached */ } - regs->tpc = fixup; + regs->tpc = entry->fixup; regs->tnpc = regs->tpc + 4; - regs->u_regs [UREG_G2] = g2; regs->tstate &= ~TSTATE_ASI; regs->tstate |= (ASI_AIUS << 24UL); diff --git a/arch/sparc64/mm/Makefile b/arch/sparc64/mm/Makefile index cda87333a77..9d0960e69f4 100644 --- a/arch/sparc64/mm/Makefile +++ b/arch/sparc64/mm/Makefile @@ -5,6 +5,6 @@ EXTRA_AFLAGS := -ansi EXTRA_CFLAGS := -Werror -obj-y := ultra.o tlb.o fault.o init.o generic.o extable.o +obj-y := ultra.o tlb.o fault.o init.o generic.o obj-$(CONFIG_HUGETLB_PAGE) += hugetlbpage.o diff --git a/arch/sparc64/mm/extable.c b/arch/sparc64/mm/extable.c deleted file mode 100644 index ec334297ff4..00000000000 --- a/arch/sparc64/mm/extable.c +++ /dev/null @@ -1,80 +0,0 @@ -/* - * linux/arch/sparc64/mm/extable.c - */ - -#include -#include -#include - -extern const struct exception_table_entry __start___ex_table[]; -extern const struct exception_table_entry __stop___ex_table[]; - -void sort_extable(struct exception_table_entry *start, - struct exception_table_entry *finish) -{ -} - -/* Caller knows they are in a range if ret->fixup == 0 */ -const struct exception_table_entry * -search_extable(const struct exception_table_entry *start, - const struct exception_table_entry *last, - unsigned long value) -{ - const struct exception_table_entry *walk; - - /* Single insn entries are encoded as: - * word 1: insn address - * word 2: fixup code address - * - * Range entries are encoded as: - * word 1: first insn address - * word 2: 0 - * word 3: last insn address + 4 bytes - * word 4: fixup code address - * - * See asm/uaccess.h for more details. - */ - - /* 1. Try to find an exact match. */ - for (walk = start; walk <= last; walk++) { - if (walk->fixup == 0) { - /* A range entry, skip both parts. */ - walk++; - continue; - } - - if (walk->insn == value) - return walk; - } - - /* 2. Try to find a range match. */ - for (walk = start; walk <= (last - 1); walk++) { - if (walk->fixup) - continue; - - if (walk[0].insn <= value && walk[1].insn > value) - return walk; - - walk++; - } - - return NULL; -} - -/* Special extable search, which handles ranges. Returns fixup */ -unsigned long search_extables_range(unsigned long addr, unsigned long *g2) -{ - const struct exception_table_entry *entry; - - entry = search_exception_tables(addr); - if (!entry) - return 0; - - /* Inside range? Fix g2 and return correct fixup */ - if (!entry->fixup) { - *g2 = (addr - entry->insn) / 4; - return (entry + 1)->fixup; - } - - return entry->fixup; -} diff --git a/arch/sparc64/mm/fault.c b/arch/sparc64/mm/fault.c index db1e3310e90..59dc9a2ece5 100644 --- a/arch/sparc64/mm/fault.c +++ b/arch/sparc64/mm/fault.c @@ -242,7 +242,6 @@ static unsigned int get_fault_insn(struct pt_regs *regs, unsigned int insn) static void do_kernel_fault(struct pt_regs *regs, int si_code, int fault_code, unsigned int insn, unsigned long address) { - unsigned long g2; unsigned char asi = ASI_P; if ((!insn) && (regs->tstate & TSTATE_PRIV)) @@ -273,11 +272,9 @@ static void do_kernel_fault(struct pt_regs *regs, int si_code, int fault_code, } } - g2 = regs->u_regs[UREG_G2]; - /* Is this in ex_table? */ if (regs->tstate & TSTATE_PRIV) { - unsigned long fixup; + const struct exception_table_entry *entry; if (asi == ASI_P && (insn & 0xc0800000) == 0xc0800000) { if (insn & 0x2000) @@ -288,10 +285,9 @@ static void do_kernel_fault(struct pt_regs *regs, int si_code, int fault_code, /* Look in asi.h: All _S asis have LS bit set */ if ((asi & 0x1) && - (fixup = search_extables_range(regs->tpc, &g2))) { - regs->tpc = fixup; + (entry = search_exception_tables(regs->tpc))) { + regs->tpc = entry->fixup; regs->tnpc = regs->tpc + 4; - regs->u_regs[UREG_G2] = g2; return; } } else { diff --git a/include/asm-sparc64/uaccess.h b/include/asm-sparc64/uaccess.h index 80a65d7e3db..c099aa33978 100644 --- a/include/asm-sparc64/uaccess.h +++ b/include/asm-sparc64/uaccess.h @@ -70,25 +70,12 @@ static inline int access_ok(int type, const void __user * addr, unsigned long si * with the main instruction path. This means when everything is well, * we don't even have to jump over them. Further, they do not intrude * on our cache or tlb entries. - * - * There is a special way how to put a range of potentially faulting - * insns (like twenty ldd/std's with now intervening other instructions) - * You specify address of first in insn and 0 in fixup and in the next - * exception_table_entry you specify last potentially faulting insn + 1 - * and in fixup the routine which should handle the fault. - * That fixup code will get - * (faulting_insn_address - first_insn_in_the_range_address)/4 - * in %g2 (ie. index of the faulting instruction in the range). */ -struct exception_table_entry -{ - unsigned insn, fixup; +struct exception_table_entry { + unsigned int insn, fixup; }; -/* Special exable search, which handles ranges. Returns fixup */ -unsigned long search_extables_range(unsigned long addr, unsigned long *g2); - extern void __ret_efault(void); /* Uh, these should become the main single-value transfer routines.. -- cgit v1.2.3 From 5fd29752f09cabff582f65c0ce35518db4c64937 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Wed, 28 Sep 2005 20:41:45 -0700 Subject: [SPARC64]: Fix fault handling in unaligned trap handler. We were not calling kernel_mna_trap_fault() correctly. Instead of being fancy, just return 0 vs. -EFAULT from the assembler stubs, and handle that return value as appropriate. Create an "__retl_efault" stub for assembler exception table entries and use it where possible. Signed-off-by: David S. Miller --- arch/sparc64/kernel/head.S | 7 ++-- arch/sparc64/kernel/sys32.S | 57 ++++++++++++++++++------------- arch/sparc64/kernel/una_asm.S | 65 ++++++++++++++++-------------------- arch/sparc64/kernel/unaligned.c | 36 +++++++++++--------- arch/sparc64/lib/strncpy_from_user.S | 16 ++++----- include/asm-sparc64/uaccess.h | 1 + 6 files changed, 95 insertions(+), 87 deletions(-) diff --git a/arch/sparc64/kernel/head.S b/arch/sparc64/kernel/head.S index ecc748fb9ad..89406f9649a 100644 --- a/arch/sparc64/kernel/head.S +++ b/arch/sparc64/kernel/head.S @@ -540,8 +540,11 @@ bootup_user_stack_end: prom_tba: .xword 0 tlb_type: .word 0 /* Must NOT end up in BSS */ .section ".fixup",#alloc,#execinstr - .globl __ret_efault + + .globl __ret_efault, __retl_efault __ret_efault: ret restore %g0, -EFAULT, %o0 - +__retl_efault: + retl + mov -EFAULT, %o0 diff --git a/arch/sparc64/kernel/sys32.S b/arch/sparc64/kernel/sys32.S index 4fb99e0bc7c..9cd272ac3ac 100644 --- a/arch/sparc64/kernel/sys32.S +++ b/arch/sparc64/kernel/sys32.S @@ -157,6 +157,9 @@ sys32_socketcall: /* %o0=call, %o1=args */ or %g2, %lo(__socketcall_table_begin), %g2 jmpl %g2 + %o0, %g0 nop +do_einval: + retl + mov -EINVAL, %o0 .align 32 __socketcall_table_begin: @@ -316,29 +319,37 @@ do_sys_recvmsg: /* compat_sys_recvmsg(int, struct compat_msghdr *, unsigned int) nop nop -do_einval: - retl - mov -EINVAL, %o0 -do_efault: - retl - mov -EFAULT, %o0 - .section __ex_table .align 4 - .word 1b, do_efault, 2b, do_efault, 3b, do_efault, 4b, do_efault - .word 5b, do_efault, 6b, do_efault, 7b, do_efault, 8b, do_efault - .word 9b, do_efault, 10b, do_efault, 11b, do_efault, 12b, do_efault - .word 13b, do_efault, 14b, do_efault, 15b, do_efault, 16b, do_efault - .word 17b, do_efault, 18b, do_efault, 19b, do_efault, 20b, do_efault - .word 21b, do_efault, 22b, do_efault, 23b, do_efault, 24b, do_efault - .word 25b, do_efault, 26b, do_efault, 27b, do_efault, 28b, do_efault - .word 29b, do_efault, 30b, do_efault, 31b, do_efault, 32b, do_efault - .word 33b, do_efault, 34b, do_efault, 35b, do_efault, 36b, do_efault - .word 37b, do_efault, 38b, do_efault, 39b, do_efault, 40b, do_efault - .word 41b, do_efault, 42b, do_efault, 43b, do_efault, 44b, do_efault - .word 45b, do_efault, 46b, do_efault, 47b, do_efault, 48b, do_efault - .word 49b, do_efault, 50b, do_efault, 51b, do_efault, 52b, do_efault - .word 53b, do_efault, 54b, do_efault, 55b, do_efault, 56b, do_efault - .word 57b, do_efault, 58b, do_efault, 59b, do_efault, 60b, do_efault - .word 61b, do_efault, 62b, do_efault + .word 1b, __retl_efault, 2b, __retl_efault + .word 3b, __retl_efault, 4b, __retl_efault + .word 5b, __retl_efault, 6b, __retl_efault + .word 7b, __retl_efault, 8b, __retl_efault + .word 9b, __retl_efault, 10b, __retl_efault + .word 11b, __retl_efault, 12b, __retl_efault + .word 13b, __retl_efault, 14b, __retl_efault + .word 15b, __retl_efault, 16b, __retl_efault + .word 17b, __retl_efault, 18b, __retl_efault + .word 19b, __retl_efault, 20b, __retl_efault + .word 21b, __retl_efault, 22b, __retl_efault + .word 23b, __retl_efault, 24b, __retl_efault + .word 25b, __retl_efault, 26b, __retl_efault + .word 27b, __retl_efault, 28b, __retl_efault + .word 29b, __retl_efault, 30b, __retl_efault + .word 31b, __retl_efault, 32b, __retl_efault + .word 33b, __retl_efault, 34b, __retl_efault + .word 35b, __retl_efault, 36b, __retl_efault + .word 37b, __retl_efault, 38b, __retl_efault + .word 39b, __retl_efault, 40b, __retl_efault + .word 41b, __retl_efault, 42b, __retl_efault + .word 43b, __retl_efault, 44b, __retl_efault + .word 45b, __retl_efault, 46b, __retl_efault + .word 47b, __retl_efault, 48b, __retl_efault + .word 49b, __retl_efault, 50b, __retl_efault + .word 51b, __retl_efault, 52b, __retl_efault + .word 53b, __retl_efault, 54b, __retl_efault + .word 55b, __retl_efault, 56b, __retl_efault + .word 57b, __retl_efault, 58b, __retl_efault + .word 59b, __retl_efault, 60b, __retl_efault + .word 61b, __retl_efault, 62b, __retl_efault .previous diff --git a/arch/sparc64/kernel/una_asm.S b/arch/sparc64/kernel/una_asm.S index da48400bcc9..1f5b5b708ce 100644 --- a/arch/sparc64/kernel/una_asm.S +++ b/arch/sparc64/kernel/una_asm.S @@ -6,13 +6,6 @@ .text -kernel_unaligned_trap_fault: - call kernel_mna_trap_fault - nop - retl - nop - .size kern_unaligned_trap_fault, .-kern_unaligned_trap_fault - .globl __do_int_store __do_int_store: rd %asi, %o4 @@ -51,24 +44,24 @@ __do_int_store: 0: wr %o4, 0x0, %asi retl - nop + mov 0, %o0 .size __do_int_store, .-__do_int_store .section __ex_table - .word 4b, kernel_unaligned_trap_fault - .word 5b, kernel_unaligned_trap_fault - .word 6b, kernel_unaligned_trap_fault - .word 7b, kernel_unaligned_trap_fault - .word 8b, kernel_unaligned_trap_fault - .word 9b, kernel_unaligned_trap_fault - .word 10b, kernel_unaligned_trap_fault - .word 11b, kernel_unaligned_trap_fault - .word 12b, kernel_unaligned_trap_fault - .word 13b, kernel_unaligned_trap_fault - .word 14b, kernel_unaligned_trap_fault - .word 15b, kernel_unaligned_trap_fault - .word 16b, kernel_unaligned_trap_fault - .word 17b, kernel_unaligned_trap_fault + .word 4b, __retl_efault + .word 5b, __retl_efault + .word 6b, __retl_efault + .word 7b, __retl_efault + .word 8b, __retl_efault + .word 9b, __retl_efault + .word 10b, __retl_efault + .word 11b, __retl_efault + .word 12b, __retl_efault + .word 13b, __retl_efault + .word 14b, __retl_efault + .word 15b, __retl_efault + .word 16b, __retl_efault + .word 17b, __retl_efault .previous .globl do_int_load @@ -133,21 +126,21 @@ do_int_load: 0: wr %o5, 0x0, %asi retl - nop + mov 0, %o0 .size __do_int_load, .-__do_int_load .section __ex_table - .word 4b, kernel_unaligned_trap_fault - .word 5b, kernel_unaligned_trap_fault - .word 6b, kernel_unaligned_trap_fault - .word 7b, kernel_unaligned_trap_fault - .word 8b, kernel_unaligned_trap_fault - .word 9b, kernel_unaligned_trap_fault - .word 10b, kernel_unaligned_trap_fault - .word 11b, kernel_unaligned_trap_fault - .word 12b, kernel_unaligned_trap_fault - .word 13b, kernel_unaligned_trap_fault - .word 14b, kernel_unaligned_trap_fault - .word 15b, kernel_unaligned_trap_fault - .word 16b, kernel_unaligned_trap_fault + .word 4b, __retl_efault + .word 5b, __retl_efault + .word 6b, __retl_efault + .word 7b, __retl_efault + .word 8b, __retl_efault + .word 9b, __retl_efault + .word 10b, __retl_efault + .word 11b, __retl_efault + .word 12b, __retl_efault + .word 13b, __retl_efault + .word 14b, __retl_efault + .word 15b, __retl_efault + .word 16b, __retl_efault .previous diff --git a/arch/sparc64/kernel/unaligned.c b/arch/sparc64/kernel/unaligned.c index 9d6be20f412..70faf630603 100644 --- a/arch/sparc64/kernel/unaligned.c +++ b/arch/sparc64/kernel/unaligned.c @@ -180,14 +180,14 @@ static void __attribute_used__ unaligned_panic(char *str, struct pt_regs *regs) die_if_kernel(str, regs); } -extern void do_int_load(unsigned long *dest_reg, int size, - unsigned long *saddr, int is_signed, int asi); +extern int do_int_load(unsigned long *dest_reg, int size, + unsigned long *saddr, int is_signed, int asi); -extern void __do_int_store(unsigned long *dst_addr, int size, - unsigned long src_val, int asi); +extern int __do_int_store(unsigned long *dst_addr, int size, + unsigned long src_val, int asi); -static inline void do_int_store(int reg_num, int size, unsigned long *dst_addr, - struct pt_regs *regs, int asi, int orig_asi) +static inline int do_int_store(int reg_num, int size, unsigned long *dst_addr, + struct pt_regs *regs, int asi, int orig_asi) { unsigned long zero = 0; unsigned long *src_val_p = &zero; @@ -219,7 +219,7 @@ static inline void do_int_store(int reg_num, int size, unsigned long *dst_addr, break; }; } - __do_int_store(dst_addr, size, src_val, asi); + return __do_int_store(dst_addr, size, src_val, asi); } static inline void advance(struct pt_regs *regs) @@ -242,7 +242,7 @@ static inline int ok_for_kernel(unsigned int insn) return !floating_point_load_or_store_p(insn); } -void kernel_mna_trap_fault(void) +static void kernel_mna_trap_fault(void) { struct pt_regs *regs = current_thread_info()->kern_una_regs; unsigned int insn = current_thread_info()->kern_una_insn; @@ -294,7 +294,7 @@ asmlinkage void kernel_unaligned_trap(struct pt_regs *regs, unsigned int insn, u kernel_mna_trap_fault(); } else { unsigned long addr, *reg_addr; - int orig_asi, asi; + int orig_asi, asi, err; addr = compute_effective_address(regs, insn, ((insn >> 25) & 0x1f)); @@ -319,9 +319,10 @@ asmlinkage void kernel_unaligned_trap(struct pt_regs *regs, unsigned int insn, u switch (dir) { case load: reg_addr = fetch_reg_addr(((insn>>25)&0x1f), regs); - do_int_load(reg_addr, size, (unsigned long *) addr, - decode_signedness(insn), asi); - if (unlikely(asi != orig_asi)) { + err = do_int_load(reg_addr, size, + (unsigned long *) addr, + decode_signedness(insn), asi); + if (likely(!err) && unlikely(asi != orig_asi)) { unsigned long val_in = *reg_addr; switch (size) { case 2: @@ -343,16 +344,19 @@ asmlinkage void kernel_unaligned_trap(struct pt_regs *regs, unsigned int insn, u break; case store: - do_int_store(((insn>>25)&0x1f), size, - (unsigned long *) addr, regs, - asi, orig_asi); + err = do_int_store(((insn>>25)&0x1f), size, + (unsigned long *) addr, regs, + asi, orig_asi); break; default: panic("Impossible kernel unaligned trap."); /* Not reached... */ } - advance(regs); + if (unlikely(err)) + kernel_mna_trap_fault(); + else + advance(regs); } } diff --git a/arch/sparc64/lib/strncpy_from_user.S b/arch/sparc64/lib/strncpy_from_user.S index 09cbbaa0ebf..e1264650ca7 100644 --- a/arch/sparc64/lib/strncpy_from_user.S +++ b/arch/sparc64/lib/strncpy_from_user.S @@ -125,15 +125,11 @@ __strncpy_from_user: add %o2, %o3, %o0 .size __strncpy_from_user, .-__strncpy_from_user - .section .fixup,#alloc,#execinstr - .align 4 -4: retl - mov -EFAULT, %o0 - .section __ex_table,#alloc .align 4 - .word 60b, 4b - .word 61b, 4b - .word 62b, 4b - .word 63b, 4b - .word 64b, 4b + .word 60b, __retl_efault + .word 61b, __retl_efault + .word 62b, __retl_efault + .word 63b, __retl_efault + .word 64b, __retl_efault + .previous diff --git a/include/asm-sparc64/uaccess.h b/include/asm-sparc64/uaccess.h index c099aa33978..bc8ddbb1cbe 100644 --- a/include/asm-sparc64/uaccess.h +++ b/include/asm-sparc64/uaccess.h @@ -77,6 +77,7 @@ struct exception_table_entry { }; extern void __ret_efault(void); +extern void __retl_efault(void); /* Uh, these should become the main single-value transfer routines.. * They automatically use the right size if we just have the right -- cgit v1.2.3 From efdc1e2083e04cc70721d55803889b346c1a3de2 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Wed, 28 Sep 2005 21:06:47 -0700 Subject: [SPARC64]: Simplify user fault fixup handling. Instead of doing byte-at-a-time user accesses to figure out where the fault occurred, read the saved fault_address from the current thread structure. For the sake of defensive programming, if the fault_address does not fall into the user buffer range, simply assume the whole area faulted. This will cause the fixup for copy_from_user() to clear the entire kernel side buffer. Signed-off-by: David S. Miller --- arch/sparc64/lib/user_fixup.c | 63 ++++++++++++++++++++----------------------- arch/sparc64/mm/fault.c | 10 ++----- include/asm-sparc64/uaccess.h | 6 ++--- 3 files changed, 34 insertions(+), 45 deletions(-) diff --git a/arch/sparc64/lib/user_fixup.c b/arch/sparc64/lib/user_fixup.c index 0278e34125d..19d1fdb17d0 100644 --- a/arch/sparc64/lib/user_fixup.c +++ b/arch/sparc64/lib/user_fixup.c @@ -11,61 +11,56 @@ /* Calculating the exact fault address when using * block loads and stores can be very complicated. + * * Instead of trying to be clever and handling all * of the cases, just fix things up simply here. */ -unsigned long copy_from_user_fixup(void *to, const void __user *from, unsigned long size) +static unsigned long compute_size(unsigned long start, unsigned long size, unsigned long *offset) { - char *dst = to; - const char __user *src = from; + unsigned long fault_addr = current_thread_info()->fault_address; + unsigned long end = start + size; - while (size) { - if (__get_user(*dst, src)) - break; - dst++; - src++; - size--; + if (fault_addr < start || fault_addr >= end) { + *offset = 0; + } else { + *offset = start - fault_addr; + size = end - fault_addr; } + return size; +} - if (size) - memset(dst, 0, size); +unsigned long copy_from_user_fixup(void *to, const void __user *from, unsigned long size) +{ + unsigned long offset; + + size = compute_size((unsigned long) from, size, &offset); + if (likely(size)) + memset(to + offset, 0, size); return size; } unsigned long copy_to_user_fixup(void __user *to, const void *from, unsigned long size) { - char __user *dst = to; - const char *src = from; - - while (size) { - if (__put_user(*src, dst)) - break; - dst++; - src++; - size--; - } + unsigned long offset; - return size; + return compute_size((unsigned long) to, size, &offset); } unsigned long copy_in_user_fixup(void __user *to, void __user *from, unsigned long size) { - char __user *dst = to; - char __user *src = from; + unsigned long fault_addr = current_thread_info()->fault_address; + unsigned long start = (unsigned long) to; + unsigned long end = start + size; - while (size) { - char tmp; + if (fault_addr >= start && fault_addr < end) + return end - fault_addr; - if (__get_user(tmp, src)) - break; - if (__put_user(tmp, dst)) - break; - dst++; - src++; - size--; - } + start = (unsigned long) from; + end = start + size; + if (fault_addr >= start && fault_addr < end) + return end - fault_addr; return size; } diff --git a/arch/sparc64/mm/fault.c b/arch/sparc64/mm/fault.c index 59dc9a2ece5..4a52e79d515 100644 --- a/arch/sparc64/mm/fault.c +++ b/arch/sparc64/mm/fault.c @@ -457,7 +457,7 @@ good_area: } up_read(&mm->mmap_sem); - goto fault_done; + return; /* * Something tried to access memory that isn't in our memory map.. @@ -469,8 +469,7 @@ bad_area: handle_kernel_fault: do_kernel_fault(regs, si_code, fault_code, insn, address); - - goto fault_done; + return; /* * We ran out of memory, or some other thing happened to us that made @@ -501,9 +500,4 @@ do_sigbus: /* Kernel mode? Handle exceptions or die */ if (regs->tstate & TSTATE_PRIV) goto handle_kernel_fault; - -fault_done: - /* These values are no longer needed, clear them. */ - set_thread_fault_code(0); - current_thread_info()->fault_address = 0; } diff --git a/include/asm-sparc64/uaccess.h b/include/asm-sparc64/uaccess.h index bc8ddbb1cbe..203e8eee635 100644 --- a/include/asm-sparc64/uaccess.h +++ b/include/asm-sparc64/uaccess.h @@ -251,7 +251,7 @@ copy_from_user(void *to, const void __user *from, unsigned long size) { unsigned long ret = ___copy_from_user(to, from, size); - if (ret) + if (unlikely(ret)) ret = copy_from_user_fixup(to, from, size); return ret; } @@ -267,7 +267,7 @@ copy_to_user(void __user *to, const void *from, unsigned long size) { unsigned long ret = ___copy_to_user(to, from, size); - if (ret) + if (unlikely(ret)) ret = copy_to_user_fixup(to, from, size); return ret; } @@ -283,7 +283,7 @@ copy_in_user(void __user *to, void __user *from, unsigned long size) { unsigned long ret = ___copy_in_user(to, from, size); - if (ret) + if (unlikely(ret)) ret = copy_in_user_fixup(to, from, size); return ret; } -- cgit v1.2.3 From 801ab3c731e77324c055769491711e620100dbfb Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Wed, 28 Sep 2005 21:31:25 -0700 Subject: [SPARC]: Declare paging_init() in asm/pgtable.h Signed-off-by: David S. Miller --- arch/sparc/kernel/setup.c | 2 -- arch/sparc64/kernel/setup.c | 2 -- include/asm-sparc/pgtable.h | 2 ++ include/asm-sparc64/pgtable.h | 2 ++ 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/arch/sparc/kernel/setup.c b/arch/sparc/kernel/setup.c index 53c192a4982..3509e430553 100644 --- a/arch/sparc/kernel/setup.c +++ b/arch/sparc/kernel/setup.c @@ -249,8 +249,6 @@ struct tt_entry *sparc_ttable; struct pt_regs fake_swapper_regs; -extern void paging_init(void); - void __init setup_arch(char **cmdline_p) { int i; diff --git a/arch/sparc64/kernel/setup.c b/arch/sparc64/kernel/setup.c index 8e8baf2354d..516f4854955 100644 --- a/arch/sparc64/kernel/setup.c +++ b/arch/sparc64/kernel/setup.c @@ -492,8 +492,6 @@ void register_prom_callbacks(void) "' linux-.soft2 to .soft2"); } -extern void paging_init(void); - void __init setup_arch(char **cmdline_p) { int i; diff --git a/include/asm-sparc/pgtable.h b/include/asm-sparc/pgtable.h index 8f4f6a95965..8395ad2f1c0 100644 --- a/include/asm-sparc/pgtable.h +++ b/include/asm-sparc/pgtable.h @@ -82,6 +82,8 @@ extern unsigned long page_kernel; /* Top-level page directory */ extern pgd_t swapper_pg_dir[1024]; +extern void paging_init(void); + /* Page table for 0-4MB for everybody, on the Sparc this * holds the same as on the i386. */ diff --git a/include/asm-sparc64/pgtable.h b/include/asm-sparc64/pgtable.h index 53d612aba8d..82273c801b0 100644 --- a/include/asm-sparc64/pgtable.h +++ b/include/asm-sparc64/pgtable.h @@ -341,6 +341,8 @@ static inline void set_pte_at(struct mm_struct *mm, unsigned long addr, pte_t *p extern pgd_t swapper_pg_dir[2048]; extern pmd_t swapper_low_pmd_dir[2048]; +extern void paging_init(void); + /* These do nothing with the way I have things setup. */ #define mmu_lockarea(vaddr, len) (vaddr) #define mmu_unlockarea(vaddr, len) do { } while(0) -- cgit v1.2.3 From 0836a0eb4073c3e0a09c5965833b9dec19f5abc7 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Wed, 28 Sep 2005 21:38:08 -0700 Subject: [SPARC64]: Move phys_base, kern_{base,size}, and sp_banks[] init to paging_init Also, move prom_probe_memory() into arch/sparc64/mm/init.c Signed-off-by: David S. Miller --- arch/sparc64/kernel/setup.c | 19 -------------- arch/sparc64/mm/fault.c | 47 ---------------------------------- arch/sparc64/mm/init.c | 62 ++++++++++++++++++++++++++++++++++++++++++++- 3 files changed, 61 insertions(+), 67 deletions(-) diff --git a/arch/sparc64/kernel/setup.c b/arch/sparc64/kernel/setup.c index 516f4854955..4c9c8f24174 100644 --- a/arch/sparc64/kernel/setup.c +++ b/arch/sparc64/kernel/setup.c @@ -464,8 +464,6 @@ static void __init boot_flags_init(char *commands) } } -extern int prom_probe_memory(void); -extern unsigned long start, end; extern void panic_setup(char *, int *); extern unsigned short root_flags; @@ -494,8 +492,6 @@ void register_prom_callbacks(void) void __init setup_arch(char **cmdline_p) { - int i; - /* Initialize PROM console and command line. */ *cmdline_p = prom_getbootargs(); strcpy(saved_command_line, *cmdline_p); @@ -514,21 +510,6 @@ void __init setup_arch(char **cmdline_p) boot_flags_init(*cmdline_p); idprom_init(); - (void) prom_probe_memory(); - - phys_base = 0xffffffffffffffffUL; - for (i = 0; sp_banks[i].num_bytes != 0; i++) { - unsigned long top; - - if (sp_banks[i].base_addr < phys_base) - phys_base = sp_banks[i].base_addr; - top = sp_banks[i].base_addr + - sp_banks[i].num_bytes; - } - pfn_base = phys_base >> PAGE_SHIFT; - - kern_base = (prom_boot_mapping_phys_low >> 22UL) << 22UL; - kern_size = (unsigned long)&_end - (unsigned long)KERNBASE; if (!root_flags) root_mountflags &= ~MS_RDONLY; diff --git a/arch/sparc64/mm/fault.c b/arch/sparc64/mm/fault.c index 4a52e79d515..80793d61f31 100644 --- a/arch/sparc64/mm/fault.c +++ b/arch/sparc64/mm/fault.c @@ -71,53 +71,6 @@ void set_brkpt(unsigned long addr, unsigned char mask, int flags, int mode) : "memory"); } -/* Nice, simple, prom library does all the sweating for us. ;) */ -unsigned long __init prom_probe_memory (void) -{ - register struct linux_mlist_p1275 *mlist; - register unsigned long bytes, base_paddr, tally; - register int i; - - i = 0; - mlist = *prom_meminfo()->p1275_available; - bytes = tally = mlist->num_bytes; - base_paddr = mlist->start_adr; - - sp_banks[0].base_addr = base_paddr; - sp_banks[0].num_bytes = bytes; - - while (mlist->theres_more != (void *) 0) { - i++; - mlist = mlist->theres_more; - bytes = mlist->num_bytes; - tally += bytes; - if (i >= SPARC_PHYS_BANKS-1) { - printk ("The machine has more banks than " - "this kernel can support\n" - "Increase the SPARC_PHYS_BANKS " - "setting (currently %d)\n", - SPARC_PHYS_BANKS); - i = SPARC_PHYS_BANKS-1; - break; - } - - sp_banks[i].base_addr = mlist->start_adr; - sp_banks[i].num_bytes = mlist->num_bytes; - } - - i++; - sp_banks[i].base_addr = 0xdeadbeefbeefdeadUL; - sp_banks[i].num_bytes = 0; - - /* Now mask all bank sizes on a page boundary, it is all we can - * use anyways. - */ - for (i = 0; sp_banks[i].num_bytes != 0; i++) - sp_banks[i].num_bytes &= PAGE_MASK; - - return tally; -} - static void __kprobes unhandled_fault(unsigned long address, struct task_struct *tsk, struct pt_regs *regs) diff --git a/arch/sparc64/mm/init.c b/arch/sparc64/mm/init.c index 9f6ca624892..63a7b9bafaf 100644 --- a/arch/sparc64/mm/init.c +++ b/arch/sparc64/mm/init.c @@ -1425,6 +1425,50 @@ void kernel_map_pages(struct page *page, int numpages, int enable) } #endif +static void __init prom_probe_memory(void) +{ + struct linux_mlist_p1275 *mlist; + unsigned long bytes, base_paddr, tally; + int i; + + i = 0; + mlist = *prom_meminfo()->p1275_available; + bytes = tally = mlist->num_bytes; + base_paddr = mlist->start_adr; + + sp_banks[0].base_addr = base_paddr; + sp_banks[0].num_bytes = bytes; + + while (mlist->theres_more != (void *) 0) { + i++; + mlist = mlist->theres_more; + bytes = mlist->num_bytes; + tally += bytes; + if (i >= SPARC_PHYS_BANKS-1) { + printk ("The machine has more banks than " + "this kernel can support\n" + "Increase the SPARC_PHYS_BANKS " + "setting (currently %d)\n", + SPARC_PHYS_BANKS); + i = SPARC_PHYS_BANKS-1; + break; + } + + sp_banks[i].base_addr = mlist->start_adr; + sp_banks[i].num_bytes = mlist->num_bytes; + } + + i++; + sp_banks[i].base_addr = 0xdeadbeefbeefdeadUL; + sp_banks[i].num_bytes = 0; + + /* Now mask all bank sizes on a page boundary, it is all we can + * use anyways. + */ + for (i = 0; sp_banks[i].num_bytes != 0; i++) + sp_banks[i].num_bytes &= PAGE_MASK; +} + /* paging_init() sets up the page tables */ extern void cheetah_ecache_flush_init(void); @@ -1435,7 +1479,23 @@ pgd_t swapper_pg_dir[2048]; void __init paging_init(void) { unsigned long end_pfn, pages_avail, shift; - unsigned long real_end; + unsigned long real_end, i; + + prom_probe_memory(); + + phys_base = 0xffffffffffffffffUL; + for (i = 0; sp_banks[i].num_bytes != 0; i++) { + unsigned long top; + + if (sp_banks[i].base_addr < phys_base) + phys_base = sp_banks[i].base_addr; + top = sp_banks[i].base_addr + + sp_banks[i].num_bytes; + } + pfn_base = phys_base >> PAGE_SHIFT; + + kern_base = (prom_boot_mapping_phys_low >> 22UL) << 22UL; + kern_size = (unsigned long)&_end - (unsigned long)KERNBASE; set_bit(0, mmu_context_bmap); -- cgit v1.2.3 From 10147570f9eaff3920f0c67bad7244c2eb958d4f Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Wed, 28 Sep 2005 21:46:43 -0700 Subject: [SPARC64]: Kill all external references to sp_banks[] Thus, we can mark sp_banks[] static in arch/sparc64/mm/init.c Signed-off-by: David S. Miller --- arch/sparc64/kernel/traps.c | 33 ++++++--------------------------- arch/sparc64/mm/fault.c | 2 -- arch/sparc64/mm/init.c | 23 ++++++++++++++++++++++- include/asm-sparc64/page.h | 17 ----------------- include/asm-sparc64/pgtable.h | 1 + 5 files changed, 29 insertions(+), 47 deletions(-) diff --git a/arch/sparc64/kernel/traps.c b/arch/sparc64/kernel/traps.c index 1aa15990f5a..eeb1e835c42 100644 --- a/arch/sparc64/kernel/traps.c +++ b/arch/sparc64/kernel/traps.c @@ -757,26 +757,12 @@ void __init cheetah_ecache_flush_init(void) ecache_flush_size = (2 * largest_size); ecache_flush_linesize = smallest_linesize; - /* Discover a physically contiguous chunk of physical - * memory in 'sp_banks' of size ecache_flush_size calculated - * above. Store the physical base of this area at - * ecache_flush_physbase. - */ - for (node = 0; ; node++) { - if (sp_banks[node].num_bytes == 0) - break; - if (sp_banks[node].num_bytes >= ecache_flush_size) { - ecache_flush_physbase = sp_banks[node].base_addr; - break; - } - } + ecache_flush_physbase = find_ecache_flush_span(ecache_flush_size); - /* Note: Zero would be a valid value of ecache_flush_physbase so - * don't use that as the success test. :-) - */ - if (sp_banks[node].num_bytes == 0) { + if (ecache_flush_physbase == ~0UL) { prom_printf("cheetah_ecache_flush_init: Cannot find %d byte " - "contiguous physical memory.\n", ecache_flush_size); + "contiguous physical memory.\n", + ecache_flush_size); prom_halt(); } @@ -1345,16 +1331,9 @@ static int cheetah_fix_ce(unsigned long physaddr) /* Return non-zero if PADDR is a valid physical memory address. */ static int cheetah_check_main_memory(unsigned long paddr) { - int i; + unsigned long vaddr = PAGE_OFFSET + paddr; - for (i = 0; ; i++) { - if (sp_banks[i].num_bytes == 0) - break; - if (paddr >= sp_banks[i].base_addr && - paddr < (sp_banks[i].base_addr + sp_banks[i].num_bytes)) - return 1; - } - return 0; + return kern_addr_valid(vaddr); } void cheetah_cee_handler(struct pt_regs *regs, unsigned long afsr, unsigned long afar) diff --git a/arch/sparc64/mm/fault.c b/arch/sparc64/mm/fault.c index 80793d61f31..31fbc67719a 100644 --- a/arch/sparc64/mm/fault.c +++ b/arch/sparc64/mm/fault.c @@ -32,8 +32,6 @@ #define ELEMENTS(arr) (sizeof (arr)/sizeof (arr[0])) -extern struct sparc_phys_banks sp_banks[SPARC_PHYS_BANKS]; - /* * To debug kernel to catch accesses to certain virtual/physical addresses. * Mode = 0 selects physical watchpoints, mode = 1 selects virtual watchpoints. diff --git a/arch/sparc64/mm/init.c b/arch/sparc64/mm/init.c index 63a7b9bafaf..48851a2e4fe 100644 --- a/arch/sparc64/mm/init.c +++ b/arch/sparc64/mm/init.c @@ -41,7 +41,14 @@ extern void device_scan(void); -struct sparc_phys_banks sp_banks[SPARC_PHYS_BANKS]; +struct sparc_phys_banks { + unsigned long base_addr; + unsigned long num_bytes; +}; + +#define SPARC_PHYS_BANKS 32 + +static struct sparc_phys_banks sp_banks[SPARC_PHYS_BANKS]; unsigned long *sparc64_valid_addr_bitmap __read_mostly; @@ -1425,6 +1432,20 @@ void kernel_map_pages(struct page *page, int numpages, int enable) } #endif +unsigned long __init find_ecache_flush_span(unsigned long size) +{ + unsigned long i; + + for (i = 0; ; i++) { + if (sp_banks[i].num_bytes == 0) + break; + if (sp_banks[i].num_bytes >= size) + return sp_banks[i].base_addr; + } + + return ~0UL; +} + static void __init prom_probe_memory(void) { struct linux_mlist_p1275 *mlist; diff --git a/include/asm-sparc64/page.h b/include/asm-sparc64/page.h index 7f8d764abc4..5426bb28a99 100644 --- a/include/asm-sparc64/page.h +++ b/include/asm-sparc64/page.h @@ -140,23 +140,6 @@ extern unsigned long page_to_pfn(struct page *); #define virt_to_phys __pa #define phys_to_virt __va -/* The following structure is used to hold the physical - * memory configuration of the machine. This is filled in - * probe_memory() and is later used by mem_init() to set up - * mem_map[]. We statically allocate SPARC_PHYS_BANKS of - * these structs, this is arbitrary. The entry after the - * last valid one has num_bytes==0. - */ - -struct sparc_phys_banks { - unsigned long base_addr; - unsigned long num_bytes; -}; - -#define SPARC_PHYS_BANKS 32 - -extern struct sparc_phys_banks sp_banks[SPARC_PHYS_BANKS]; - #endif /* !(__ASSEMBLY__) */ #define VM_DATA_DEFAULT_FLAGS (VM_READ | VM_WRITE | VM_EXEC | \ diff --git a/include/asm-sparc64/pgtable.h b/include/asm-sparc64/pgtable.h index 82273c801b0..8c6dfc6c7af 100644 --- a/include/asm-sparc64/pgtable.h +++ b/include/asm-sparc64/pgtable.h @@ -342,6 +342,7 @@ extern pgd_t swapper_pg_dir[2048]; extern pmd_t swapper_low_pmd_dir[2048]; extern void paging_init(void); +extern unsigned long find_ecache_flush_span(unsigned long size); /* These do nothing with the way I have things setup. */ #define mmu_lockarea(vaddr, len) (vaddr) -- cgit v1.2.3 From ed3ffaf7b5e0262cb860f106a6632933671cc88f Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Wed, 28 Sep 2005 21:48:25 -0700 Subject: [SPARC64]: Solidify check in cheetah_check_main_memory(). Need to make sure the address is below high_memory before passing it to kern_addr_valid(). Signed-off-by: David S. Miller --- arch/sparc64/kernel/traps.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/arch/sparc64/kernel/traps.c b/arch/sparc64/kernel/traps.c index eeb1e835c42..7f190fc5754 100644 --- a/arch/sparc64/kernel/traps.c +++ b/arch/sparc64/kernel/traps.c @@ -1333,6 +1333,9 @@ static int cheetah_check_main_memory(unsigned long paddr) { unsigned long vaddr = PAGE_OFFSET + paddr; + if (vaddr > high_memory) + return 0; + return kern_addr_valid(vaddr); } -- cgit v1.2.3 From 01d40f28b125e0a9aa0ec24642be67fc4c5dfaff Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Wed, 28 Sep 2005 22:37:53 -0700 Subject: [NET]: Fix reversed logic in eth_type_trans(). I got the second compare_eth_addr() test reversed, oops. Signed-off-by: David S. Miller --- net/ethernet/eth.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/ethernet/eth.c b/net/ethernet/eth.c index 8b299cc8206..68a5ca86644 100644 --- a/net/ethernet/eth.c +++ b/net/ethernet/eth.c @@ -191,7 +191,7 @@ __be16 eth_type_trans(struct sk_buff *skb, struct net_device *dev) */ else if(1 /*dev->flags&IFF_PROMISC*/) { - if (unlikely(!compare_eth_addr(eth->h_dest, dev->dev_addr))) + if (unlikely(compare_eth_addr(eth->h_dest, dev->dev_addr))) skb->pkt_type = PACKET_OTHERHOST; } -- cgit v1.2.3 From ca5da7106214e03f5302ca630bd38a9145b27391 Mon Sep 17 00:00:00 2001 From: Russell King Date: Thu, 29 Sep 2005 09:44:54 +0100 Subject: [ARM] pxafb: Remove #if DEBUG, convert DPRINTK to pr_debug Fix warning: drivers/video/pxafb.h:119:5: warning: "DEBUG" is not defined by removing the whole #if DEBUG #define DPRINTK(fmt, args...) printk...etc... #else #define DPRINTK(fmt, args...) #endif stuff - we have pr_debug() for this. Signed-off-by: Russell King --- drivers/video/pxafb.c | 108 +++++++++++++++++++++++++------------------------- drivers/video/pxafb.h | 9 ----- 2 files changed, 54 insertions(+), 63 deletions(-) diff --git a/drivers/video/pxafb.c b/drivers/video/pxafb.c index 34d4dcc0320..194eed0a238 100644 --- a/drivers/video/pxafb.c +++ b/drivers/video/pxafb.c @@ -260,9 +260,9 @@ static int pxafb_check_var(struct fb_var_screeninfo *var, struct fb_info *info) } #ifdef CONFIG_CPU_FREQ - DPRINTK("dma period = %d ps, clock = %d kHz\n", - pxafb_display_dma_period(var), - get_clk_frequency_khz(0)); + pr_debug("pxafb: dma period = %d ps, clock = %d kHz\n", + pxafb_display_dma_period(var), + get_clk_frequency_khz(0)); #endif return 0; @@ -270,7 +270,7 @@ static int pxafb_check_var(struct fb_var_screeninfo *var, struct fb_info *info) static inline void pxafb_set_truecolor(u_int is_true_color) { - DPRINTK("true_color = %d\n", is_true_color); + pr_debug("pxafb: true_color = %d\n", is_true_color); // do your machine-specific setup if needed } @@ -284,7 +284,7 @@ static int pxafb_set_par(struct fb_info *info) struct fb_var_screeninfo *var = &info->var; unsigned long palette_mem_size; - DPRINTK("set_par\n"); + pr_debug("pxafb: set_par\n"); if (var->bits_per_pixel == 16) fbi->fb.fix.visual = FB_VISUAL_TRUECOLOR; @@ -308,7 +308,7 @@ static int pxafb_set_par(struct fb_info *info) palette_mem_size = fbi->palette_size * sizeof(u16); - DPRINTK("palette_mem_size = 0x%08lx\n", (u_long) palette_mem_size); + pr_debug("pxafb: palette_mem_size = 0x%08lx\n", palette_mem_size); fbi->palette_cpu = (u16 *)(fbi->map_cpu + PAGE_SIZE - palette_mem_size); fbi->palette_dma = fbi->map_dma + PAGE_SIZE - palette_mem_size; @@ -369,7 +369,7 @@ static int pxafb_blank(int blank, struct fb_info *info) struct pxafb_info *fbi = (struct pxafb_info *)info; int i; - DPRINTK("pxafb_blank: blank=%d\n", blank); + pr_debug("pxafb: blank=%d\n", blank); switch (blank) { case FB_BLANK_POWERDOWN: @@ -508,15 +508,15 @@ static int pxafb_activate_var(struct fb_var_screeninfo *var, struct pxafb_info * u_long flags; u_int lines_per_panel, pcd = get_pcd(var->pixclock); - DPRINTK("Configuring PXA LCD\n"); + pr_debug("pxafb: Configuring PXA LCD\n"); - DPRINTK("var: xres=%d hslen=%d lm=%d rm=%d\n", - var->xres, var->hsync_len, - var->left_margin, var->right_margin); - DPRINTK("var: yres=%d vslen=%d um=%d bm=%d\n", - var->yres, var->vsync_len, - var->upper_margin, var->lower_margin); - DPRINTK("var: pixclock=%d pcd=%d\n", var->pixclock, pcd); + pr_debug("var: xres=%d hslen=%d lm=%d rm=%d\n", + var->xres, var->hsync_len, + var->left_margin, var->right_margin); + pr_debug("var: yres=%d vslen=%d um=%d bm=%d\n", + var->yres, var->vsync_len, + var->upper_margin, var->lower_margin); + pr_debug("var: pixclock=%d pcd=%d\n", var->pixclock, pcd); #if DEBUG_VAR if (var->xres < 16 || var->xres > 1024) @@ -589,10 +589,10 @@ static int pxafb_activate_var(struct fb_var_screeninfo *var, struct pxafb_info * if (pcd) new_regs.lccr3 |= LCCR3_PixClkDiv(pcd); - DPRINTK("nlccr0 = 0x%08x\n", new_regs.lccr0); - DPRINTK("nlccr1 = 0x%08x\n", new_regs.lccr1); - DPRINTK("nlccr2 = 0x%08x\n", new_regs.lccr2); - DPRINTK("nlccr3 = 0x%08x\n", new_regs.lccr3); + pr_debug("nlccr0 = 0x%08x\n", new_regs.lccr0); + pr_debug("nlccr1 = 0x%08x\n", new_regs.lccr1); + pr_debug("nlccr2 = 0x%08x\n", new_regs.lccr2); + pr_debug("nlccr3 = 0x%08x\n", new_regs.lccr3); /* Update shadow copy atomically */ local_irq_save(flags); @@ -637,24 +637,24 @@ static int pxafb_activate_var(struct fb_var_screeninfo *var, struct pxafb_info * } #if 0 - DPRINTK("fbi->dmadesc_fblow_cpu = 0x%p\n", fbi->dmadesc_fblow_cpu); - DPRINTK("fbi->dmadesc_fbhigh_cpu = 0x%p\n", fbi->dmadesc_fbhigh_cpu); - DPRINTK("fbi->dmadesc_palette_cpu = 0x%p\n", fbi->dmadesc_palette_cpu); - DPRINTK("fbi->dmadesc_fblow_dma = 0x%x\n", fbi->dmadesc_fblow_dma); - DPRINTK("fbi->dmadesc_fbhigh_dma = 0x%x\n", fbi->dmadesc_fbhigh_dma); - DPRINTK("fbi->dmadesc_palette_dma = 0x%x\n", fbi->dmadesc_palette_dma); - - DPRINTK("fbi->dmadesc_fblow_cpu->fdadr = 0x%x\n", fbi->dmadesc_fblow_cpu->fdadr); - DPRINTK("fbi->dmadesc_fbhigh_cpu->fdadr = 0x%x\n", fbi->dmadesc_fbhigh_cpu->fdadr); - DPRINTK("fbi->dmadesc_palette_cpu->fdadr = 0x%x\n", fbi->dmadesc_palette_cpu->fdadr); - - DPRINTK("fbi->dmadesc_fblow_cpu->fsadr = 0x%x\n", fbi->dmadesc_fblow_cpu->fsadr); - DPRINTK("fbi->dmadesc_fbhigh_cpu->fsadr = 0x%x\n", fbi->dmadesc_fbhigh_cpu->fsadr); - DPRINTK("fbi->dmadesc_palette_cpu->fsadr = 0x%x\n", fbi->dmadesc_palette_cpu->fsadr); - - DPRINTK("fbi->dmadesc_fblow_cpu->ldcmd = 0x%x\n", fbi->dmadesc_fblow_cpu->ldcmd); - DPRINTK("fbi->dmadesc_fbhigh_cpu->ldcmd = 0x%x\n", fbi->dmadesc_fbhigh_cpu->ldcmd); - DPRINTK("fbi->dmadesc_palette_cpu->ldcmd = 0x%x\n", fbi->dmadesc_palette_cpu->ldcmd); + pr_debug("fbi->dmadesc_fblow_cpu = 0x%p\n", fbi->dmadesc_fblow_cpu); + pr_debug("fbi->dmadesc_fbhigh_cpu = 0x%p\n", fbi->dmadesc_fbhigh_cpu); + pr_debug("fbi->dmadesc_palette_cpu = 0x%p\n", fbi->dmadesc_palette_cpu); + pr_debug("fbi->dmadesc_fblow_dma = 0x%x\n", fbi->dmadesc_fblow_dma); + pr_debug("fbi->dmadesc_fbhigh_dma = 0x%x\n", fbi->dmadesc_fbhigh_dma); + pr_debug("fbi->dmadesc_palette_dma = 0x%x\n", fbi->dmadesc_palette_dma); + + pr_debug("fbi->dmadesc_fblow_cpu->fdadr = 0x%x\n", fbi->dmadesc_fblow_cpu->fdadr); + pr_debug("fbi->dmadesc_fbhigh_cpu->fdadr = 0x%x\n", fbi->dmadesc_fbhigh_cpu->fdadr); + pr_debug("fbi->dmadesc_palette_cpu->fdadr = 0x%x\n", fbi->dmadesc_palette_cpu->fdadr); + + pr_debug("fbi->dmadesc_fblow_cpu->fsadr = 0x%x\n", fbi->dmadesc_fblow_cpu->fsadr); + pr_debug("fbi->dmadesc_fbhigh_cpu->fsadr = 0x%x\n", fbi->dmadesc_fbhigh_cpu->fsadr); + pr_debug("fbi->dmadesc_palette_cpu->fsadr = 0x%x\n", fbi->dmadesc_palette_cpu->fsadr); + + pr_debug("fbi->dmadesc_fblow_cpu->ldcmd = 0x%x\n", fbi->dmadesc_fblow_cpu->ldcmd); + pr_debug("fbi->dmadesc_fbhigh_cpu->ldcmd = 0x%x\n", fbi->dmadesc_fbhigh_cpu->ldcmd); + pr_debug("fbi->dmadesc_palette_cpu->ldcmd = 0x%x\n", fbi->dmadesc_palette_cpu->ldcmd); #endif fbi->reg_lccr0 = new_regs.lccr0; @@ -684,7 +684,7 @@ static int pxafb_activate_var(struct fb_var_screeninfo *var, struct pxafb_info * */ static inline void __pxafb_backlight_power(struct pxafb_info *fbi, int on) { - DPRINTK("backlight o%s\n", on ? "n" : "ff"); + pr_debug("pxafb: backlight o%s\n", on ? "n" : "ff"); if (pxafb_backlight_power) pxafb_backlight_power(on); @@ -692,7 +692,7 @@ static inline void __pxafb_backlight_power(struct pxafb_info *fbi, int on) static inline void __pxafb_lcd_power(struct pxafb_info *fbi, int on) { - DPRINTK("LCD power o%s\n", on ? "n" : "ff"); + pr_debug("pxafb: LCD power o%s\n", on ? "n" : "ff"); if (pxafb_lcd_power) pxafb_lcd_power(on); @@ -740,13 +740,13 @@ static void pxafb_setup_gpio(struct pxafb_info *fbi) static void pxafb_enable_controller(struct pxafb_info *fbi) { - DPRINTK("Enabling LCD controller\n"); - DPRINTK("fdadr0 0x%08x\n", (unsigned int) fbi->fdadr0); - DPRINTK("fdadr1 0x%08x\n", (unsigned int) fbi->fdadr1); - DPRINTK("reg_lccr0 0x%08x\n", (unsigned int) fbi->reg_lccr0); - DPRINTK("reg_lccr1 0x%08x\n", (unsigned int) fbi->reg_lccr1); - DPRINTK("reg_lccr2 0x%08x\n", (unsigned int) fbi->reg_lccr2); - DPRINTK("reg_lccr3 0x%08x\n", (unsigned int) fbi->reg_lccr3); + pr_debug("pxafb: Enabling LCD controller\n"); + pr_debug("fdadr0 0x%08x\n", (unsigned int) fbi->fdadr0); + pr_debug("fdadr1 0x%08x\n", (unsigned int) fbi->fdadr1); + pr_debug("reg_lccr0 0x%08x\n", (unsigned int) fbi->reg_lccr0); + pr_debug("reg_lccr1 0x%08x\n", (unsigned int) fbi->reg_lccr1); + pr_debug("reg_lccr2 0x%08x\n", (unsigned int) fbi->reg_lccr2); + pr_debug("reg_lccr3 0x%08x\n", (unsigned int) fbi->reg_lccr3); /* enable LCD controller clock */ pxa_set_cken(CKEN16_LCD, 1); @@ -761,19 +761,19 @@ static void pxafb_enable_controller(struct pxafb_info *fbi) FDADR1 = fbi->fdadr1; LCCR0 |= LCCR0_ENB; - DPRINTK("FDADR0 0x%08x\n", (unsigned int) FDADR0); - DPRINTK("FDADR1 0x%08x\n", (unsigned int) FDADR1); - DPRINTK("LCCR0 0x%08x\n", (unsigned int) LCCR0); - DPRINTK("LCCR1 0x%08x\n", (unsigned int) LCCR1); - DPRINTK("LCCR2 0x%08x\n", (unsigned int) LCCR2); - DPRINTK("LCCR3 0x%08x\n", (unsigned int) LCCR3); + pr_debug("FDADR0 0x%08x\n", (unsigned int) FDADR0); + pr_debug("FDADR1 0x%08x\n", (unsigned int) FDADR1); + pr_debug("LCCR0 0x%08x\n", (unsigned int) LCCR0); + pr_debug("LCCR1 0x%08x\n", (unsigned int) LCCR1); + pr_debug("LCCR2 0x%08x\n", (unsigned int) LCCR2); + pr_debug("LCCR3 0x%08x\n", (unsigned int) LCCR3); } static void pxafb_disable_controller(struct pxafb_info *fbi) { DECLARE_WAITQUEUE(wait, current); - DPRINTK("Disabling LCD controller\n"); + pr_debug("pxafb: disabling LCD controller\n"); set_current_state(TASK_UNINTERRUPTIBLE); add_wait_queue(&fbi->ctrlr_wait, &wait); @@ -1039,7 +1039,7 @@ static int __init pxafb_map_video_memory(struct pxafb_info *fbi) fbi->palette_size = fbi->fb.var.bits_per_pixel == 8 ? 256 : 16; palette_mem_size = fbi->palette_size * sizeof(u16); - DPRINTK("palette_mem_size = 0x%08lx\n", (u_long) palette_mem_size); + pr_debug("pxafb: palette_mem_size = 0x%08lx\n", palette_mem_size); fbi->palette_cpu = (u16 *)(fbi->map_cpu + PAGE_SIZE - palette_mem_size); fbi->palette_dma = fbi->map_dma + PAGE_SIZE - palette_mem_size; diff --git a/drivers/video/pxafb.h b/drivers/video/pxafb.h index 22c00be786a..47f41f70db7 100644 --- a/drivers/video/pxafb.h +++ b/drivers/video/pxafb.h @@ -113,15 +113,6 @@ struct pxafb_info { #define PXA_NAME "PXA" -/* - * Debug macros - */ -#if DEBUG -# define DPRINTK(fmt, args...) printk("%s: " fmt, __FUNCTION__ , ## args) -#else -# define DPRINTK(fmt, args...) -#endif - /* * Minimum X and Y resolutions */ -- cgit v1.2.3 From eb9181a2f85d46cdbbd3cb18b4541f8ab2df0933 Mon Sep 17 00:00:00 2001 From: Russell King Date: Thu, 29 Sep 2005 09:49:25 +0100 Subject: [ARM] Fix warning in arch/arm/mach-pxa/generic.c Fix arch/arm/mach-pxa/generic.c:242: warning: 'struct i2c_pxa_platform_data' declared inside parameter list caused by missing asm/arch/i2c.h include. Signed-off-by: Russell King --- arch/arm/mach-pxa/generic.c | 1 + 1 file changed, 1 insertion(+) diff --git a/arch/arm/mach-pxa/generic.c b/arch/arm/mach-pxa/generic.c index a45aaa115a7..d0660a8c4b7 100644 --- a/arch/arm/mach-pxa/generic.c +++ b/arch/arm/mach-pxa/generic.c @@ -34,6 +34,7 @@ #include #include #include +#include #include "generic.h" -- cgit v1.2.3 From d0877904470c149c6553f1309cfed6c90d67cf91 Mon Sep 17 00:00:00 2001 From: Russell King Date: Thu, 29 Sep 2005 11:12:52 +0100 Subject: [ARM] Don't include asm/arch/hardware.h directly Since asm/hardware.h's only reason for existing is to include asm/arch/hardware.h, it's completely pointless to include both. Signed-off-by: Russell King --- arch/arm/mach-l7200/core.c | 1 - drivers/usb/host/ohci-lh7a404.c | 1 - drivers/usb/host/ohci-omap.c | 1 - 3 files changed, 3 deletions(-) diff --git a/arch/arm/mach-l7200/core.c b/arch/arm/mach-l7200/core.c index 2a7fee2a763..5fd8c9f97f9 100644 --- a/arch/arm/mach-l7200/core.c +++ b/arch/arm/mach-l7200/core.c @@ -12,7 +12,6 @@ #include #include -#include /* * IRQ base register diff --git a/drivers/usb/host/ohci-lh7a404.c b/drivers/usb/host/ohci-lh7a404.c index 817620d7384..198c1c666e2 100644 --- a/drivers/usb/host/ohci-lh7a404.c +++ b/drivers/usb/host/ohci-lh7a404.c @@ -18,7 +18,6 @@ #include #include -#include extern int usb_disabled(void); diff --git a/drivers/usb/host/ohci-omap.c b/drivers/usb/host/ohci-omap.c index 5cde76faab9..d8f3ba7ad52 100644 --- a/drivers/usb/host/ohci-omap.c +++ b/drivers/usb/host/ohci-omap.c @@ -18,7 +18,6 @@ #include #include -#include #include #include #include -- cgit v1.2.3 From fc611a1a50caa04bae82ed3c1fc6505132f8343f Mon Sep 17 00:00:00 2001 From: Russell King Date: Thu, 29 Sep 2005 11:15:51 +0100 Subject: [ARM] Don't include mach-types.h unnecessarily It's pointless to include mach-types.h if you're not going to use anything from it. These references were removed as a result of: grep -lr 'asm/mach-types\.h' . | xargs grep -L 'machine_is_\|MACH_TYPE_\|MACHINE_START\|machine_type' Signed-off-by: Russell King --- arch/arm/common/locomo.c | 1 - arch/arm/mach-imx/leds-mx1ads.c | 1 - arch/arm/mach-iop3xx/common.c | 1 - arch/arm/mach-iop3xx/iop321-time.c | 1 - arch/arm/mach-iop3xx/iop331-time.c | 1 - arch/arm/mach-iop3xx/iq31244-mm.c | 1 - arch/arm/mach-iop3xx/iq80321-mm.c | 1 - arch/arm/mach-iop3xx/iq80331-mm.c | 1 - arch/arm/mach-iop3xx/iq80332-mm.c | 1 - arch/arm/mach-ixp2000/core.c | 1 - arch/arm/mach-ixp2000/pci.c | 1 - arch/arm/mach-pxa/corgi_lcd.c | 1 - arch/arm/mach-s3c2410/usb-simtec.c | 1 - arch/arm/mach-versatile/core.c | 1 - arch/arm/mach-versatile/pci.c | 1 - arch/arm/plat-omap/common.c | 1 - arch/arm/plat-omap/cpu-omap.c | 1 - arch/arm/plat-omap/usb.c | 1 - drivers/mtd/maps/bast-flash.c | 1 - drivers/mtd/maps/ixp2000.c | 1 - drivers/mtd/maps/ixp4xx.c | 1 - drivers/mtd/maps/omap_nor.c | 1 - drivers/mtd/maps/sa1100-flash.c | 1 - drivers/mtd/nand/s3c2410.c | 1 - drivers/pcmcia/omap_cf.c | 1 - drivers/serial/s3c2410.c | 2 -- drivers/usb/host/ohci-lh7a404.c | 1 - drivers/usb/host/ohci-s3c2410.c | 1 - drivers/video/backlight/corgi_bl.c | 1 - drivers/video/imxfb.c | 1 - 30 files changed, 31 deletions(-) diff --git a/arch/arm/common/locomo.c b/arch/arm/common/locomo.c index a7bd8570015..e8053d16829 100644 --- a/arch/arm/common/locomo.c +++ b/arch/arm/common/locomo.c @@ -27,7 +27,6 @@ #include #include -#include #include #include #include diff --git a/arch/arm/mach-imx/leds-mx1ads.c b/arch/arm/mach-imx/leds-mx1ads.c index e6399b06e4a..79236404aec 100644 --- a/arch/arm/mach-imx/leds-mx1ads.c +++ b/arch/arm/mach-imx/leds-mx1ads.c @@ -17,7 +17,6 @@ #include #include #include -#include #include "leds.h" /* diff --git a/arch/arm/mach-iop3xx/common.c b/arch/arm/mach-iop3xx/common.c index bda7394ec06..fdeeef489a7 100644 --- a/arch/arm/mach-iop3xx/common.c +++ b/arch/arm/mach-iop3xx/common.c @@ -27,7 +27,6 @@ unsigned long iop3xx_pcibios_min_mem = 0; /* * Default power-off for EP80219 */ -#include static inline void ep80219_send_to_pic(__u8 c) { } diff --git a/arch/arm/mach-iop3xx/iop321-time.c b/arch/arm/mach-iop3xx/iop321-time.c index 0039793b694..d67ac0e5d43 100644 --- a/arch/arm/mach-iop3xx/iop321-time.c +++ b/arch/arm/mach-iop3xx/iop321-time.c @@ -23,7 +23,6 @@ #include #include #include -#include #include #include diff --git a/arch/arm/mach-iop3xx/iop331-time.c b/arch/arm/mach-iop3xx/iop331-time.c index 8eddfac7e2b..3c1f0ebbd63 100644 --- a/arch/arm/mach-iop3xx/iop331-time.c +++ b/arch/arm/mach-iop3xx/iop331-time.c @@ -23,7 +23,6 @@ #include #include #include -#include #include #include diff --git a/arch/arm/mach-iop3xx/iq31244-mm.c b/arch/arm/mach-iop3xx/iq31244-mm.c index b01042f7de7..55992ab586b 100644 --- a/arch/arm/mach-iop3xx/iq31244-mm.c +++ b/arch/arm/mach-iop3xx/iq31244-mm.c @@ -21,7 +21,6 @@ #include #include -#include /* diff --git a/arch/arm/mach-iop3xx/iq80321-mm.c b/arch/arm/mach-iop3xx/iq80321-mm.c index 1580c7ed2b9..bb3e9e5a9af 100644 --- a/arch/arm/mach-iop3xx/iq80321-mm.c +++ b/arch/arm/mach-iop3xx/iq80321-mm.c @@ -21,7 +21,6 @@ #include #include -#include /* diff --git a/arch/arm/mach-iop3xx/iq80331-mm.c b/arch/arm/mach-iop3xx/iq80331-mm.c index ee8c333e115..129eb49b067 100644 --- a/arch/arm/mach-iop3xx/iq80331-mm.c +++ b/arch/arm/mach-iop3xx/iq80331-mm.c @@ -21,7 +21,6 @@ #include #include -#include /* diff --git a/arch/arm/mach-iop3xx/iq80332-mm.c b/arch/arm/mach-iop3xx/iq80332-mm.c index 084afcdfb1e..2feaf7591f5 100644 --- a/arch/arm/mach-iop3xx/iq80332-mm.c +++ b/arch/arm/mach-iop3xx/iq80332-mm.c @@ -21,7 +21,6 @@ #include #include -#include /* diff --git a/arch/arm/mach-ixp2000/core.c b/arch/arm/mach-ixp2000/core.c index 74bd2fd602d..f34797a46a2 100644 --- a/arch/arm/mach-ixp2000/core.c +++ b/arch/arm/mach-ixp2000/core.c @@ -30,7 +30,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/arm/mach-ixp2000/pci.c b/arch/arm/mach-ixp2000/pci.c index 0788fb2b5c1..522205acb31 100644 --- a/arch/arm/mach-ixp2000/pci.c +++ b/arch/arm/mach-ixp2000/pci.c @@ -28,7 +28,6 @@ #include #include #include -#include #include #include diff --git a/arch/arm/mach-pxa/corgi_lcd.c b/arch/arm/mach-pxa/corgi_lcd.c index c5efcd04fcb..c02ef7c0f7e 100644 --- a/arch/arm/mach-pxa/corgi_lcd.c +++ b/arch/arm/mach-pxa/corgi_lcd.c @@ -19,7 +19,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/arm/mach-s3c2410/usb-simtec.c b/arch/arm/mach-s3c2410/usb-simtec.c index f021fd82be5..5098b50158a 100644 --- a/arch/arm/mach-s3c2410/usb-simtec.c +++ b/arch/arm/mach-s3c2410/usb-simtec.c @@ -40,7 +40,6 @@ #include #include #include -#include #include "devs.h" #include "usb-simtec.h" diff --git a/arch/arm/mach-versatile/core.c b/arch/arm/mach-versatile/core.c index 3c8862fde51..6a291e6fdab 100644 --- a/arch/arm/mach-versatile/core.c +++ b/arch/arm/mach-versatile/core.c @@ -30,7 +30,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/arm/mach-versatile/pci.c b/arch/arm/mach-versatile/pci.c index d1565e851f0..b80d57d5169 100644 --- a/arch/arm/mach-versatile/pci.c +++ b/arch/arm/mach-versatile/pci.c @@ -29,7 +29,6 @@ #include #include #include -#include /* * these spaces are mapped using the following base registers: diff --git a/arch/arm/plat-omap/common.c b/arch/arm/plat-omap/common.c index 6cb20aea7f5..02bcc6c1cd1 100644 --- a/arch/arm/plat-omap/common.c +++ b/arch/arm/plat-omap/common.c @@ -25,7 +25,6 @@ #include #include #include -#include #include #include diff --git a/arch/arm/plat-omap/cpu-omap.c b/arch/arm/plat-omap/cpu-omap.c index 409aac2c4b9..fd894bb0010 100644 --- a/arch/arm/plat-omap/cpu-omap.c +++ b/arch/arm/plat-omap/cpu-omap.c @@ -21,7 +21,6 @@ #include #include -#include #include #include diff --git a/arch/arm/plat-omap/usb.c b/arch/arm/plat-omap/usb.c index 98f1c76f866..14a836d7ac2 100644 --- a/arch/arm/plat-omap/usb.c +++ b/arch/arm/plat-omap/usb.c @@ -33,7 +33,6 @@ #include #include #include -#include #include #include diff --git a/drivers/mtd/maps/bast-flash.c b/drivers/mtd/maps/bast-flash.c index 0c45464e3f7..0ba0ff7d43b 100644 --- a/drivers/mtd/maps/bast-flash.c +++ b/drivers/mtd/maps/bast-flash.c @@ -39,7 +39,6 @@ #include #include -#include #include #include diff --git a/drivers/mtd/maps/ixp2000.c b/drivers/mtd/maps/ixp2000.c index 3e94b616743..a9f86c7fbd5 100644 --- a/drivers/mtd/maps/ixp2000.c +++ b/drivers/mtd/maps/ixp2000.c @@ -30,7 +30,6 @@ #include #include -#include #include #include diff --git a/drivers/mtd/maps/ixp4xx.c b/drivers/mtd/maps/ixp4xx.c index 5afe660aa2c..05f48427a87 100644 --- a/drivers/mtd/maps/ixp4xx.c +++ b/drivers/mtd/maps/ixp4xx.c @@ -26,7 +26,6 @@ #include #include #include -#include #include #include diff --git a/drivers/mtd/maps/omap_nor.c b/drivers/mtd/maps/omap_nor.c index 8cc71409a32..b17bca657da 100644 --- a/drivers/mtd/maps/omap_nor.c +++ b/drivers/mtd/maps/omap_nor.c @@ -42,7 +42,6 @@ #include #include -#include #include #include diff --git a/drivers/mtd/maps/sa1100-flash.c b/drivers/mtd/maps/sa1100-flash.c index 52385705da0..8dcaa357b4b 100644 --- a/drivers/mtd/maps/sa1100-flash.c +++ b/drivers/mtd/maps/sa1100-flash.c @@ -21,7 +21,6 @@ #include #include -#include #include #include #include diff --git a/drivers/mtd/nand/s3c2410.c b/drivers/mtd/nand/s3c2410.c index 891e3a1b911..b47ebcb31e0 100644 --- a/drivers/mtd/nand/s3c2410.c +++ b/drivers/mtd/nand/s3c2410.c @@ -58,7 +58,6 @@ #include #include -#include #include #include diff --git a/drivers/pcmcia/omap_cf.c b/drivers/pcmcia/omap_cf.c index 08d1c928826..94be9e51654 100644 --- a/drivers/pcmcia/omap_cf.c +++ b/drivers/pcmcia/omap_cf.c @@ -22,7 +22,6 @@ #include #include -#include #include #include diff --git a/drivers/serial/s3c2410.c b/drivers/serial/s3c2410.c index c361c6fb080..3c04f590c36 100644 --- a/drivers/serial/s3c2410.c +++ b/drivers/serial/s3c2410.c @@ -82,8 +82,6 @@ #include #include -#include - /* structures */ struct s3c24xx_uart_info { diff --git a/drivers/usb/host/ohci-lh7a404.c b/drivers/usb/host/ohci-lh7a404.c index 198c1c666e2..859aca7be75 100644 --- a/drivers/usb/host/ohci-lh7a404.c +++ b/drivers/usb/host/ohci-lh7a404.c @@ -17,7 +17,6 @@ */ #include -#include extern int usb_disabled(void); diff --git a/drivers/usb/host/ohci-s3c2410.c b/drivers/usb/host/ohci-s3c2410.c index 3d9bcf78a9a..da7d5478f74 100644 --- a/drivers/usb/host/ohci-s3c2410.c +++ b/drivers/usb/host/ohci-s3c2410.c @@ -20,7 +20,6 @@ */ #include -#include #include #include diff --git a/drivers/video/backlight/corgi_bl.c b/drivers/video/backlight/corgi_bl.c index 630f2dfa969..3c72c627e65 100644 --- a/drivers/video/backlight/corgi_bl.c +++ b/drivers/video/backlight/corgi_bl.c @@ -19,7 +19,6 @@ #include #include -#include #include #define CORGI_DEFAULT_INTENSITY 0x1f diff --git a/drivers/video/imxfb.c b/drivers/video/imxfb.c index 6c2244cf0e7..1d54d3d6960 100644 --- a/drivers/video/imxfb.c +++ b/drivers/video/imxfb.c @@ -36,7 +36,6 @@ #include #include -#include #include #include -- cgit v1.2.3 From a0800f6da7c4590d49ae513d9d5ee8b1ad203b82 Mon Sep 17 00:00:00 2001 From: Wim Van Sebroeck Date: Thu, 29 Sep 2005 16:21:50 +0200 Subject: [WATCHDOG] pcwd_pci.c control status + boot-code clean-up * Clean-up control status code (use control status defines + change pcipcwd_clear_status) * Clean-up boot-code (move card info to pcipcwd_show_card_info() ) Signed-off-by: Wim Van Sebroeck --- drivers/char/watchdog/pcwd_pci.c | 175 ++++++++++++++++++++++++--------------- 1 file changed, 108 insertions(+), 67 deletions(-) diff --git a/drivers/char/watchdog/pcwd_pci.c b/drivers/char/watchdog/pcwd_pci.c index 5a80adbf803..0cb62e39e58 100644 --- a/drivers/char/watchdog/pcwd_pci.c +++ b/drivers/char/watchdog/pcwd_pci.c @@ -50,8 +50,8 @@ #include /* For inb/outb/... */ /* Module and version information */ -#define WATCHDOG_VERSION "1.01" -#define WATCHDOG_DATE "02 Sep 2005" +#define WATCHDOG_VERSION "1.02" +#define WATCHDOG_DATE "03 Sep 2005" #define WATCHDOG_DRIVER_NAME "PCI-PC Watchdog" #define WATCHDOG_NAME "pcwd_pci" #define PFX WATCHDOG_NAME ": " @@ -70,19 +70,30 @@ * These are the defines that describe the control status bits for the * PCI-PC Watchdog card. */ -#define WD_PCI_WTRP 0x01 /* Watchdog Trip status */ -#define WD_PCI_HRBT 0x02 /* Watchdog Heartbeat */ -#define WD_PCI_TTRP 0x04 /* Temperature Trip status */ +/* Port 1 : Control Status #1 */ +#define WD_PCI_WTRP 0x01 /* Watchdog Trip status */ +#define WD_PCI_HRBT 0x02 /* Watchdog Heartbeat */ +#define WD_PCI_TTRP 0x04 /* Temperature Trip status */ +#define WD_PCI_RL2A 0x08 /* Relay 2 Active */ +#define WD_PCI_RL1A 0x10 /* Relay 1 Active */ +#define WD_PCI_R2DS 0x40 /* Relay 2 Disable Temperature-trip/reset */ +#define WD_PCI_RLY2 0x80 /* Activate Relay 2 on the board */ +/* Port 2 : Control Status #2 */ +#define WD_PCI_WDIS 0x10 /* Watchdog Disable */ +#define WD_PCI_ENTP 0x20 /* Enable Temperature Trip Reset */ +#define WD_PCI_WRSP 0x40 /* Watchdog wrote response */ +#define WD_PCI_PCMD 0x80 /* PC has sent command */ /* according to documentation max. time to process a command for the pci * watchdog card is 100 ms, so we give it 150 ms to do it's job */ #define PCI_COMMAND_TIMEOUT 150 /* Watchdog's internal commands */ -#define CMD_GET_STATUS 0x04 -#define CMD_GET_FIRMWARE_VERSION 0x08 -#define CMD_READ_WATCHDOG_TIMEOUT 0x18 -#define CMD_WRITE_WATCHDOG_TIMEOUT 0x19 +#define CMD_GET_STATUS 0x04 +#define CMD_GET_FIRMWARE_VERSION 0x08 +#define CMD_READ_WATCHDOG_TIMEOUT 0x18 +#define CMD_WRITE_WATCHDOG_TIMEOUT 0x19 +#define CMD_GET_CLEAR_RESET_COUNT 0x84 /* We can only use 1 card due to the /dev/watchdog restriction */ static int cards_found; @@ -91,12 +102,12 @@ static int cards_found; static int temp_panic; static unsigned long is_active; static char expect_release; -static struct { - int supports_temp; /* Wether or not the card has a temperature device */ - int boot_status; /* The card's boot status */ - unsigned long io_addr; /* The cards I/O address */ - spinlock_t io_lock; - struct pci_dev *pdev; +static struct { /* this is private data for each PCI-PC watchdog card */ + int supports_temp; /* Wether or not the card has a temperature device */ + int boot_status; /* The card's boot status */ + unsigned long io_addr; /* The cards I/O address */ + spinlock_t io_lock; /* the lock for io operations */ + struct pci_dev *pdev; /* the PCI-device */ } pcipcwd_private; /* module parameters */ @@ -131,10 +142,10 @@ static int send_command(int cmd, int *msb, int *lsb) /* wait till the pci card processed the command, signaled by * the WRSP bit in port 2 and give it a max. timeout of * PCI_COMMAND_TIMEOUT to process */ - got_response = inb_p(pcipcwd_private.io_addr + 2) & 0x40; + got_response = inb_p(pcipcwd_private.io_addr + 2) & WD_PCI_WRSP; for (count = 0; (count < PCI_COMMAND_TIMEOUT) && (!got_response); count++) { mdelay(1); - got_response = inb_p(pcipcwd_private.io_addr + 2) & 0x40; + got_response = inb_p(pcipcwd_private.io_addr + 2) & WD_PCI_WRSP; } if (got_response) { @@ -150,6 +161,55 @@ static int send_command(int cmd, int *msb, int *lsb) return got_response; } +static inline void pcipcwd_check_temperature_support(void) +{ + if (inb_p(pcipcwd_private.io_addr) != 0xF0) + pcipcwd_private.supports_temp = 1; +} + +static int pcipcwd_get_option_switches(void) +{ + int option_switches; + + option_switches = inb_p(pcipcwd_private.io_addr + 3); + return option_switches; +} + +static void pcipcwd_show_card_info(void) +{ + int got_fw_rev, fw_rev_major, fw_rev_minor; + char fw_ver_str[20]; /* The cards firmware version */ + int option_switches; + + got_fw_rev = send_command(CMD_GET_FIRMWARE_VERSION, &fw_rev_major, &fw_rev_minor); + if (got_fw_rev) { + sprintf(fw_ver_str, "%u.%02u", fw_rev_major, fw_rev_minor); + } else { + sprintf(fw_ver_str, ""); + } + + /* Get switch settings */ + option_switches = pcipcwd_get_option_switches(); + + printk(KERN_INFO PFX "Found card at port 0x%04x (Firmware: %s) %s temp option\n", + (int) pcipcwd_private.io_addr, fw_ver_str, + (pcipcwd_private.supports_temp ? "with" : "without")); + + printk(KERN_INFO PFX "Option switches (0x%02x): Temperature Reset Enable=%s, Power On Delay=%s\n", + option_switches, + ((option_switches & 0x10) ? "ON" : "OFF"), + ((option_switches & 0x08) ? "ON" : "OFF")); + + if (pcipcwd_private.boot_status & WDIOF_CARDRESET) + printk(KERN_INFO PFX "Previous reset was caused by the Watchdog card\n"); + + if (pcipcwd_private.boot_status & WDIOF_OVERHEAT) + printk(KERN_INFO PFX "Card sensed a CPU Overheat\n"); + + if (pcipcwd_private.boot_status == 0) + printk(KERN_INFO PFX "No previous trip detected - Cold boot or reset\n"); +} + static int pcipcwd_start(void) { int stat_reg; @@ -161,7 +221,7 @@ static int pcipcwd_start(void) stat_reg = inb_p(pcipcwd_private.io_addr + 2); spin_unlock(&pcipcwd_private.io_lock); - if (stat_reg & 0x10) { + if (stat_reg & WD_PCI_WDIS) { printk(KERN_ERR PFX "Card timer not enabled\n"); return -1; } @@ -183,7 +243,7 @@ static int pcipcwd_stop(void) stat_reg = inb_p(pcipcwd_private.io_addr + 2); spin_unlock(&pcipcwd_private.io_lock); - if (!(stat_reg & 0x10)) { + if (!(stat_reg & WD_PCI_WDIS)) { printk(KERN_ERR PFX "Card did not acknowledge disable attempt\n"); return -1; } @@ -194,7 +254,7 @@ static int pcipcwd_stop(void) static int pcipcwd_keepalive(void) { /* Re-trigger watchdog by writing to port 0 */ - outb_p(0x42, pcipcwd_private.io_addr); + outb_p(0x42, pcipcwd_private.io_addr); /* send out any data */ return 0; } @@ -215,13 +275,13 @@ static int pcipcwd_set_heartbeat(int t) static int pcipcwd_get_status(int *status) { - int new_status; + int control_status; *status=0; - new_status = inb_p(pcipcwd_private.io_addr + 1); - if (new_status & WD_PCI_WTRP) + control_status = inb_p(pcipcwd_private.io_addr + 1); + if (control_status & WD_PCI_WTRP) *status |= WDIOF_CARDRESET; - if (new_status & WD_PCI_TTRP) { + if (control_status & WD_PCI_TTRP) { *status |= WDIOF_OVERHEAT; if (temp_panic) panic(PFX "Temperature overheat trip!\n"); @@ -232,7 +292,20 @@ static int pcipcwd_get_status(int *status) static int pcipcwd_clear_status(void) { - outb_p(0x01, pcipcwd_private.io_addr + 1); + int control_status; + int msb; + int reset_counter; + + control_status = inb_p(pcipcwd_private.io_addr + 1); + + /* clear trip status & LED and keep mode of relay 2 */ + outb_p((control_status & WD_PCI_R2DS) | WD_PCI_WTRP, pcipcwd_private.io_addr + 1); + + /* clear reset counter */ + msb=0; + reset_counter=0xff; + send_command(CMD_GET_CLEAR_RESET_COUNT, &msb, &reset_counter); + return 0; } @@ -242,11 +315,13 @@ static int pcipcwd_get_temperature(int *temperature) if (!pcipcwd_private.supports_temp) return -ENODEV; + *temperature = inb_p(pcipcwd_private.io_addr); + /* * Convert celsius to fahrenheit, since this was * the decided 'standard' for this return value. */ - *temperature = ((inb_p(pcipcwd_private.io_addr)) * 9 / 5) + 32; + *temperature = (*temperature * 9 / 5) + 32; return 0; } @@ -256,7 +331,7 @@ static int pcipcwd_get_temperature(int *temperature) */ static ssize_t pcipcwd_write(struct file *file, const char __user *data, - size_t len, loff_t *ppos) + size_t len, loff_t *ppos) { /* See if we got the magic character 'V' and reload the timer */ if (len) { @@ -381,8 +456,9 @@ static int pcipcwd_ioctl(struct inode *inode, struct file *file, static int pcipcwd_open(struct inode *inode, struct file *file) { /* /dev/watchdog can only be opened once */ - if (test_and_set_bit(0, &is_active)) + if (test_and_set_bit(0, &is_active)) { return -EBUSY; + } /* Activate */ pcipcwd_start(); @@ -492,19 +568,10 @@ static struct notifier_block pcipcwd_notifier = { * Init & exit routines */ -static inline void check_temperature_support(void) -{ - if (inb_p(pcipcwd_private.io_addr) != 0xF0) - pcipcwd_private.supports_temp = 1; -} - static int __devinit pcipcwd_card_init(struct pci_dev *pdev, const struct pci_device_id *ent) { int ret = -EIO; - int got_fw_rev, fw_rev_major, fw_rev_minor; - char fw_ver_str[20]; - char option_switches; cards_found++; if (cards_found == 1) @@ -546,36 +613,10 @@ static int __devinit pcipcwd_card_init(struct pci_dev *pdev, pcipcwd_stop(); /* Check whether or not the card supports the temperature device */ - check_temperature_support(); - - /* Get the Firmware Version */ - got_fw_rev = send_command(CMD_GET_FIRMWARE_VERSION, &fw_rev_major, &fw_rev_minor); - if (got_fw_rev) { - sprintf(fw_ver_str, "%u.%02u", fw_rev_major, fw_rev_minor); - } else { - sprintf(fw_ver_str, ""); - } + pcipcwd_check_temperature_support(); - /* Get switch settings */ - option_switches = inb_p(pcipcwd_private.io_addr + 3); - - printk(KERN_INFO PFX "Found card at port 0x%04x (Firmware: %s) %s temp option\n", - (int) pcipcwd_private.io_addr, fw_ver_str, - (pcipcwd_private.supports_temp ? "with" : "without")); - - printk(KERN_INFO PFX "Option switches (0x%02x): Temperature Reset Enable=%s, Power On Delay=%s\n", - option_switches, - ((option_switches & 0x10) ? "ON" : "OFF"), - ((option_switches & 0x08) ? "ON" : "OFF")); - - if (pcipcwd_private.boot_status & WDIOF_CARDRESET) - printk(KERN_INFO PFX "Previous reset was caused by the Watchdog card\n"); - - if (pcipcwd_private.boot_status & WDIOF_OVERHEAT) - printk(KERN_INFO PFX "Card sensed a CPU Overheat\n"); - - if (pcipcwd_private.boot_status == 0) - printk(KERN_INFO PFX "No previous trip detected - Cold boot or reset\n"); + /* Show info about the card itself */ + pcipcwd_show_card_info(); /* Check that the heartbeat value is within it's range ; if not reset to the default */ if (pcipcwd_set_heartbeat(heartbeat)) { @@ -656,7 +697,7 @@ static struct pci_driver pcipcwd_driver = { static int __init pcipcwd_init_module(void) { - spin_lock_init (&pcipcwd_private.io_lock); + spin_lock_init(&pcipcwd_private.io_lock); return pci_register_driver(&pcipcwd_driver); } -- cgit v1.2.3 From 195331d7c9813fe7f1a93c09afa2c7dcdf2790a8 Mon Sep 17 00:00:00 2001 From: Wim Van Sebroeck Date: Thu, 29 Sep 2005 16:22:30 +0200 Subject: [WATCHDOG] pcwd_pci.c add debug module_param Add debugging code for the pcwd_pci driver. Signed-off-by: Wim Van Sebroeck --- drivers/char/watchdog/pcwd_pci.c | 64 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 64 insertions(+) diff --git a/drivers/char/watchdog/pcwd_pci.c b/drivers/char/watchdog/pcwd_pci.c index 0cb62e39e58..0b8e493be04 100644 --- a/drivers/char/watchdog/pcwd_pci.c +++ b/drivers/char/watchdog/pcwd_pci.c @@ -111,6 +111,13 @@ static struct { /* this is private data for each PCI-PC watchdog card */ } pcipcwd_private; /* module parameters */ +#define QUIET 0 /* Default */ +#define VERBOSE 1 /* Verbose */ +#define DEBUG 2 /* print fancy stuff too */ +static int debug = QUIET; +module_param(debug, int, 0); +MODULE_PARM_DESC(debug, "Debug level: 0=Quiet, 1=Verbose, 2=Debug (default=0)"); + #define WATCHDOG_HEARTBEAT 2 /* 2 sec default heartbeat */ static int heartbeat = WATCHDOG_HEARTBEAT; module_param(heartbeat, int, 0); @@ -128,6 +135,10 @@ static int send_command(int cmd, int *msb, int *lsb) { int got_response, count; + if (debug >= DEBUG) + printk(KERN_DEBUG PFX "sending following data cmd=0x%02x msb=0x%02x lsb=0x%02x\n", + cmd, *msb, *lsb); + spin_lock(&pcipcwd_private.io_lock); /* If a command requires data it should be written first. * Data for commands with 8 bits of data should be written to port 4. @@ -148,6 +159,15 @@ static int send_command(int cmd, int *msb, int *lsb) got_response = inb_p(pcipcwd_private.io_addr + 2) & WD_PCI_WRSP; } + if (debug >= DEBUG) { + if (got_response) { + printk(KERN_DEBUG PFX "time to process command was: %d ms\n", + count); + } else { + printk(KERN_DEBUG PFX "card did not respond on command!\n"); + } + } + if (got_response) { /* read back response */ *lsb = inb_p(pcipcwd_private.io_addr + 4); @@ -155,7 +175,12 @@ static int send_command(int cmd, int *msb, int *lsb) /* clear WRSP bit */ inb_p(pcipcwd_private.io_addr + 6); + + if (debug >= DEBUG) + printk(KERN_DEBUG PFX "received following data for cmd=0x%02x: msb=0x%02x lsb=0x%02x\n", + cmd, *msb, *lsb); } + spin_unlock(&pcipcwd_private.io_lock); return got_response; @@ -226,6 +251,9 @@ static int pcipcwd_start(void) return -1; } + if (debug >= VERBOSE) + printk(KERN_DEBUG PFX "Watchdog started\n"); + return 0; } @@ -248,6 +276,9 @@ static int pcipcwd_stop(void) return -1; } + if (debug >= VERBOSE) + printk(KERN_DEBUG PFX "Watchdog stopped\n"); + return 0; } @@ -255,6 +286,10 @@ static int pcipcwd_keepalive(void) { /* Re-trigger watchdog by writing to port 0 */ outb_p(0x42, pcipcwd_private.io_addr); /* send out any data */ + + if (debug >= DEBUG) + printk(KERN_DEBUG PFX "Watchdog keepalive signal send\n"); + return 0; } @@ -270,6 +305,10 @@ static int pcipcwd_set_heartbeat(int t) send_command(CMD_WRITE_WATCHDOG_TIMEOUT, &t_msb, &t_lsb); heartbeat = t; + if (debug >= VERBOSE) + printk(KERN_DEBUG PFX "New heartbeat: %d\n", + heartbeat); + return 0; } @@ -287,6 +326,10 @@ static int pcipcwd_get_status(int *status) panic(PFX "Temperature overheat trip!\n"); } + if (debug >= DEBUG) + printk(KERN_DEBUG PFX "Control Status #1: 0x%02x\n", + control_status); + return 0; } @@ -296,8 +339,17 @@ static int pcipcwd_clear_status(void) int msb; int reset_counter; + if (debug >= VERBOSE) + printk(KERN_INFO PFX "clearing watchdog trip status & LED\n"); + control_status = inb_p(pcipcwd_private.io_addr + 1); + if (debug >= DEBUG) { + printk(KERN_DEBUG PFX "status was: 0x%02x\n", control_status); + printk(KERN_DEBUG PFX "sending: 0x%02x\n", + (control_status & WD_PCI_R2DS) | WD_PCI_WTRP); + } + /* clear trip status & LED and keep mode of relay 2 */ outb_p((control_status & WD_PCI_R2DS) | WD_PCI_WTRP, pcipcwd_private.io_addr + 1); @@ -306,6 +358,11 @@ static int pcipcwd_clear_status(void) reset_counter=0xff; send_command(CMD_GET_CLEAR_RESET_COUNT, &msb, &reset_counter); + if (debug >= DEBUG) { + printk(KERN_DEBUG PFX "reset count was: 0x%02x\n", + reset_counter); + } + return 0; } @@ -323,6 +380,11 @@ static int pcipcwd_get_temperature(int *temperature) */ *temperature = (*temperature * 9 / 5) + 32; + if (debug >= DEBUG) { + printk(KERN_DEBUG PFX "temperature is: %d F\n", + *temperature); + } + return 0; } @@ -457,6 +519,8 @@ static int pcipcwd_open(struct inode *inode, struct file *file) { /* /dev/watchdog can only be opened once */ if (test_and_set_bit(0, &is_active)) { + if (debug >= VERBOSE) + printk(KERN_ERR PFX "Attempt to open already opened device.\n"); return -EBUSY; } -- cgit v1.2.3 From ecba97d4aacf4e80c56eb73e39af0369cb8539a4 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Wed, 28 Sep 2005 22:27:23 +0100 Subject: [PATCH] uml makefiles sanitized UML makefiles sanitized: - number of generated headers reduced to 2 (from user-offsets.c and kernel-offsets.c resp.). The rest is made constant and simply includes those two. - mk_... helpers are gone now that we don't need to generate these headers - arch/um/include2 removed since everything under arch/um/include/sysdep is constant now and symlink can point straight to source tree. - dependencies seriously simplified. Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- arch/um/Makefile | 68 +++------------- arch/um/Makefile-i386 | 22 ------ arch/um/Makefile-skas | 2 - arch/um/Makefile-x86_64 | 21 ----- arch/um/include/common-offsets.h | 4 +- arch/um/include/skas_ptregs.h | 6 ++ arch/um/include/sysdep-i386/sc.h | 44 +++++++++++ arch/um/include/sysdep-i386/thread.h | 11 +++ arch/um/include/sysdep-x86_64/sc.h | 45 +++++++++++ arch/um/include/sysdep-x86_64/thread.h | 10 +++ arch/um/include/task.h | 9 +++ arch/um/kernel/skas/Makefile | 2 - arch/um/kernel/skas/util/Makefile | 5 -- arch/um/kernel/skas/util/mk_ptregs-i386.c | 49 ------------ arch/um/kernel/skas/util/mk_ptregs-x86_64.c | 66 ---------------- arch/um/os-Linux/elf_aux.c | 2 +- arch/um/os-Linux/util/Makefile | 4 - arch/um/os-Linux/util/mk_user_constants.c | 23 ------ arch/um/sys-i386/Makefile | 2 - arch/um/sys-i386/kernel-offsets.c | 4 +- arch/um/sys-i386/user-offsets.c | 73 ++++++++--------- arch/um/sys-i386/util/Makefile | 5 -- arch/um/sys-i386/util/mk_sc.c | 51 ------------ arch/um/sys-i386/util/mk_thread.c | 22 ------ arch/um/sys-x86_64/Makefile | 2 - arch/um/sys-x86_64/kernel-offsets.c | 2 +- arch/um/sys-x86_64/user-offsets.c | 117 +++++++++++++++------------- arch/um/sys-x86_64/util/Makefile | 8 -- arch/um/sys-x86_64/util/mk_sc.c | 47 ----------- arch/um/sys-x86_64/util/mk_thread.c | 20 ----- arch/um/util/Makefile | 5 -- arch/um/util/mk_constants.c | 32 -------- arch/um/util/mk_task.c | 30 ------- 33 files changed, 240 insertions(+), 573 deletions(-) create mode 100644 arch/um/include/skas_ptregs.h create mode 100644 arch/um/include/sysdep-i386/sc.h create mode 100644 arch/um/include/sysdep-i386/thread.h create mode 100644 arch/um/include/sysdep-x86_64/sc.h create mode 100644 arch/um/include/sysdep-x86_64/thread.h create mode 100644 arch/um/include/task.h delete mode 100644 arch/um/kernel/skas/util/Makefile delete mode 100644 arch/um/kernel/skas/util/mk_ptregs-i386.c delete mode 100644 arch/um/kernel/skas/util/mk_ptregs-x86_64.c delete mode 100644 arch/um/os-Linux/util/Makefile delete mode 100644 arch/um/os-Linux/util/mk_user_constants.c delete mode 100644 arch/um/sys-i386/util/Makefile delete mode 100644 arch/um/sys-i386/util/mk_sc.c delete mode 100644 arch/um/sys-i386/util/mk_thread.c delete mode 100644 arch/um/sys-x86_64/util/Makefile delete mode 100644 arch/um/sys-x86_64/util/mk_sc.c delete mode 100644 arch/um/sys-x86_64/util/mk_thread.c delete mode 100644 arch/um/util/Makefile delete mode 100644 arch/um/util/mk_constants.c delete mode 100644 arch/um/util/mk_task.c diff --git a/arch/um/Makefile b/arch/um/Makefile index 5b5af95721a..7af37e342e3 100644 --- a/arch/um/Makefile +++ b/arch/um/Makefile @@ -28,8 +28,6 @@ SYMLINK_HEADERS := $(foreach header,$(SYMLINK_HEADERS),include/asm-um/$(header)) ARCH_SYMLINKS = include/asm-um/arch $(ARCH_DIR)/include/sysdep $(ARCH_DIR)/os \ $(SYMLINK_HEADERS) $(ARCH_DIR)/include/uml-config.h -GEN_HEADERS += $(ARCH_DIR)/include/task.h $(ARCH_DIR)/include/kern_constants.h - um-modes-$(CONFIG_MODE_TT) += tt um-modes-$(CONFIG_MODE_SKAS) += skas @@ -45,9 +43,7 @@ endif ARCH_INCLUDE := -I$(ARCH_DIR)/include ifneq ($(KBUILD_SRC),) -ARCH_INCLUDE += -I$(ARCH_DIR)/include2 ARCH_INCLUDE += -I$(srctree)/$(ARCH_DIR)/include -MRPROPER_DIRS += $(ARCH_DIR)/include2 endif SYS_DIR := $(ARCH_DIR)/include/sysdep-$(SUBARCH) @@ -87,10 +83,6 @@ CONFIG_KERNEL_HALF_GIGS ?= 0 SIZE = (($(CONFIG_NEST_LEVEL) + $(CONFIG_KERNEL_HALF_GIGS)) * 0x20000000) -ifeq ($(CONFIG_MODE_SKAS), y) -$(SYS_HEADERS) : $(ARCH_DIR)/include/skas_ptregs.h -endif - .PHONY: linux all: linux @@ -111,7 +103,8 @@ else $(shell cd $(ARCH_DIR) && ln -sf Kconfig.$(SUBARCH) Kconfig.arch) endif -archprepare: $(ARCH_SYMLINKS) $(SYS_HEADERS) $(GEN_HEADERS) +archprepare: $(ARCH_SYMLINKS) $(ARCH_DIR)/include/user_constants.h +prepare: $(ARCH_DIR)/include/kern_constants.h LINK-$(CONFIG_LD_SCRIPT_STATIC) += -static LINK-$(CONFIG_LD_SCRIPT_DYN) += -Wl,-rpath,/lib @@ -146,15 +139,13 @@ endef #When cleaning we don't include .config, so we don't include #TT or skas makefiles and don't clean skas_ptregs.h. CLEAN_FILES += linux x.i gmon.out $(ARCH_DIR)/include/uml-config.h \ - $(GEN_HEADERS) $(ARCH_DIR)/include/skas_ptregs.h \ - $(ARCH_DIR)/include/user_constants.h $(ARCH_DIR)/Kconfig.arch + $(ARCH_DIR)/include/user_constants.h \ + $(ARCH_DIR)/include/kern_constants.h $(ARCH_DIR)/Kconfig.arch MRPROPER_FILES += $(SYMLINK_HEADERS) $(ARCH_SYMLINKS) \ $(addprefix $(ARCH_DIR)/kernel/,$(KERN_SYMLINKS)) $(ARCH_DIR)/os archclean: - $(Q)$(MAKE) $(clean)=$(ARCH_DIR)/util - $(Q)$(MAKE) $(clean)=$(ARCH_DIR)/os-$(OS)/util @find . \( -name '*.bb' -o -name '*.bbg' -o -name '*.da' \ -o -name '*.gcov' \) -type f -print | xargs rm -f @@ -180,9 +171,7 @@ $(ARCH_DIR)/include/sysdep: @echo ' SYMLINK $@' ifneq ($(KBUILD_SRC),) $(Q)mkdir -p $(ARCH_DIR)/include - $(Q)mkdir -p $(ARCH_DIR)/include2 - $(Q)ln -fsn sysdep-$(SUBARCH) $(ARCH_DIR)/include/sysdep - $(Q)ln -fsn $(srctree)/$(ARCH_DIR)/include/sysdep-$(SUBARCH) $(ARCH_DIR)/include2/sysdep + $(Q)ln -fsn $(srctree)/$(ARCH_DIR)/include/sysdep-$(SUBARCH) $(ARCH_DIR)/include/sysdep else $(Q)cd $(ARCH_DIR)/include && ln -sf sysdep-$(SUBARCH) sysdep endif @@ -202,8 +191,6 @@ endef define filechk_gen-asm-offsets (set -e; \ - echo "#ifndef __ASM_OFFSETS_H__"; \ - echo "#define __ASM_OFFSETS_H__"; \ echo "/*"; \ echo " * DO NOT MODIFY."; \ echo " *"; \ @@ -212,8 +199,7 @@ define filechk_gen-asm-offsets echo " */"; \ echo ""; \ sed -ne "/^->/{s:^->\([^ ]*\) [\$$#]*\([^ ]*\) \(.*\):#define \1 \2 /* \3 */:; s:->::; p;}"; \ - echo ""; \ - echo "#endif" ) + echo ""; ) endef $(ARCH_DIR)/include/uml-config.h : include/linux/autoconf.h @@ -222,50 +208,18 @@ $(ARCH_DIR)/include/uml-config.h : include/linux/autoconf.h $(ARCH_DIR)/user-offsets.s: $(ARCH_DIR)/sys-$(SUBARCH)/user-offsets.c $(CC) $(USER_CFLAGS) -S -o $@ $< -$(ARCH_DIR)/user-offsets.h: $(ARCH_DIR)/user-offsets.s +$(ARCH_DIR)/include/user_constants.h: $(ARCH_DIR)/user-offsets.s $(call filechk,gen-asm-offsets) -CLEAN_FILES += $(ARCH_DIR)/user-offsets.s $(ARCH_DIR)/user-offsets.h +CLEAN_FILES += $(ARCH_DIR)/user-offsets.s $(ARCH_DIR)/kernel-offsets.s: $(ARCH_DIR)/sys-$(SUBARCH)/kernel-offsets.c \ - $(ARCH_SYMLINKS) \ - $(SYS_DIR)/sc.h \ - include/asm include/linux/version.h \ - include/config/MARKER \ - $(ARCH_DIR)/include/user_constants.h + archprepare $(CC) $(CFLAGS) $(NOSTDINC_FLAGS) $(CPPFLAGS) -S -o $@ $< -$(ARCH_DIR)/kernel-offsets.h: $(ARCH_DIR)/kernel-offsets.s +$(ARCH_DIR)/include/kern_constants.h: $(ARCH_DIR)/kernel-offsets.s $(call filechk,gen-asm-offsets) -CLEAN_FILES += $(ARCH_DIR)/kernel-offsets.s $(ARCH_DIR)/kernel-offsets.h - -$(ARCH_DIR)/include/task.h: $(ARCH_DIR)/util/mk_task - $(call filechk,gen_header) - -$(ARCH_DIR)/include/user_constants.h: $(ARCH_DIR)/os-$(OS)/util/mk_user_constants - $(call filechk,gen_header) - -$(ARCH_DIR)/include/kern_constants.h: $(ARCH_DIR)/util/mk_constants - $(call filechk,gen_header) - -$(ARCH_DIR)/include/skas_ptregs.h: $(ARCH_DIR)/kernel/skas/util/mk_ptregs - $(call filechk,gen_header) - -$(ARCH_DIR)/os-$(OS)/util/mk_user_constants: $(ARCH_DIR)/os-$(OS)/util FORCE ; - -$(ARCH_DIR)/util/mk_task $(ARCH_DIR)/util/mk_constants: $(ARCH_DIR)/include/user_constants.h $(ARCH_DIR)/util \ - FORCE ; - -$(ARCH_DIR)/kernel/skas/util/mk_ptregs: $(ARCH_DIR)/kernel/skas/util FORCE ; - -$(ARCH_DIR)/util: scripts_basic $(SYS_DIR)/sc.h $(ARCH_DIR)/kernel-offsets.h FORCE - $(Q)$(MAKE) $(build)=$@ - -$(ARCH_DIR)/kernel/skas/util: scripts_basic $(ARCH_DIR)/user-offsets.h FORCE - $(Q)$(MAKE) $(build)=$@ - -$(ARCH_DIR)/os-$(OS)/util: scripts_basic $(ARCH_DIR)/user-offsets.h FORCE - $(Q)$(MAKE) $(build)=$@ +CLEAN_FILES += $(ARCH_DIR)/kernel-offsets.s export SUBARCH USER_CFLAGS OS diff --git a/arch/um/Makefile-i386 b/arch/um/Makefile-i386 index 1ab431a53ac..2ee8a285811 100644 --- a/arch/um/Makefile-i386 +++ b/arch/um/Makefile-i386 @@ -32,25 +32,3 @@ CFLAGS += -U__$(SUBARCH)__ -U$(SUBARCH) ifneq ($(CONFIG_GPROF),y) ARCH_CFLAGS += -DUM_FASTCALL endif - -SYS_UTIL_DIR := $(ARCH_DIR)/sys-i386/util -SYS_HEADERS := $(SYS_DIR)/sc.h $(SYS_DIR)/thread.h - -prepare: $(SYS_HEADERS) - -$(SYS_DIR)/sc.h: $(SYS_UTIL_DIR)/mk_sc - $(call filechk,gen_header) - -$(SYS_DIR)/thread.h: $(SYS_UTIL_DIR)/mk_thread - $(call filechk,gen_header) - -$(SYS_UTIL_DIR)/mk_sc: scripts_basic $(ARCH_DIR)/user-offsets.h FORCE - $(Q)$(MAKE) $(build)=$(SYS_UTIL_DIR) $@ - -$(SYS_UTIL_DIR)/mk_thread: scripts_basic $(ARCH_DIR)/kernel-offsets.h FORCE - $(Q)$(MAKE) $(build)=$(SYS_UTIL_DIR) $@ - -$(SYS_UTIL_DIR): scripts_basic include/asm FORCE - $(Q)$(MAKE) $(build)=$(SYS_UTIL_DIR) - -CLEAN_FILES += $(SYS_HEADERS) diff --git a/arch/um/Makefile-skas b/arch/um/Makefile-skas index fd18ec57227..ac35de5316a 100644 --- a/arch/um/Makefile-skas +++ b/arch/um/Makefile-skas @@ -10,5 +10,3 @@ CFLAGS-$(CONFIG_GCOV) += $(GCOV_OPT) CFLAGS-$(CONFIG_GPROF) += $(GPROF_OPT) LINK-$(CONFIG_GCOV) += $(GCOV_OPT) LINK-$(CONFIG_GPROF) += $(GPROF_OPT) - -GEN_HEADERS += $(ARCH_DIR)/include/skas_ptregs.h diff --git a/arch/um/Makefile-x86_64 b/arch/um/Makefile-x86_64 index 436abbba409..4f118d5cc2e 100644 --- a/arch/um/Makefile-x86_64 +++ b/arch/um/Makefile-x86_64 @@ -12,24 +12,3 @@ CHECKFLAGS += -m64 ELF_ARCH := i386:x86-64 ELF_FORMAT := elf64-x86-64 - -SYS_UTIL_DIR := $(ARCH_DIR)/sys-x86_64/util -SYS_DIR := $(ARCH_DIR)/include/sysdep-x86_64 - -SYS_HEADERS = $(SYS_DIR)/sc.h $(SYS_DIR)/thread.h - -prepare: $(SYS_HEADERS) - -$(SYS_DIR)/sc.h: $(SYS_UTIL_DIR)/mk_sc - $(call filechk,gen_header) - -$(SYS_DIR)/thread.h: $(SYS_UTIL_DIR)/mk_thread - $(call filechk,gen_header) - -$(SYS_UTIL_DIR)/mk_sc: scripts_basic $(ARCH_DIR)/user-offsets.h FORCE - $(Q)$(MAKE) $(build)=$(SYS_UTIL_DIR) $@ - -$(SYS_UTIL_DIR)/mk_thread: scripts_basic $(GEN_HEADERS) $(ARCH_DIR)/kernel-offsets.h FORCE - $(Q)$(MAKE) $(build)=$(SYS_UTIL_DIR) $@ - -CLEAN_FILES += $(SYS_HEADERS) diff --git a/arch/um/include/common-offsets.h b/arch/um/include/common-offsets.h index 782ac3a3baf..356390d1f8b 100644 --- a/arch/um/include/common-offsets.h +++ b/arch/um/include/common-offsets.h @@ -1,7 +1,7 @@ /* for use by sys-$SUBARCH/kernel-offsets.c */ -OFFSET(TASK_REGS, task_struct, thread.regs); -OFFSET(TASK_PID, task_struct, pid); +OFFSET(HOST_TASK_REGS, task_struct, thread.regs); +OFFSET(HOST_TASK_PID, task_struct, pid); DEFINE(UM_KERN_PAGE_SIZE, PAGE_SIZE); DEFINE(UM_NSEC_PER_SEC, NSEC_PER_SEC); DEFINE_STR(UM_KERN_EMERG, KERN_EMERG); diff --git a/arch/um/include/skas_ptregs.h b/arch/um/include/skas_ptregs.h new file mode 100644 index 00000000000..73db19e9c07 --- /dev/null +++ b/arch/um/include/skas_ptregs.h @@ -0,0 +1,6 @@ +#ifndef __SKAS_PT_REGS_ +#define __SKAS_PT_REGS_ + +#include + +#endif diff --git a/arch/um/include/sysdep-i386/sc.h b/arch/um/include/sysdep-i386/sc.h new file mode 100644 index 00000000000..c57d1780ad3 --- /dev/null +++ b/arch/um/include/sysdep-i386/sc.h @@ -0,0 +1,44 @@ +#ifndef __SYSDEP_I386_SC_H +#define __SYSDEP_I386_SC_H + +#include + +#define SC_OFFSET(sc, field) \ + *((unsigned long *) &(((char *) (sc))[HOST_##field])) +#define SC_FP_OFFSET(sc, field) \ + *((unsigned long *) &(((char *) (SC_FPSTATE(sc)))[HOST_##field])) +#define SC_FP_OFFSET_PTR(sc, field, type) \ + ((type *) &(((char *) (SC_FPSTATE(sc)))[HOST_##field])) + +#define SC_IP(sc) SC_OFFSET(sc, SC_IP) +#define SC_SP(sc) SC_OFFSET(sc, SC_SP) +#define SC_FS(sc) SC_OFFSET(sc, SC_FS) +#define SC_GS(sc) SC_OFFSET(sc, SC_GS) +#define SC_DS(sc) SC_OFFSET(sc, SC_DS) +#define SC_ES(sc) SC_OFFSET(sc, SC_ES) +#define SC_SS(sc) SC_OFFSET(sc, SC_SS) +#define SC_CS(sc) SC_OFFSET(sc, SC_CS) +#define SC_EFLAGS(sc) SC_OFFSET(sc, SC_EFLAGS) +#define SC_EAX(sc) SC_OFFSET(sc, SC_EAX) +#define SC_EBX(sc) SC_OFFSET(sc, SC_EBX) +#define SC_ECX(sc) SC_OFFSET(sc, SC_ECX) +#define SC_EDX(sc) SC_OFFSET(sc, SC_EDX) +#define SC_EDI(sc) SC_OFFSET(sc, SC_EDI) +#define SC_ESI(sc) SC_OFFSET(sc, SC_ESI) +#define SC_EBP(sc) SC_OFFSET(sc, SC_EBP) +#define SC_TRAPNO(sc) SC_OFFSET(sc, SC_TRAPNO) +#define SC_ERR(sc) SC_OFFSET(sc, SC_ERR) +#define SC_CR2(sc) SC_OFFSET(sc, SC_CR2) +#define SC_FPSTATE(sc) SC_OFFSET(sc, SC_FPSTATE) +#define SC_SIGMASK(sc) SC_OFFSET(sc, SC_SIGMASK) +#define SC_FP_CW(sc) SC_FP_OFFSET(sc, SC_FP_CW) +#define SC_FP_SW(sc) SC_FP_OFFSET(sc, SC_FP_SW) +#define SC_FP_TAG(sc) SC_FP_OFFSET(sc, SC_FP_TAG) +#define SC_FP_IPOFF(sc) SC_FP_OFFSET(sc, SC_FP_IPOFF) +#define SC_FP_CSSEL(sc) SC_FP_OFFSET(sc, SC_FP_CSSEL) +#define SC_FP_DATAOFF(sc) SC_FP_OFFSET(sc, SC_FP_DATAOFF) +#define SC_FP_DATASEL(sc) SC_FP_OFFSET(sc, SC_FP_DATASEL) +#define SC_FP_ST(sc) SC_FP_OFFSET_PTR(sc, SC_FP_ST, struct _fpstate) +#define SC_FXSR_ENV(sc) SC_FP_OFFSET_PTR(sc, SC_FXSR_ENV, void) + +#endif diff --git a/arch/um/include/sysdep-i386/thread.h b/arch/um/include/sysdep-i386/thread.h new file mode 100644 index 00000000000..e2bd6bae8b8 --- /dev/null +++ b/arch/um/include/sysdep-i386/thread.h @@ -0,0 +1,11 @@ +#ifndef __UM_THREAD_H +#define __UM_THREAD_H + +#include + +#define TASK_DEBUGREGS(task) ((unsigned long *) &(((char *) (task))[HOST_TASK_DEBUGREGS])) +#ifdef CONFIG_MODE_TT +#define TASK_EXTERN_PID(task) *((int *) &(((char *) (task))[HOST_TASK_EXTERN_PID])) +#endif + +#endif diff --git a/arch/um/include/sysdep-x86_64/sc.h b/arch/um/include/sysdep-x86_64/sc.h new file mode 100644 index 00000000000..a160d9fcc59 --- /dev/null +++ b/arch/um/include/sysdep-x86_64/sc.h @@ -0,0 +1,45 @@ +#ifndef __SYSDEP_X86_64_SC_H +#define __SYSDEP_X86_64_SC_H + +/* Copyright (C) 2003 - 2004 PathScale, Inc + * Released under the GPL + */ + +#include + +#define SC_OFFSET(sc, field) \ + *((unsigned long *) &(((char *) (sc))[HOST_##field])) + +#define SC_RBX(sc) SC_OFFSET(sc, SC_RBX) +#define SC_RCX(sc) SC_OFFSET(sc, SC_RCX) +#define SC_RDX(sc) SC_OFFSET(sc, SC_RDX) +#define SC_RSI(sc) SC_OFFSET(sc, SC_RSI) +#define SC_RDI(sc) SC_OFFSET(sc, SC_RDI) +#define SC_RBP(sc) SC_OFFSET(sc, SC_RBP) +#define SC_RAX(sc) SC_OFFSET(sc, SC_RAX) +#define SC_R8(sc) SC_OFFSET(sc, SC_R8) +#define SC_R9(sc) SC_OFFSET(sc, SC_R9) +#define SC_R10(sc) SC_OFFSET(sc, SC_R10) +#define SC_R11(sc) SC_OFFSET(sc, SC_R11) +#define SC_R12(sc) SC_OFFSET(sc, SC_R12) +#define SC_R13(sc) SC_OFFSET(sc, SC_R13) +#define SC_R14(sc) SC_OFFSET(sc, SC_R14) +#define SC_R15(sc) SC_OFFSET(sc, SC_R15) +#define SC_IP(sc) SC_OFFSET(sc, SC_IP) +#define SC_SP(sc) SC_OFFSET(sc, SC_SP) +#define SC_CR2(sc) SC_OFFSET(sc, SC_CR2) +#define SC_ERR(sc) SC_OFFSET(sc, SC_ERR) +#define SC_TRAPNO(sc) SC_OFFSET(sc, SC_TRAPNO) +#define SC_CS(sc) SC_OFFSET(sc, SC_CS) +#define SC_FS(sc) SC_OFFSET(sc, SC_FS) +#define SC_GS(sc) SC_OFFSET(sc, SC_GS) +#define SC_EFLAGS(sc) SC_OFFSET(sc, SC_EFLAGS) +#define SC_SIGMASK(sc) SC_OFFSET(sc, SC_SIGMASK) +#if 0 +#define SC_ORIG_RAX(sc) SC_OFFSET(sc, SC_ORIG_RAX) +#define SC_DS(sc) SC_OFFSET(sc, SC_DS) +#define SC_ES(sc) SC_OFFSET(sc, SC_ES) +#define SC_SS(sc) SC_OFFSET(sc, SC_SS) +#endif + +#endif diff --git a/arch/um/include/sysdep-x86_64/thread.h b/arch/um/include/sysdep-x86_64/thread.h new file mode 100644 index 00000000000..6a76a7f3683 --- /dev/null +++ b/arch/um/include/sysdep-x86_64/thread.h @@ -0,0 +1,10 @@ +#ifndef __UM_THREAD_H +#define __UM_THREAD_H + +#include + +#ifdef CONFIG_MODE_TT +#define TASK_EXTERN_PID(task) *((int *) &(((char *) (task))[HOST_TASK_EXTERN_PID])) +#endif + +#endif diff --git a/arch/um/include/task.h b/arch/um/include/task.h new file mode 100644 index 00000000000..6375ba7203c --- /dev/null +++ b/arch/um/include/task.h @@ -0,0 +1,9 @@ +#ifndef __TASK_H +#define __TASK_H + +#include + +#define TASK_REGS(task) ((union uml_pt_regs *) &(((char *) (task))[HOST_TASK_REGS])) +#define TASK_PID(task) *((int *) &(((char *) (task))[HOST_TASK_PID])) + +#endif diff --git a/arch/um/kernel/skas/Makefile b/arch/um/kernel/skas/Makefile index db36c7c9594..8de471b59c1 100644 --- a/arch/um/kernel/skas/Makefile +++ b/arch/um/kernel/skas/Makefile @@ -6,8 +6,6 @@ obj-y := clone.o exec_kern.o mem.o mem_user.o mmu.o process.o process_kern.o \ syscall.o tlb.o trap_user.o uaccess.o -subdir- := util - USER_OBJS := process.o clone.o include arch/um/scripts/Makefile.rules diff --git a/arch/um/kernel/skas/util/Makefile b/arch/um/kernel/skas/util/Makefile deleted file mode 100644 index f7b7eba8334..00000000000 --- a/arch/um/kernel/skas/util/Makefile +++ /dev/null @@ -1,5 +0,0 @@ -hostprogs-y := mk_ptregs -always := $(hostprogs-y) - -mk_ptregs-objs := mk_ptregs-$(SUBARCH).o -HOSTCFLAGS_mk_ptregs-$(SUBARCH).o := -I$(objtree)/arch/um diff --git a/arch/um/kernel/skas/util/mk_ptregs-i386.c b/arch/um/kernel/skas/util/mk_ptregs-i386.c deleted file mode 100644 index 1f96e1eeb8a..00000000000 --- a/arch/um/kernel/skas/util/mk_ptregs-i386.c +++ /dev/null @@ -1,49 +0,0 @@ -#include -#include - -#define SHOW(name) printf("#define %s %d\n", #name, name) - -int main(int argc, char **argv) -{ - printf("/* Automatically generated by " - "arch/um/kernel/skas/util/mk_ptregs */\n"); - printf("\n"); - printf("#ifndef __SKAS_PT_REGS_\n"); - printf("#define __SKAS_PT_REGS_\n"); - printf("\n"); - SHOW(HOST_FRAME_SIZE); - SHOW(HOST_FP_SIZE); - SHOW(HOST_XFP_SIZE); - - SHOW(HOST_IP); - SHOW(HOST_SP); - SHOW(HOST_EFLAGS); - SHOW(HOST_EAX); - SHOW(HOST_EBX); - SHOW(HOST_ECX); - SHOW(HOST_EDX); - SHOW(HOST_ESI); - SHOW(HOST_EDI); - SHOW(HOST_EBP); - SHOW(HOST_CS); - SHOW(HOST_SS); - SHOW(HOST_DS); - SHOW(HOST_FS); - SHOW(HOST_ES); - SHOW(HOST_GS); - - printf("\n"); - printf("#endif\n"); - return(0); -} - -/* - * Overrides for Emacs so that we follow Linus's tabbing style. - * Emacs will notice this stuff at the end of the file and automatically - * adjust the settings for this buffer only. This must remain at the end - * of the file. - * --------------------------------------------------------------------------- - * Local variables: - * c-file-style: "linux" - * End: - */ diff --git a/arch/um/kernel/skas/util/mk_ptregs-x86_64.c b/arch/um/kernel/skas/util/mk_ptregs-x86_64.c deleted file mode 100644 index 5fccbfe35f7..00000000000 --- a/arch/um/kernel/skas/util/mk_ptregs-x86_64.c +++ /dev/null @@ -1,66 +0,0 @@ -/* - * Copyright 2003 PathScale, Inc. - * - * Licensed under the GPL - */ - -#include -#include - -#define SHOW(name) \ - printf("#define %s (%d / sizeof(unsigned long))\n", #name, name) - -int main(int argc, char **argv) -{ - printf("/* Automatically generated by " - "arch/um/kernel/skas/util/mk_ptregs */\n"); - printf("\n"); - printf("#ifndef __SKAS_PT_REGS_\n"); - printf("#define __SKAS_PT_REGS_\n"); - SHOW(HOST_FRAME_SIZE); - SHOW(HOST_RBX); - SHOW(HOST_RCX); - SHOW(HOST_RDI); - SHOW(HOST_RSI); - SHOW(HOST_RDX); - SHOW(HOST_RBP); - SHOW(HOST_RAX); - SHOW(HOST_R8); - SHOW(HOST_R9); - SHOW(HOST_R10); - SHOW(HOST_R11); - SHOW(HOST_R12); - SHOW(HOST_R13); - SHOW(HOST_R14); - SHOW(HOST_R15); - SHOW(HOST_ORIG_RAX); - SHOW(HOST_CS); - SHOW(HOST_SS); - SHOW(HOST_EFLAGS); -#if 0 - SHOW(HOST_FS); - SHOW(HOST_GS); - SHOW(HOST_DS); - SHOW(HOST_ES); -#endif - - SHOW(HOST_IP); - SHOW(HOST_SP); - printf("#define HOST_FP_SIZE 0\n"); - printf("#define HOST_XFP_SIZE 0\n"); - printf("\n"); - printf("\n"); - printf("#endif\n"); - return(0); -} - -/* - * Overrides for Emacs so that we follow Linus's tabbing style. - * Emacs will notice this stuff at the end of the file and automatically - * adjust the settings for this buffer only. This must remain at the end - * of the file. - * --------------------------------------------------------------------------- - * Local variables: - * c-file-style: "linux" - * End: - */ diff --git a/arch/um/os-Linux/elf_aux.c b/arch/um/os-Linux/elf_aux.c index ab33cb3c74e..5a99dd3fbed 100644 --- a/arch/um/os-Linux/elf_aux.c +++ b/arch/um/os-Linux/elf_aux.c @@ -12,7 +12,7 @@ #include "init.h" #include "elf_user.h" #include "mem_user.h" -#include +#include /* Use the one from the kernel - the host may miss it, if having old headers. */ #if UM_ELF_CLASS == UM_ELFCLASS32 diff --git a/arch/um/os-Linux/util/Makefile b/arch/um/os-Linux/util/Makefile deleted file mode 100644 index 9778aed0c31..00000000000 --- a/arch/um/os-Linux/util/Makefile +++ /dev/null @@ -1,4 +0,0 @@ -hostprogs-y := mk_user_constants -always := $(hostprogs-y) - -HOSTCFLAGS_mk_user_constants.o := -I$(objtree)/arch/um diff --git a/arch/um/os-Linux/util/mk_user_constants.c b/arch/um/os-Linux/util/mk_user_constants.c deleted file mode 100644 index 4838f30eecf..00000000000 --- a/arch/um/os-Linux/util/mk_user_constants.c +++ /dev/null @@ -1,23 +0,0 @@ -#include -#include - -int main(int argc, char **argv) -{ - printf("/*\n"); - printf(" * Generated by mk_user_constants\n"); - printf(" */\n"); - printf("\n"); - printf("#ifndef __UM_USER_CONSTANTS_H\n"); - printf("#define __UM_USER_CONSTANTS_H\n"); - printf("\n"); - /* I'd like to use FRAME_SIZE from ptrace.h here, but that's wrong on - * x86_64 (216 vs 168 bytes). user_regs_struct is the correct size on - * both x86_64 and i386. - */ - printf("#define UM_FRAME_SIZE %d\n", __UM_FRAME_SIZE); - - printf("\n"); - printf("#endif\n"); - - return(0); -} diff --git a/arch/um/sys-i386/Makefile b/arch/um/sys-i386/Makefile index 4ca2a229da4..6dfeb70f695 100644 --- a/arch/um/sys-i386/Makefile +++ b/arch/um/sys-i386/Makefile @@ -18,6 +18,4 @@ module.c-dir = kernel $(obj)/stub_segv.o : _c_flags = $(call unprofile,$(CFLAGS)) -subdir- := util - include arch/um/scripts/Makefile.unmap diff --git a/arch/um/sys-i386/kernel-offsets.c b/arch/um/sys-i386/kernel-offsets.c index a1070af2bcd..35db8505750 100644 --- a/arch/um/sys-i386/kernel-offsets.c +++ b/arch/um/sys-i386/kernel-offsets.c @@ -18,9 +18,9 @@ void foo(void) { - OFFSET(TASK_DEBUGREGS, task_struct, thread.arch.debugregs); + OFFSET(HOST_TASK_DEBUGREGS, task_struct, thread.arch.debugregs); #ifdef CONFIG_MODE_TT - OFFSET(TASK_EXTERN_PID, task_struct, thread.mode.tt.extern_pid); + OFFSET(HOST_TASK_EXTERN_PID, task_struct, thread.mode.tt.extern_pid); #endif #include } diff --git a/arch/um/sys-i386/user-offsets.c b/arch/um/sys-i386/user-offsets.c index 3ceaabceb3d..677fc26a9bb 100644 --- a/arch/um/sys-i386/user-offsets.c +++ b/arch/um/sys-i386/user-offsets.c @@ -7,47 +7,48 @@ #define DEFINE(sym, val) \ asm volatile("\n->" #sym " %0 " #val : : "i" (val)) +#define DEFINE_LONGS(sym, val) \ + asm volatile("\n->" #sym " %0 " #val : : "i" (val/sizeof(unsigned long))) + #define OFFSET(sym, str, mem) \ DEFINE(sym, offsetof(struct str, mem)); void foo(void) { - OFFSET(SC_IP, sigcontext, eip); - OFFSET(SC_SP, sigcontext, esp); - OFFSET(SC_FS, sigcontext, fs); - OFFSET(SC_GS, sigcontext, gs); - OFFSET(SC_DS, sigcontext, ds); - OFFSET(SC_ES, sigcontext, es); - OFFSET(SC_SS, sigcontext, ss); - OFFSET(SC_CS, sigcontext, cs); - OFFSET(SC_EFLAGS, sigcontext, eflags); - OFFSET(SC_EAX, sigcontext, eax); - OFFSET(SC_EBX, sigcontext, ebx); - OFFSET(SC_ECX, sigcontext, ecx); - OFFSET(SC_EDX, sigcontext, edx); - OFFSET(SC_EDI, sigcontext, edi); - OFFSET(SC_ESI, sigcontext, esi); - OFFSET(SC_EBP, sigcontext, ebp); - OFFSET(SC_TRAPNO, sigcontext, trapno); - OFFSET(SC_ERR, sigcontext, err); - OFFSET(SC_CR2, sigcontext, cr2); - OFFSET(SC_FPSTATE, sigcontext, fpstate); - OFFSET(SC_SIGMASK, sigcontext, oldmask); - OFFSET(SC_FP_CW, _fpstate, cw); - OFFSET(SC_FP_SW, _fpstate, sw); - OFFSET(SC_FP_TAG, _fpstate, tag); - OFFSET(SC_FP_IPOFF, _fpstate, ipoff); - OFFSET(SC_FP_CSSEL, _fpstate, cssel); - OFFSET(SC_FP_DATAOFF, _fpstate, dataoff); - OFFSET(SC_FP_DATASEL, _fpstate, datasel); - OFFSET(SC_FP_ST, _fpstate, _st); - OFFSET(SC_FXSR_ENV, _fpstate, _fxsr_env); + OFFSET(HOST_SC_IP, sigcontext, eip); + OFFSET(HOST_SC_SP, sigcontext, esp); + OFFSET(HOST_SC_FS, sigcontext, fs); + OFFSET(HOST_SC_GS, sigcontext, gs); + OFFSET(HOST_SC_DS, sigcontext, ds); + OFFSET(HOST_SC_ES, sigcontext, es); + OFFSET(HOST_SC_SS, sigcontext, ss); + OFFSET(HOST_SC_CS, sigcontext, cs); + OFFSET(HOST_SC_EFLAGS, sigcontext, eflags); + OFFSET(HOST_SC_EAX, sigcontext, eax); + OFFSET(HOST_SC_EBX, sigcontext, ebx); + OFFSET(HOST_SC_ECX, sigcontext, ecx); + OFFSET(HOST_SC_EDX, sigcontext, edx); + OFFSET(HOST_SC_EDI, sigcontext, edi); + OFFSET(HOST_SC_ESI, sigcontext, esi); + OFFSET(HOST_SC_EBP, sigcontext, ebp); + OFFSET(HOST_SC_TRAPNO, sigcontext, trapno); + OFFSET(HOST_SC_ERR, sigcontext, err); + OFFSET(HOST_SC_CR2, sigcontext, cr2); + OFFSET(HOST_SC_FPSTATE, sigcontext, fpstate); + OFFSET(HOST_SC_SIGMASK, sigcontext, oldmask); + OFFSET(HOST_SC_FP_CW, _fpstate, cw); + OFFSET(HOST_SC_FP_SW, _fpstate, sw); + OFFSET(HOST_SC_FP_TAG, _fpstate, tag); + OFFSET(HOST_SC_FP_IPOFF, _fpstate, ipoff); + OFFSET(HOST_SC_FP_CSSEL, _fpstate, cssel); + OFFSET(HOST_SC_FP_DATAOFF, _fpstate, dataoff); + OFFSET(HOST_SC_FP_DATASEL, _fpstate, datasel); + OFFSET(HOST_SC_FP_ST, _fpstate, _st); + OFFSET(HOST_SC_FXSR_ENV, _fpstate, _fxsr_env); - DEFINE(HOST_FRAME_SIZE, FRAME_SIZE); - DEFINE(HOST_FP_SIZE, - sizeof(struct user_i387_struct) / sizeof(unsigned long)); - DEFINE(HOST_XFP_SIZE, - sizeof(struct user_fxsr_struct) / sizeof(unsigned long)); + DEFINE_LONGS(HOST_FRAME_SIZE, FRAME_SIZE); + DEFINE_LONGS(HOST_FP_SIZE, sizeof(struct user_i387_struct)); + DEFINE_LONGS(HOST_XFP_SIZE, sizeof(struct user_fxsr_struct)); DEFINE(HOST_IP, EIP); DEFINE(HOST_SP, UESP); @@ -65,5 +66,5 @@ void foo(void) DEFINE(HOST_FS, FS); DEFINE(HOST_ES, ES); DEFINE(HOST_GS, GS); - DEFINE(__UM_FRAME_SIZE, sizeof(struct user_regs_struct)); + DEFINE(UM_FRAME_SIZE, sizeof(struct user_regs_struct)); } diff --git a/arch/um/sys-i386/util/Makefile b/arch/um/sys-i386/util/Makefile deleted file mode 100644 index bf61afd0b04..00000000000 --- a/arch/um/sys-i386/util/Makefile +++ /dev/null @@ -1,5 +0,0 @@ -hostprogs-y := mk_sc mk_thread -always := $(hostprogs-y) - -HOSTCFLAGS_mk_sc.o := -I$(objtree)/arch/um -HOSTCFLAGS_mk_thread.o := -I$(objtree)/arch/um diff --git a/arch/um/sys-i386/util/mk_sc.c b/arch/um/sys-i386/util/mk_sc.c deleted file mode 100644 index 04c0d73433a..00000000000 --- a/arch/um/sys-i386/util/mk_sc.c +++ /dev/null @@ -1,51 +0,0 @@ -#include -#include - -#define SC_OFFSET(name, field) \ - printf("#define " #name "(sc) *((unsigned long *) &(((char *) (sc))[%d]))\n",\ - name) - -#define SC_FP_OFFSET(name, field) \ - printf("#define " #name \ - "(sc) *((unsigned long *) &(((char *) (SC_FPSTATE(sc)))[%d]))\n",\ - name) - -#define SC_FP_OFFSET_PTR(name, field, type) \ - printf("#define " #name \ - "(sc) ((" type " *) &(((char *) (SC_FPSTATE(sc)))[%d]))\n",\ - name) - -int main(int argc, char **argv) -{ - SC_OFFSET(SC_IP, eip); - SC_OFFSET(SC_SP, esp); - SC_OFFSET(SC_FS, fs); - SC_OFFSET(SC_GS, gs); - SC_OFFSET(SC_DS, ds); - SC_OFFSET(SC_ES, es); - SC_OFFSET(SC_SS, ss); - SC_OFFSET(SC_CS, cs); - SC_OFFSET(SC_EFLAGS, eflags); - SC_OFFSET(SC_EAX, eax); - SC_OFFSET(SC_EBX, ebx); - SC_OFFSET(SC_ECX, ecx); - SC_OFFSET(SC_EDX, edx); - SC_OFFSET(SC_EDI, edi); - SC_OFFSET(SC_ESI, esi); - SC_OFFSET(SC_EBP, ebp); - SC_OFFSET(SC_TRAPNO, trapno); - SC_OFFSET(SC_ERR, err); - SC_OFFSET(SC_CR2, cr2); - SC_OFFSET(SC_FPSTATE, fpstate); - SC_OFFSET(SC_SIGMASK, oldmask); - SC_FP_OFFSET(SC_FP_CW, cw); - SC_FP_OFFSET(SC_FP_SW, sw); - SC_FP_OFFSET(SC_FP_TAG, tag); - SC_FP_OFFSET(SC_FP_IPOFF, ipoff); - SC_FP_OFFSET(SC_FP_CSSEL, cssel); - SC_FP_OFFSET(SC_FP_DATAOFF, dataoff); - SC_FP_OFFSET(SC_FP_DATASEL, datasel); - SC_FP_OFFSET_PTR(SC_FP_ST, _st, "struct _fpstate"); - SC_FP_OFFSET_PTR(SC_FXSR_ENV, _fxsr_env, "void"); - return(0); -} diff --git a/arch/um/sys-i386/util/mk_thread.c b/arch/um/sys-i386/util/mk_thread.c deleted file mode 100644 index 7470d0dda67..00000000000 --- a/arch/um/sys-i386/util/mk_thread.c +++ /dev/null @@ -1,22 +0,0 @@ -#include -#include - -int main(int argc, char **argv) -{ - printf("/*\n"); - printf(" * Generated by mk_thread\n"); - printf(" */\n"); - printf("\n"); - printf("#ifndef __UM_THREAD_H\n"); - printf("#define __UM_THREAD_H\n"); - printf("\n"); - printf("#define TASK_DEBUGREGS(task) ((unsigned long *) " - "&(((char *) (task))[%d]))\n", TASK_DEBUGREGS); -#ifdef TASK_EXTERN_PID - printf("#define TASK_EXTERN_PID(task) *((int *) &(((char *) (task))[%d]))\n", - TASK_EXTERN_PID); -#endif - printf("\n"); - printf("#endif\n"); - return(0); -} diff --git a/arch/um/sys-x86_64/Makefile b/arch/um/sys-x86_64/Makefile index f0ab574d1e9..06c3633457a 100644 --- a/arch/um/sys-x86_64/Makefile +++ b/arch/um/sys-x86_64/Makefile @@ -29,6 +29,4 @@ module.c-dir = kernel $(obj)/stub_segv.o: _c_flags = $(call unprofile,$(CFLAGS)) -subdir- := util - include arch/um/scripts/Makefile.unmap diff --git a/arch/um/sys-x86_64/kernel-offsets.c b/arch/um/sys-x86_64/kernel-offsets.c index 998541eade4..bfcb104b846 100644 --- a/arch/um/sys-x86_64/kernel-offsets.c +++ b/arch/um/sys-x86_64/kernel-offsets.c @@ -19,7 +19,7 @@ void foo(void) { #ifdef CONFIG_MODE_TT - OFFSET(TASK_EXTERN_PID, task_struct, thread.mode.tt.extern_pid); + OFFSET(HOST_TASK_EXTERN_PID, task_struct, thread.mode.tt.extern_pid); #endif #include } diff --git a/arch/um/sys-x86_64/user-offsets.c b/arch/um/sys-x86_64/user-offsets.c index 513d17ceafd..5a585bfbb8c 100644 --- a/arch/um/sys-x86_64/user-offsets.c +++ b/arch/um/sys-x86_64/user-offsets.c @@ -16,71 +16,76 @@ typedef __u32 u32; #define DEFINE(sym, val) \ asm volatile("\n->" #sym " %0 " #val : : "i" (val)) +#define DEFINE_LONGS(sym, val) \ + asm volatile("\n->" #sym " %0 " #val : : "i" (val/sizeof(unsigned long))) + #define OFFSET(sym, str, mem) \ DEFINE(sym, offsetof(struct str, mem)); void foo(void) { - OFFSET(SC_RBX, sigcontext, rbx); - OFFSET(SC_RCX, sigcontext, rcx); - OFFSET(SC_RDX, sigcontext, rdx); - OFFSET(SC_RSI, sigcontext, rsi); - OFFSET(SC_RDI, sigcontext, rdi); - OFFSET(SC_RBP, sigcontext, rbp); - OFFSET(SC_RAX, sigcontext, rax); - OFFSET(SC_R8, sigcontext, r8); - OFFSET(SC_R9, sigcontext, r9); - OFFSET(SC_R10, sigcontext, r10); - OFFSET(SC_R11, sigcontext, r11); - OFFSET(SC_R12, sigcontext, r12); - OFFSET(SC_R13, sigcontext, r13); - OFFSET(SC_R14, sigcontext, r14); - OFFSET(SC_R15, sigcontext, r15); - OFFSET(SC_IP, sigcontext, rip); - OFFSET(SC_SP, sigcontext, rsp); - OFFSET(SC_CR2, sigcontext, cr2); - OFFSET(SC_ERR, sigcontext, err); - OFFSET(SC_TRAPNO, sigcontext, trapno); - OFFSET(SC_CS, sigcontext, cs); - OFFSET(SC_FS, sigcontext, fs); - OFFSET(SC_GS, sigcontext, gs); - OFFSET(SC_EFLAGS, sigcontext, eflags); - OFFSET(SC_SIGMASK, sigcontext, oldmask); + OFFSET(HOST_SC_RBX, sigcontext, rbx); + OFFSET(HOST_SC_RCX, sigcontext, rcx); + OFFSET(HOST_SC_RDX, sigcontext, rdx); + OFFSET(HOST_SC_RSI, sigcontext, rsi); + OFFSET(HOST_SC_RDI, sigcontext, rdi); + OFFSET(HOST_SC_RBP, sigcontext, rbp); + OFFSET(HOST_SC_RAX, sigcontext, rax); + OFFSET(HOST_SC_R8, sigcontext, r8); + OFFSET(HOST_SC_R9, sigcontext, r9); + OFFSET(HOST_SC_R10, sigcontext, r10); + OFFSET(HOST_SC_R11, sigcontext, r11); + OFFSET(HOST_SC_R12, sigcontext, r12); + OFFSET(HOST_SC_R13, sigcontext, r13); + OFFSET(HOST_SC_R14, sigcontext, r14); + OFFSET(HOST_SC_R15, sigcontext, r15); + OFFSET(HOST_SC_IP, sigcontext, rip); + OFFSET(HOST_SC_SP, sigcontext, rsp); + OFFSET(HOST_SC_CR2, sigcontext, cr2); + OFFSET(HOST_SC_ERR, sigcontext, err); + OFFSET(HOST_SC_TRAPNO, sigcontext, trapno); + OFFSET(HOST_SC_CS, sigcontext, cs); + OFFSET(HOST_SC_FS, sigcontext, fs); + OFFSET(HOST_SC_GS, sigcontext, gs); + OFFSET(HOST_SC_EFLAGS, sigcontext, eflags); + OFFSET(HOST_SC_SIGMASK, sigcontext, oldmask); #if 0 - OFFSET(SC_ORIG_RAX, sigcontext, orig_rax); - OFFSET(SC_DS, sigcontext, ds); - OFFSET(SC_ES, sigcontext, es); - OFFSET(SC_SS, sigcontext, ss); + OFFSET(HOST_SC_ORIG_RAX, sigcontext, orig_rax); + OFFSET(HOST_SC_DS, sigcontext, ds); + OFFSET(HOST_SC_ES, sigcontext, es); + OFFSET(HOST_SC_SS, sigcontext, ss); #endif - DEFINE(HOST_FRAME_SIZE, FRAME_SIZE); - DEFINE(HOST_RBX, RBX); - DEFINE(HOST_RCX, RCX); - DEFINE(HOST_RDI, RDI); - DEFINE(HOST_RSI, RSI); - DEFINE(HOST_RDX, RDX); - DEFINE(HOST_RBP, RBP); - DEFINE(HOST_RAX, RAX); - DEFINE(HOST_R8, R8); - DEFINE(HOST_R9, R9); - DEFINE(HOST_R10, R10); - DEFINE(HOST_R11, R11); - DEFINE(HOST_R12, R12); - DEFINE(HOST_R13, R13); - DEFINE(HOST_R14, R14); - DEFINE(HOST_R15, R15); - DEFINE(HOST_ORIG_RAX, ORIG_RAX); - DEFINE(HOST_CS, CS); - DEFINE(HOST_SS, SS); - DEFINE(HOST_EFLAGS, EFLAGS); + DEFINE_LONGS(HOST_FRAME_SIZE, FRAME_SIZE); + DEFINE(HOST_FP_SIZE, 0); + DEFINE(HOST_XFP_SIZE, 0); + DEFINE_LONGS(HOST_RBX, RBX); + DEFINE_LONGS(HOST_RCX, RCX); + DEFINE_LONGS(HOST_RDI, RDI); + DEFINE_LONGS(HOST_RSI, RSI); + DEFINE_LONGS(HOST_RDX, RDX); + DEFINE_LONGS(HOST_RBP, RBP); + DEFINE_LONGS(HOST_RAX, RAX); + DEFINE_LONGS(HOST_R8, R8); + DEFINE_LONGS(HOST_R9, R9); + DEFINE_LONGS(HOST_R10, R10); + DEFINE_LONGS(HOST_R11, R11); + DEFINE_LONGS(HOST_R12, R12); + DEFINE_LONGS(HOST_R13, R13); + DEFINE_LONGS(HOST_R14, R14); + DEFINE_LONGS(HOST_R15, R15); + DEFINE_LONGS(HOST_ORIG_RAX, ORIG_RAX); + DEFINE_LONGS(HOST_CS, CS); + DEFINE_LONGS(HOST_SS, SS); + DEFINE_LONGS(HOST_EFLAGS, EFLAGS); #if 0 - DEFINE(HOST_FS, FS); - DEFINE(HOST_GS, GS); - DEFINE(HOST_DS, DS); - DEFINE(HOST_ES, ES); + DEFINE_LONGS(HOST_FS, FS); + DEFINE_LONGS(HOST_GS, GS); + DEFINE_LONGS(HOST_DS, DS); + DEFINE_LONGS(HOST_ES, ES); #endif - DEFINE(HOST_IP, RIP); - DEFINE(HOST_SP, RSP); - DEFINE(__UM_FRAME_SIZE, sizeof(struct user_regs_struct)); + DEFINE_LONGS(HOST_IP, RIP); + DEFINE_LONGS(HOST_SP, RSP); + DEFINE(UM_FRAME_SIZE, sizeof(struct user_regs_struct)); } diff --git a/arch/um/sys-x86_64/util/Makefile b/arch/um/sys-x86_64/util/Makefile deleted file mode 100644 index 75b052cfc20..00000000000 --- a/arch/um/sys-x86_64/util/Makefile +++ /dev/null @@ -1,8 +0,0 @@ -# Copyright 2003 - 2004 Pathscale, Inc -# Released under the GPL - -hostprogs-y := mk_sc mk_thread -always := $(hostprogs-y) - -HOSTCFLAGS_mk_sc.o := -I$(objtree)/arch/um -HOSTCFLAGS_mk_thread.o := -I$(objtree)/arch/um diff --git a/arch/um/sys-x86_64/util/mk_sc.c b/arch/um/sys-x86_64/util/mk_sc.c deleted file mode 100644 index 7619bc377c1..00000000000 --- a/arch/um/sys-x86_64/util/mk_sc.c +++ /dev/null @@ -1,47 +0,0 @@ -/* Copyright (C) 2003 - 2004 PathScale, Inc - * Released under the GPL - */ - -#include -#include - -#define SC_OFFSET(name) \ - printf("#define " #name \ - "(sc) *((unsigned long *) &(((char *) (sc))[%d]))\n",\ - name) - -int main(int argc, char **argv) -{ - SC_OFFSET(SC_RBX); - SC_OFFSET(SC_RCX); - SC_OFFSET(SC_RDX); - SC_OFFSET(SC_RSI); - SC_OFFSET(SC_RDI); - SC_OFFSET(SC_RBP); - SC_OFFSET(SC_RAX); - SC_OFFSET(SC_R8); - SC_OFFSET(SC_R9); - SC_OFFSET(SC_R10); - SC_OFFSET(SC_R11); - SC_OFFSET(SC_R12); - SC_OFFSET(SC_R13); - SC_OFFSET(SC_R14); - SC_OFFSET(SC_R15); - SC_OFFSET(SC_IP); - SC_OFFSET(SC_SP); - SC_OFFSET(SC_CR2); - SC_OFFSET(SC_ERR); - SC_OFFSET(SC_TRAPNO); - SC_OFFSET(SC_CS); - SC_OFFSET(SC_FS); - SC_OFFSET(SC_GS); - SC_OFFSET(SC_EFLAGS); - SC_OFFSET(SC_SIGMASK); -#if 0 - SC_OFFSET(SC_ORIG_RAX); - SC_OFFSET(SC_DS); - SC_OFFSET(SC_ES); - SC_OFFSET(SC_SS); -#endif - return(0); -} diff --git a/arch/um/sys-x86_64/util/mk_thread.c b/arch/um/sys-x86_64/util/mk_thread.c deleted file mode 100644 index 15517396e9c..00000000000 --- a/arch/um/sys-x86_64/util/mk_thread.c +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -int main(int argc, char **argv) -{ - printf("/*\n"); - printf(" * Generated by mk_thread\n"); - printf(" */\n"); - printf("\n"); - printf("#ifndef __UM_THREAD_H\n"); - printf("#define __UM_THREAD_H\n"); - printf("\n"); -#ifdef TASK_EXTERN_PID - printf("#define TASK_EXTERN_PID(task) *((int *) &(((char *) (task))[%d]))\n", - TASK_EXTERN_PID); -#endif - printf("\n"); - printf("#endif\n"); - return(0); -} diff --git a/arch/um/util/Makefile b/arch/um/util/Makefile deleted file mode 100644 index 4c7551c2803..00000000000 --- a/arch/um/util/Makefile +++ /dev/null @@ -1,5 +0,0 @@ -hostprogs-y := mk_task mk_constants -always := $(hostprogs-y) - -HOSTCFLAGS_mk_task.o := -I$(objtree)/arch/um -HOSTCFLAGS_mk_constants.o := -I$(objtree)/arch/um diff --git a/arch/um/util/mk_constants.c b/arch/um/util/mk_constants.c deleted file mode 100644 index ab217becc36..00000000000 --- a/arch/um/util/mk_constants.c +++ /dev/null @@ -1,32 +0,0 @@ -#include -#include - -#define SHOW_INT(sym) printf("#define %s %d\n", #sym, sym) -#define SHOW_STR(sym) printf("#define %s %s\n", #sym, sym) - -int main(int argc, char **argv) -{ - printf("/*\n"); - printf(" * Generated by mk_constants\n"); - printf(" */\n"); - printf("\n"); - printf("#ifndef __UM_CONSTANTS_H\n"); - printf("#define __UM_CONSTANTS_H\n"); - printf("\n"); - - SHOW_INT(UM_KERN_PAGE_SIZE); - - SHOW_STR(UM_KERN_EMERG); - SHOW_STR(UM_KERN_ALERT); - SHOW_STR(UM_KERN_CRIT); - SHOW_STR(UM_KERN_ERR); - SHOW_STR(UM_KERN_WARNING); - SHOW_STR(UM_KERN_NOTICE); - SHOW_STR(UM_KERN_INFO); - SHOW_STR(UM_KERN_DEBUG); - - SHOW_INT(UM_NSEC_PER_SEC); - printf("\n"); - printf("#endif\n"); - return(0); -} diff --git a/arch/um/util/mk_task.c b/arch/um/util/mk_task.c deleted file mode 100644 index 36c9606505e..00000000000 --- a/arch/um/util/mk_task.c +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -void print_ptr(char *name, char *type, int offset) -{ - printf("#define %s(task) ((%s *) &(((char *) (task))[%d]))\n", name, type, - offset); -} - -void print(char *name, char *type, int offset) -{ - printf("#define %s(task) *((%s *) &(((char *) (task))[%d]))\n", name, type, - offset); -} - -int main(int argc, char **argv) -{ - printf("/*\n"); - printf(" * Generated by mk_task\n"); - printf(" */\n"); - printf("\n"); - printf("#ifndef __TASK_H\n"); - printf("#define __TASK_H\n"); - printf("\n"); - print_ptr("TASK_REGS", "union uml_pt_regs", TASK_REGS); - print("TASK_PID", "int", TASK_PID); - printf("\n"); - printf("#endif\n"); - return(0); -} -- cgit v1.2.3 From 666002218d59db271e5c1ede1d80227170c51987 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Wed, 28 Sep 2005 22:32:57 +0100 Subject: [PATCH] proc_mkdir() should be used to create procfs directories A bunch of create_proc_dir_entry() calls creating directories had crept in since the last sweep; converted to proc_mkdir(). Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- drivers/char/drm/drm_drv.c | 2 +- drivers/char/drm/drm_proc.c | 2 +- drivers/isdn/divert/divert_procfs.c | 6 +++--- drivers/isdn/hardware/eicon/diva_didd.c | 6 ++---- drivers/isdn/hardware/eicon/divasproc.c | 2 +- drivers/isdn/hysdn/hysdn_procconf.c | 2 +- drivers/media/video/cpia.c | 2 +- drivers/net/ibmveth.c | 6 +++--- drivers/net/irda/vlsi_ir.c | 4 ++-- drivers/net/pppoe.c | 4 ++-- drivers/net/sk98lin/skge.c | 8 ++++---- drivers/scsi/sg.c | 3 +-- drivers/usb/media/vicam.c | 4 ++-- net/core/pktgen.c | 23 ++++++----------------- net/ieee80211/ieee80211_module.c | 2 +- 15 files changed, 31 insertions(+), 45 deletions(-) diff --git a/drivers/char/drm/drm_drv.c b/drivers/char/drm/drm_drv.c index 6ba48f346fc..041bb47b5c3 100644 --- a/drivers/char/drm/drm_drv.c +++ b/drivers/char/drm/drm_drv.c @@ -376,7 +376,7 @@ static int __init drm_core_init(void) goto err_p2; } - drm_proc_root = create_proc_entry("dri", S_IFDIR, NULL); + drm_proc_root = proc_mkdir("dri", NULL); if (!drm_proc_root) { DRM_ERROR("Cannot create /proc/dri\n"); ret = -1; diff --git a/drivers/char/drm/drm_proc.c b/drivers/char/drm/drm_proc.c index 32d2bb99462..97796100248 100644 --- a/drivers/char/drm/drm_proc.c +++ b/drivers/char/drm/drm_proc.c @@ -95,7 +95,7 @@ int drm_proc_init(drm_device_t *dev, int minor, char name[64]; sprintf(name, "%d", minor); - *dev_root = create_proc_entry(name, S_IFDIR, root); + *dev_root = proc_mkdir(name, root); if (!*dev_root) { DRM_ERROR("Cannot create /proc/dri/%s\n", name); return -1; diff --git a/drivers/isdn/divert/divert_procfs.c b/drivers/isdn/divert/divert_procfs.c index e1f0d87de0e..0b0ea26023e 100644 --- a/drivers/isdn/divert/divert_procfs.c +++ b/drivers/isdn/divert/divert_procfs.c @@ -287,12 +287,12 @@ divert_dev_init(void) init_waitqueue_head(&rd_queue); #ifdef CONFIG_PROC_FS - isdn_proc_entry = create_proc_entry("isdn", S_IFDIR | S_IRUGO | S_IXUGO, proc_net); + isdn_proc_entry = proc_mkdir("net/isdn", NULL); if (!isdn_proc_entry) return (-1); isdn_divert_entry = create_proc_entry("divert", S_IFREG | S_IRUGO, isdn_proc_entry); if (!isdn_divert_entry) { - remove_proc_entry("isdn", proc_net); + remove_proc_entry("net/isdn", NULL); return (-1); } isdn_divert_entry->proc_fops = &isdn_fops; @@ -312,7 +312,7 @@ divert_dev_deinit(void) #ifdef CONFIG_PROC_FS remove_proc_entry("divert", isdn_proc_entry); - remove_proc_entry("isdn", proc_net); + remove_proc_entry("net/isdn", NULL); #endif /* CONFIG_PROC_FS */ return (0); diff --git a/drivers/isdn/hardware/eicon/diva_didd.c b/drivers/isdn/hardware/eicon/diva_didd.c index 7fdf8ae5be5..27204f4b111 100644 --- a/drivers/isdn/hardware/eicon/diva_didd.c +++ b/drivers/isdn/hardware/eicon/diva_didd.c @@ -30,8 +30,6 @@ static char *DRIVERNAME = static char *DRIVERLNAME = "divadidd"; char *DRIVERRELEASE_DIDD = "2.0"; -static char *main_proc_dir = "eicon"; - MODULE_DESCRIPTION("DIDD table driver for diva drivers"); MODULE_AUTHOR("Cytronics & Melware, Eicon Networks"); MODULE_SUPPORTED_DEVICE("Eicon diva drivers"); @@ -89,7 +87,7 @@ proc_read(char *page, char **start, off_t off, int count, int *eof, static int DIVA_INIT_FUNCTION create_proc(void) { - proc_net_eicon = create_proc_entry(main_proc_dir, S_IFDIR, proc_net); + proc_net_eicon = proc_mkdir("net/eicon", NULL); if (proc_net_eicon) { if ((proc_didd = @@ -105,7 +103,7 @@ static int DIVA_INIT_FUNCTION create_proc(void) static void DIVA_EXIT_FUNCTION remove_proc(void) { remove_proc_entry(DRIVERLNAME, proc_net_eicon); - remove_proc_entry(main_proc_dir, proc_net); + remove_proc_entry("net/eicon", NULL); } static int DIVA_INIT_FUNCTION divadidd_init(void) diff --git a/drivers/isdn/hardware/eicon/divasproc.c b/drivers/isdn/hardware/eicon/divasproc.c index b6435589d45..c12efa6f842 100644 --- a/drivers/isdn/hardware/eicon/divasproc.c +++ b/drivers/isdn/hardware/eicon/divasproc.c @@ -381,7 +381,7 @@ int create_adapter_proc(diva_os_xdi_adapter_t * a) char tmp[16]; sprintf(tmp, "%s%d", adapter_dir_name, a->controller); - if (!(de = create_proc_entry(tmp, S_IFDIR, proc_net_eicon))) + if (!(de = proc_mkdir(tmp, proc_net_eicon))) return (0); a->proc_adapter_dir = (void *) de; diff --git a/drivers/isdn/hysdn/hysdn_procconf.c b/drivers/isdn/hysdn/hysdn_procconf.c index 5da507e532f..639582f61f4 100644 --- a/drivers/isdn/hysdn/hysdn_procconf.c +++ b/drivers/isdn/hysdn/hysdn_procconf.c @@ -394,7 +394,7 @@ hysdn_procconf_init(void) hysdn_card *card; uchar conf_name[20]; - hysdn_proc_entry = create_proc_entry(PROC_SUBDIR_NAME, S_IFDIR | S_IRUGO | S_IXUGO, proc_net); + hysdn_proc_entry = proc_mkdir(PROC_SUBDIR_NAME, proc_net); if (!hysdn_proc_entry) { printk(KERN_ERR "HYSDN: unable to create hysdn subdir\n"); return (-1); diff --git a/drivers/media/video/cpia.c b/drivers/media/video/cpia.c index 8c08b7f1ad2..b7ec9bf4508 100644 --- a/drivers/media/video/cpia.c +++ b/drivers/media/video/cpia.c @@ -1397,7 +1397,7 @@ static void destroy_proc_cpia_cam(struct cam_data *cam) static void proc_cpia_create(void) { - cpia_proc_root = create_proc_entry("cpia", S_IFDIR, NULL); + cpia_proc_root = proc_mkdir("cpia", NULL); if (cpia_proc_root) cpia_proc_root->owner = THIS_MODULE; diff --git a/drivers/net/ibmveth.c b/drivers/net/ibmveth.c index 32d5fabd4b1..a2c4dd4fb22 100644 --- a/drivers/net/ibmveth.c +++ b/drivers/net/ibmveth.c @@ -99,7 +99,7 @@ static irqreturn_t ibmveth_interrupt(int irq, void *dev_instance, struct pt_regs static inline void ibmveth_schedule_replenishing(struct ibmveth_adapter*); #ifdef CONFIG_PROC_FS -#define IBMVETH_PROC_DIR "ibmveth" +#define IBMVETH_PROC_DIR "net/ibmveth" static struct proc_dir_entry *ibmveth_proc_dir; #endif @@ -1010,7 +1010,7 @@ static int __devexit ibmveth_remove(struct vio_dev *dev) #ifdef CONFIG_PROC_FS static void ibmveth_proc_register_driver(void) { - ibmveth_proc_dir = create_proc_entry(IBMVETH_PROC_DIR, S_IFDIR, proc_net); + ibmveth_proc_dir = proc_mkdir(IBMVETH_PROC_DIR, NULL); if (ibmveth_proc_dir) { SET_MODULE_OWNER(ibmveth_proc_dir); } @@ -1018,7 +1018,7 @@ static void ibmveth_proc_register_driver(void) static void ibmveth_proc_unregister_driver(void) { - remove_proc_entry(IBMVETH_PROC_DIR, proc_net); + remove_proc_entry(IBMVETH_PROC_DIR, NULL); } static void *ibmveth_seq_start(struct seq_file *seq, loff_t *pos) diff --git a/drivers/net/irda/vlsi_ir.c b/drivers/net/irda/vlsi_ir.c index 6d9de626c96..651c5a6578f 100644 --- a/drivers/net/irda/vlsi_ir.c +++ b/drivers/net/irda/vlsi_ir.c @@ -1875,11 +1875,11 @@ static int __init vlsi_mod_init(void) sirpulse = !!sirpulse; - /* create_proc_entry returns NULL if !CONFIG_PROC_FS. + /* proc_mkdir returns NULL if !CONFIG_PROC_FS. * Failure to create the procfs entry is handled like running * without procfs - it's not required for the driver to work. */ - vlsi_proc_root = create_proc_entry(PROC_DIR, S_IFDIR, NULL); + vlsi_proc_root = proc_mkdir(PROC_DIR, NULL); if (vlsi_proc_root) { /* protect registered procdir against module removal. * Because we are in the module init path there's no race diff --git a/drivers/net/pppoe.c b/drivers/net/pppoe.c index 82f236cc3b9..a842ecc60a3 100644 --- a/drivers/net/pppoe.c +++ b/drivers/net/pppoe.c @@ -1070,7 +1070,7 @@ static int __init pppoe_proc_init(void) { struct proc_dir_entry *p; - p = create_proc_entry("pppoe", S_IRUGO, proc_net); + p = create_proc_entry("net/pppoe", S_IRUGO, NULL); if (!p) return -ENOMEM; @@ -1142,7 +1142,7 @@ static void __exit pppoe_exit(void) dev_remove_pack(&pppoes_ptype); dev_remove_pack(&pppoed_ptype); unregister_netdevice_notifier(&pppoe_notifier); - remove_proc_entry("pppoe", proc_net); + remove_proc_entry("net/pppoe", NULL); proto_unregister(&pppoe_sk_proto); } diff --git a/drivers/net/sk98lin/skge.c b/drivers/net/sk98lin/skge.c index 2e72d79a143..b18c92cb629 100644 --- a/drivers/net/sk98lin/skge.c +++ b/drivers/net/sk98lin/skge.c @@ -235,7 +235,7 @@ static int SkDrvDeInitAdapter(SK_AC *pAC, int devNbr); * Extern Function Prototypes * ******************************************************************************/ -static const char SKRootName[] = "sk98lin"; +static const char SKRootName[] = "net/sk98lin"; static struct proc_dir_entry *pSkRootDir; extern struct file_operations sk_proc_fops; @@ -5242,20 +5242,20 @@ static int __init skge_init(void) { int error; - pSkRootDir = proc_mkdir(SKRootName, proc_net); + pSkRootDir = proc_mkdir(SKRootName, NULL); if (pSkRootDir) pSkRootDir->owner = THIS_MODULE; error = pci_register_driver(&skge_driver); if (error) - proc_net_remove(SKRootName); + remove_proc_entry(SKRootName, NULL); return error; } static void __exit skge_exit(void) { pci_unregister_driver(&skge_driver); - proc_net_remove(SKRootName); + remove_proc_entry(SKRootName, NULL); } diff --git a/drivers/scsi/sg.c b/drivers/scsi/sg.c index 4d09a6e4dd2..ad94367df43 100644 --- a/drivers/scsi/sg.c +++ b/drivers/scsi/sg.c @@ -2849,8 +2849,7 @@ sg_proc_init(void) struct proc_dir_entry *pdep; struct sg_proc_leaf * leaf; - sg_proc_sgp = create_proc_entry(sg_proc_sg_dirname, - S_IFDIR | S_IRUGO | S_IXUGO, NULL); + sg_proc_sgp = proc_mkdir(sg_proc_sg_dirname, NULL); if (!sg_proc_sgp) return 1; for (k = 0; k < num_leaves; ++k) { diff --git a/drivers/usb/media/vicam.c b/drivers/usb/media/vicam.c index 4a5857c53f1..0bc0b1247a6 100644 --- a/drivers/usb/media/vicam.c +++ b/drivers/usb/media/vicam.c @@ -1148,7 +1148,7 @@ vicam_write_proc_gain(struct file *file, const char *buffer, static void vicam_create_proc_root(void) { - vicam_proc_root = create_proc_entry("video/vicam", S_IFDIR, 0); + vicam_proc_root = proc_mkdir("video/vicam", NULL); if (vicam_proc_root) vicam_proc_root->owner = THIS_MODULE; @@ -1181,7 +1181,7 @@ vicam_create_proc_entry(struct vicam_camera *cam) sprintf(name, "video%d", cam->vdev.minor); - cam->proc_dir = create_proc_entry(name, S_IFDIR, vicam_proc_root); + cam->proc_dir = proc_mkdir(name, vicam_proc_root); if ( !cam->proc_dir ) return; // FIXME: We should probably return an error here diff --git a/net/core/pktgen.c b/net/core/pktgen.c index ef430b1e8e4..b7f2d65a614 100644 --- a/net/core/pktgen.c +++ b/net/core/pktgen.c @@ -186,7 +186,7 @@ /* Used to help with determining the pkts on receive */ #define PKTGEN_MAGIC 0xbe9be955 -#define PG_PROC_DIR "pktgen" +#define PG_PROC_DIR "net/pktgen" #define MAX_CFLOWS 65536 @@ -1476,18 +1476,7 @@ static int proc_thread_write(struct file *file, const char __user *user_buffer, static int create_proc_dir(void) { - int len; - /* does proc_dir already exists */ - len = strlen(PG_PROC_DIR); - - for (pg_proc_dir = proc_net->subdir; pg_proc_dir; pg_proc_dir=pg_proc_dir->next) { - if ((pg_proc_dir->namelen == len) && - (! memcmp(pg_proc_dir->name, PG_PROC_DIR, len))) - break; - } - - if (!pg_proc_dir) - pg_proc_dir = create_proc_entry(PG_PROC_DIR, S_IFDIR, proc_net); + pg_proc_dir = proc_mkdir(PG_PROC_DIR, NULL); if (!pg_proc_dir) return -ENODEV; @@ -1497,7 +1486,7 @@ static int create_proc_dir(void) static int remove_proc_dir(void) { - remove_proc_entry(PG_PROC_DIR, proc_net); + remove_proc_entry(PG_PROC_DIR, NULL); return 0; } @@ -2908,7 +2897,7 @@ static int pktgen_add_device(struct pktgen_thread *t, const char* ifname) pkt_dev->udp_dst_max = 9; strncpy(pkt_dev->ifname, ifname, 31); - sprintf(pkt_dev->fname, "net/%s/%s", PG_PROC_DIR, ifname); + sprintf(pkt_dev->fname, "%s/%s", PG_PROC_DIR, ifname); if (! pktgen_setup_dev(pkt_dev)) { printk("pktgen: ERROR: pktgen_setup_dev failed.\n"); @@ -2981,7 +2970,7 @@ static int pktgen_create_thread(const char* name, int cpu) spin_lock_init(&t->if_lock); t->cpu = cpu; - sprintf(t->fname, "net/%s/%s", PG_PROC_DIR, t->name); + sprintf(t->fname, "%s/%s", PG_PROC_DIR, t->name); t->proc_ent = create_proc_entry(t->fname, 0600, NULL); if (!t->proc_ent) { printk("pktgen: cannot create %s procfs entry.\n", t->fname); @@ -3064,7 +3053,7 @@ static int __init pg_init(void) create_proc_dir(); - sprintf(module_fname, "net/%s/pgctrl", PG_PROC_DIR); + sprintf(module_fname, "%s/pgctrl", PG_PROC_DIR); module_proc_ent = create_proc_entry(module_fname, 0600, NULL); if (!module_proc_ent) { printk("pktgen: ERROR: cannot create %s procfs entry.\n", module_fname); diff --git a/net/ieee80211/ieee80211_module.c b/net/ieee80211/ieee80211_module.c index 03a47343ddc..6059e9e3712 100644 --- a/net/ieee80211/ieee80211_module.c +++ b/net/ieee80211/ieee80211_module.c @@ -230,7 +230,7 @@ static int __init ieee80211_init(void) struct proc_dir_entry *e; ieee80211_debug_level = debug; - ieee80211_proc = create_proc_entry(DRV_NAME, S_IFDIR, proc_net); + ieee80211_proc = proc_mkdir(DRV_NAME, proc_net); if (ieee80211_proc == NULL) { IEEE80211_ERROR("Unable to create " DRV_NAME " proc directory\n"); -- cgit v1.2.3 From 87e0f3dbd3693bc4583474ab191cbdd5e3d9d0fa Mon Sep 17 00:00:00 2001 From: Alexey Dobriyan Date: Thu, 29 Sep 2005 00:05:58 +0100 Subject: [PATCH] n_r3964: drop bogus fmt casts - print pointers with %p - casting pointer structure field to int and printing it with %d... Signed-off-by: Alexey Dobriyan Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- drivers/char/n_r3964.c | 84 +++++++++++++++++++++++++------------------------- 1 file changed, 42 insertions(+), 42 deletions(-) diff --git a/drivers/char/n_r3964.c b/drivers/char/n_r3964.c index 2291a87e8ad..97d6dc24b80 100644 --- a/drivers/char/n_r3964.c +++ b/drivers/char/n_r3964.c @@ -229,8 +229,8 @@ static int __init r3964_init(void) TRACE_L("line discipline %d registered", N_R3964); TRACE_L("flags=%x num=%x", tty_ldisc_N_R3964.flags, tty_ldisc_N_R3964.num); - TRACE_L("open=%x", (int)tty_ldisc_N_R3964.open); - TRACE_L("tty_ldisc_N_R3964 = %x", (int)&tty_ldisc_N_R3964); + TRACE_L("open=%p", tty_ldisc_N_R3964.open); + TRACE_L("tty_ldisc_N_R3964 = %p", &tty_ldisc_N_R3964); } else { @@ -267,8 +267,8 @@ static void add_tx_queue(struct r3964_info *pInfo, struct r3964_block_header *pH spin_unlock_irqrestore(&pInfo->lock, flags); - TRACE_Q("add_tx_queue %x, length %d, tx_first = %x", - (int)pHeader, pHeader->length, (int)pInfo->tx_first ); + TRACE_Q("add_tx_queue %p, length %d, tx_first = %p", + pHeader, pHeader->length, pInfo->tx_first ); } static void remove_from_tx_queue(struct r3964_info *pInfo, int error_code) @@ -285,10 +285,10 @@ static void remove_from_tx_queue(struct r3964_info *pInfo, int error_code) return; #ifdef DEBUG_QUEUE - printk("r3964: remove_from_tx_queue: %x, length %d - ", - (int)pHeader, (int)pHeader->length ); + printk("r3964: remove_from_tx_queue: %p, length %u - ", + pHeader, pHeader->length ); for(pDump=pHeader;pDump;pDump=pDump->next) - printk("%x ", (int)pDump); + printk("%p ", pDump); printk("\n"); #endif @@ -319,10 +319,10 @@ static void remove_from_tx_queue(struct r3964_info *pInfo, int error_code) spin_unlock_irqrestore(&pInfo->lock, flags); kfree(pHeader); - TRACE_M("remove_from_tx_queue - kfree %x",(int)pHeader); + TRACE_M("remove_from_tx_queue - kfree %p",pHeader); - TRACE_Q("remove_from_tx_queue: tx_first = %x, tx_last = %x", - (int)pInfo->tx_first, (int)pInfo->tx_last ); + TRACE_Q("remove_from_tx_queue: tx_first = %p, tx_last = %p", + pInfo->tx_first, pInfo->tx_last ); } static void add_rx_queue(struct r3964_info *pInfo, struct r3964_block_header *pHeader) @@ -346,9 +346,9 @@ static void add_rx_queue(struct r3964_info *pInfo, struct r3964_block_header *pH spin_unlock_irqrestore(&pInfo->lock, flags); - TRACE_Q("add_rx_queue: %x, length = %d, rx_first = %x, count = %d", - (int)pHeader, pHeader->length, - (int)pInfo->rx_first, pInfo->blocks_in_rx_queue); + TRACE_Q("add_rx_queue: %p, length = %d, rx_first = %p, count = %d", + pHeader, pHeader->length, + pInfo->rx_first, pInfo->blocks_in_rx_queue); } static void remove_from_rx_queue(struct r3964_info *pInfo, @@ -360,10 +360,10 @@ static void remove_from_rx_queue(struct r3964_info *pInfo, if(pHeader==NULL) return; - TRACE_Q("remove_from_rx_queue: rx_first = %x, rx_last = %x, count = %d", - (int)pInfo->rx_first, (int)pInfo->rx_last, pInfo->blocks_in_rx_queue ); - TRACE_Q("remove_from_rx_queue: %x, length %d", - (int)pHeader, (int)pHeader->length ); + TRACE_Q("remove_from_rx_queue: rx_first = %p, rx_last = %p, count = %d", + pInfo->rx_first, pInfo->rx_last, pInfo->blocks_in_rx_queue ); + TRACE_Q("remove_from_rx_queue: %p, length %u", + pHeader, pHeader->length ); spin_lock_irqsave(&pInfo->lock, flags); @@ -401,10 +401,10 @@ static void remove_from_rx_queue(struct r3964_info *pInfo, spin_unlock_irqrestore(&pInfo->lock, flags); kfree(pHeader); - TRACE_M("remove_from_rx_queue - kfree %x",(int)pHeader); + TRACE_M("remove_from_rx_queue - kfree %p",pHeader); - TRACE_Q("remove_from_rx_queue: rx_first = %x, rx_last = %x, count = %d", - (int)pInfo->rx_first, (int)pInfo->rx_last, pInfo->blocks_in_rx_queue ); + TRACE_Q("remove_from_rx_queue: rx_first = %p, rx_last = %p, count = %d", + pInfo->rx_first, pInfo->rx_last, pInfo->blocks_in_rx_queue ); } static void put_char(struct r3964_info *pInfo, unsigned char ch) @@ -506,8 +506,8 @@ static void transmit_block(struct r3964_info *pInfo) if(tty->driver->write_room) room=tty->driver->write_room(tty); - TRACE_PS("transmit_block %x, room %d, length %d", - (int)pBlock, room, pBlock->length); + TRACE_PS("transmit_block %p, room %d, length %d", + pBlock, room, pBlock->length); while(pInfo->tx_position < pBlock->length) { @@ -588,7 +588,7 @@ static void on_receive_block(struct r3964_info *pInfo) /* prepare struct r3964_block_header: */ pBlock = kmalloc(length+sizeof(struct r3964_block_header), GFP_KERNEL); - TRACE_M("on_receive_block - kmalloc %x",(int)pBlock); + TRACE_M("on_receive_block - kmalloc %p",pBlock); if(pBlock==NULL) return; @@ -868,11 +868,11 @@ static int enable_signals(struct r3964_info *pInfo, pid_t pid, int arg) if(pMsg) { kfree(pMsg); - TRACE_M("enable_signals - msg kfree %x",(int)pMsg); + TRACE_M("enable_signals - msg kfree %p",pMsg); } } kfree(pClient); - TRACE_M("enable_signals - kfree %x",(int)pClient); + TRACE_M("enable_signals - kfree %p",pClient); return 0; } } @@ -890,7 +890,7 @@ static int enable_signals(struct r3964_info *pInfo, pid_t pid, int arg) { /* add client to client list */ pClient=kmalloc(sizeof(struct r3964_client_info), GFP_KERNEL); - TRACE_M("enable_signals - kmalloc %x",(int)pClient); + TRACE_M("enable_signals - kmalloc %p",pClient); if(pClient==NULL) return -ENOMEM; @@ -954,7 +954,7 @@ static void add_msg(struct r3964_client_info *pClient, int msg_id, int arg, queue_the_message: pMsg = kmalloc(sizeof(struct r3964_message), GFP_KERNEL); - TRACE_M("add_msg - kmalloc %x",(int)pMsg); + TRACE_M("add_msg - kmalloc %p",pMsg); if(pMsg==NULL) { return; } @@ -1067,11 +1067,11 @@ static int r3964_open(struct tty_struct *tty) struct r3964_info *pInfo; TRACE_L("open"); - TRACE_L("tty=%x, PID=%d, disc_data=%x", - (int)tty, current->pid, (int)tty->disc_data); + TRACE_L("tty=%p, PID=%d, disc_data=%p", + tty, current->pid, tty->disc_data); pInfo=kmalloc(sizeof(struct r3964_info), GFP_KERNEL); - TRACE_M("r3964_open - info kmalloc %x",(int)pInfo); + TRACE_M("r3964_open - info kmalloc %p",pInfo); if(!pInfo) { @@ -1080,26 +1080,26 @@ static int r3964_open(struct tty_struct *tty) } pInfo->rx_buf = kmalloc(RX_BUF_SIZE, GFP_KERNEL); - TRACE_M("r3964_open - rx_buf kmalloc %x",(int)pInfo->rx_buf); + TRACE_M("r3964_open - rx_buf kmalloc %p",pInfo->rx_buf); if(!pInfo->rx_buf) { printk(KERN_ERR "r3964: failed to alloc receive buffer\n"); kfree(pInfo); - TRACE_M("r3964_open - info kfree %x",(int)pInfo); + TRACE_M("r3964_open - info kfree %p",pInfo); return -ENOMEM; } pInfo->tx_buf = kmalloc(TX_BUF_SIZE, GFP_KERNEL); - TRACE_M("r3964_open - tx_buf kmalloc %x",(int)pInfo->tx_buf); + TRACE_M("r3964_open - tx_buf kmalloc %p",pInfo->tx_buf); if(!pInfo->tx_buf) { printk(KERN_ERR "r3964: failed to alloc transmit buffer\n"); kfree(pInfo->rx_buf); - TRACE_M("r3964_open - rx_buf kfree %x",(int)pInfo->rx_buf); + TRACE_M("r3964_open - rx_buf kfree %p",pInfo->rx_buf); kfree(pInfo); - TRACE_M("r3964_open - info kfree %x",(int)pInfo); + TRACE_M("r3964_open - info kfree %p",pInfo); return -ENOMEM; } @@ -1154,11 +1154,11 @@ static void r3964_close(struct tty_struct *tty) if(pMsg) { kfree(pMsg); - TRACE_M("r3964_close - msg kfree %x",(int)pMsg); + TRACE_M("r3964_close - msg kfree %p",pMsg); } } kfree(pClient); - TRACE_M("r3964_close - client kfree %x",(int)pClient); + TRACE_M("r3964_close - client kfree %p",pClient); pClient=pNext; } /* Remove jobs from tx_queue: */ @@ -1177,11 +1177,11 @@ static void r3964_close(struct tty_struct *tty) /* Free buffers: */ wake_up_interruptible(&pInfo->read_wait); kfree(pInfo->rx_buf); - TRACE_M("r3964_close - rx_buf kfree %x",(int)pInfo->rx_buf); + TRACE_M("r3964_close - rx_buf kfree %p",pInfo->rx_buf); kfree(pInfo->tx_buf); - TRACE_M("r3964_close - tx_buf kfree %x",(int)pInfo->tx_buf); + TRACE_M("r3964_close - tx_buf kfree %p",pInfo->tx_buf); kfree(pInfo); - TRACE_M("r3964_close - info kfree %x",(int)pInfo); + TRACE_M("r3964_close - info kfree %p",pInfo); } static ssize_t r3964_read(struct tty_struct *tty, struct file *file, @@ -1234,7 +1234,7 @@ repeat: count = sizeof(struct r3964_client_message); kfree(pMsg); - TRACE_M("r3964_read - msg kfree %x",(int)pMsg); + TRACE_M("r3964_read - msg kfree %p",pMsg); if (copy_to_user(buf,&theMsg, count)) return -EFAULT; @@ -1279,7 +1279,7 @@ static ssize_t r3964_write(struct tty_struct * tty, struct file * file, * Allocate a buffer for the data and copy it from the buffer with header prepended */ new_data = kmalloc (count+sizeof(struct r3964_block_header), GFP_KERNEL); - TRACE_M("r3964_write - kmalloc %x",(int)new_data); + TRACE_M("r3964_write - kmalloc %p",new_data); if (new_data == NULL) { if (pInfo->flags & R3964_DEBUG) { -- cgit v1.2.3 From 775b048d09c85d87a65a7ccd9c4f9372953a5d95 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Thu, 29 Sep 2005 00:07:29 +0100 Subject: [PATCH] cyblafb: portability fixes, sanitized work with pointers Signed-off-by: Al Viro Acked-by: Knut Petersen Signed-off-by: Linus Torvalds --- drivers/video/cyblafb.c | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/drivers/video/cyblafb.c b/drivers/video/cyblafb.c index ae2762cb560..6992100a508 100644 --- a/drivers/video/cyblafb.c +++ b/drivers/video/cyblafb.c @@ -410,20 +410,21 @@ static void cyblafb_imageblit(struct fb_info *info, out32(GE0C,point(image->dx+image->width-1,image->dy+image->height-1)); while(index < index_end) { + const char *p = image->data + index; for(i=0;idata + index))); + out32(GE9C,*(u32*)p); + p+=4; index+=4; } switch(width_dbs) { case 0: break; - case 8: out32(GE9C,*((u8*)((u32)image->data+index))); + case 8: out32(GE9C,*(u8*)p); index+=1; break; - case 16: out32(GE9C,*((u16*)((u32)image->data+index))); + case 16: out32(GE9C,*(u16*)p); index+=2; break; - case 24: out32(GE9C,(u32)(*((u16*)((u32)image->data+index))) | - (u32)(*((u8*)((u32)image->data+index+2)))<<16); + case 24: out32(GE9C,*(u16*)p | *(u8*)(p+2)<<16); index+=3; break; } -- cgit v1.2.3 From 2ad4f86b60b649fd7428265c08d73a3bd360c81b Mon Sep 17 00:00:00 2001 From: Al Viro Date: Thu, 29 Sep 2005 00:09:02 +0100 Subject: [PATCH] arm/versatile iomem annotations Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- arch/arm/mach-versatile/core.c | 43 +++++++++++++++++++------------------ include/asm-arm/arch-versatile/io.h | 6 +++++- 2 files changed, 27 insertions(+), 22 deletions(-) diff --git a/arch/arm/mach-versatile/core.c b/arch/arm/mach-versatile/core.c index 3c8862fde51..58c1330d863 100644 --- a/arch/arm/mach-versatile/core.c +++ b/arch/arm/mach-versatile/core.c @@ -52,8 +52,9 @@ * * Setup a VA for the Versatile Vectored Interrupt Controller. */ -#define VA_VIC_BASE IO_ADDRESS(VERSATILE_VIC_BASE) -#define VA_SIC_BASE IO_ADDRESS(VERSATILE_SIC_BASE) +#define __io_address(n) __io(IO_ADDRESS(n)) +#define VA_VIC_BASE __io_address(VERSATILE_VIC_BASE) +#define VA_SIC_BASE __io_address(VERSATILE_SIC_BASE) static void vic_mask_irq(unsigned int irq) { @@ -214,7 +215,7 @@ void __init versatile_map_io(void) iotable_init(versatile_io_desc, ARRAY_SIZE(versatile_io_desc)); } -#define VERSATILE_REFCOUNTER (IO_ADDRESS(VERSATILE_SYS_BASE) + VERSATILE_SYS_24MHz_OFFSET) +#define VERSATILE_REFCOUNTER (__io_address(VERSATILE_SYS_BASE) + VERSATILE_SYS_24MHz_OFFSET) /* * This is the Versatile sched_clock implementation. This has @@ -231,7 +232,7 @@ unsigned long long sched_clock(void) } -#define VERSATILE_FLASHCTRL (IO_ADDRESS(VERSATILE_SYS_BASE) + VERSATILE_SYS_FLASH_OFFSET) +#define VERSATILE_FLASHCTRL (__io_address(VERSATILE_SYS_BASE) + VERSATILE_SYS_FLASH_OFFSET) static int versatile_flash_init(void) { @@ -309,7 +310,7 @@ static struct platform_device smc91x_device = { .resource = smc91x_resources, }; -#define VERSATILE_SYSMCI (IO_ADDRESS(VERSATILE_SYS_BASE) + VERSATILE_SYS_MCI_OFFSET) +#define VERSATILE_SYSMCI (__io_address(VERSATILE_SYS_BASE) + VERSATILE_SYS_MCI_OFFSET) unsigned int mmc_status(struct device *dev) { @@ -343,11 +344,11 @@ static const struct icst307_params versatile_oscvco_params = { static void versatile_oscvco_set(struct clk *clk, struct icst307_vco vco) { - unsigned long sys_lock = IO_ADDRESS(VERSATILE_SYS_BASE) + VERSATILE_SYS_LOCK_OFFSET; + void __iomem *sys_lock = __io_address(VERSATILE_SYS_BASE) + VERSATILE_SYS_LOCK_OFFSET; #if defined(CONFIG_ARCH_VERSATILE_PB) - unsigned long sys_osc = IO_ADDRESS(VERSATILE_SYS_BASE) + VERSATILE_SYS_OSC4_OFFSET; + void __iomem *sys_osc = __io_address(VERSATILE_SYS_BASE) + VERSATILE_SYS_OSC4_OFFSET; #elif defined(CONFIG_MACH_VERSATILE_AB) - unsigned long sys_osc = IO_ADDRESS(VERSATILE_SYS_BASE) + VERSATILE_SYS_OSC1_OFFSET; + void __iomem *sys_osc = __io_address(VERSATILE_SYS_BASE) + VERSATILE_SYS_OSC1_OFFSET; #endif u32 val; @@ -483,7 +484,7 @@ static struct clcd_panel epson_2_2_in = { */ static struct clcd_panel *versatile_clcd_panel(void) { - unsigned long sys_clcd = IO_ADDRESS(VERSATILE_SYS_BASE) + VERSATILE_SYS_CLCD_OFFSET; + void __iomem *sys_clcd = __io_address(VERSATILE_SYS_BASE) + VERSATILE_SYS_CLCD_OFFSET; struct clcd_panel *panel = &vga; u32 val; @@ -510,7 +511,7 @@ static struct clcd_panel *versatile_clcd_panel(void) */ static void versatile_clcd_disable(struct clcd_fb *fb) { - unsigned long sys_clcd = IO_ADDRESS(VERSATILE_SYS_BASE) + VERSATILE_SYS_CLCD_OFFSET; + void __iomem *sys_clcd = __io_address(VERSATILE_SYS_BASE) + VERSATILE_SYS_CLCD_OFFSET; u32 val; val = readl(sys_clcd); @@ -522,7 +523,7 @@ static void versatile_clcd_disable(struct clcd_fb *fb) * If the LCD is Sanyo 2x5 in on the IB2 board, turn the back-light off */ if (fb->panel == &sanyo_2_5_in) { - unsigned long versatile_ib2_ctrl = IO_ADDRESS(VERSATILE_IB2_CTRL); + void __iomem *versatile_ib2_ctrl = __io_address(VERSATILE_IB2_CTRL); unsigned long ctrl; ctrl = readl(versatile_ib2_ctrl); @@ -537,7 +538,7 @@ static void versatile_clcd_disable(struct clcd_fb *fb) */ static void versatile_clcd_enable(struct clcd_fb *fb) { - unsigned long sys_clcd = IO_ADDRESS(VERSATILE_SYS_BASE) + VERSATILE_SYS_CLCD_OFFSET; + void __iomem *sys_clcd = __io_address(VERSATILE_SYS_BASE) + VERSATILE_SYS_CLCD_OFFSET; u32 val; val = readl(sys_clcd); @@ -571,7 +572,7 @@ static void versatile_clcd_enable(struct clcd_fb *fb) * If the LCD is Sanyo 2x5 in on the IB2 board, turn the back-light on */ if (fb->panel == &sanyo_2_5_in) { - unsigned long versatile_ib2_ctrl = IO_ADDRESS(VERSATILE_IB2_CTRL); + void __iomem *versatile_ib2_ctrl = __io_address(VERSATILE_IB2_CTRL); unsigned long ctrl; ctrl = readl(versatile_ib2_ctrl); @@ -720,7 +721,7 @@ static struct amba_device *amba_devs[] __initdata = { }; #ifdef CONFIG_LEDS -#define VA_LEDS_BASE (IO_ADDRESS(VERSATILE_SYS_BASE) + VERSATILE_SYS_LED_OFFSET) +#define VA_LEDS_BASE (__io_address(VERSATILE_SYS_BASE) + VERSATILE_SYS_LED_OFFSET) static void versatile_leds_event(led_event_t ledevt) { @@ -778,11 +779,11 @@ void __init versatile_init(void) /* * Where is the timer (VA)? */ -#define TIMER0_VA_BASE IO_ADDRESS(VERSATILE_TIMER0_1_BASE) -#define TIMER1_VA_BASE (IO_ADDRESS(VERSATILE_TIMER0_1_BASE) + 0x20) -#define TIMER2_VA_BASE IO_ADDRESS(VERSATILE_TIMER2_3_BASE) -#define TIMER3_VA_BASE (IO_ADDRESS(VERSATILE_TIMER2_3_BASE) + 0x20) -#define VA_IC_BASE IO_ADDRESS(VERSATILE_VIC_BASE) +#define TIMER0_VA_BASE __io_address(VERSATILE_TIMER0_1_BASE) +#define TIMER1_VA_BASE (__io_address(VERSATILE_TIMER0_1_BASE) + 0x20) +#define TIMER2_VA_BASE __io_address(VERSATILE_TIMER2_3_BASE) +#define TIMER3_VA_BASE (__io_address(VERSATILE_TIMER2_3_BASE) + 0x20) +#define VA_IC_BASE __io_address(VERSATILE_VIC_BASE) /* * How long is the timer interval? @@ -877,12 +878,12 @@ static void __init versatile_timer_init(void) * VERSATILE_REFCLK is 32KHz * VERSATILE_TIMCLK is 1MHz */ - val = readl(IO_ADDRESS(VERSATILE_SCTL_BASE)); + val = readl(__io_address(VERSATILE_SCTL_BASE)); writel((VERSATILE_TIMCLK << VERSATILE_TIMER1_EnSel) | (VERSATILE_TIMCLK << VERSATILE_TIMER2_EnSel) | (VERSATILE_TIMCLK << VERSATILE_TIMER3_EnSel) | (VERSATILE_TIMCLK << VERSATILE_TIMER4_EnSel) | val, - IO_ADDRESS(VERSATILE_SCTL_BASE)); + __io_address(VERSATILE_SCTL_BASE)); /* * Initialise to a known state (all timers off) diff --git a/include/asm-arm/arch-versatile/io.h b/include/asm-arm/arch-versatile/io.h index 9f895bf6149..47e904cf25c 100644 --- a/include/asm-arm/arch-versatile/io.h +++ b/include/asm-arm/arch-versatile/io.h @@ -22,7 +22,11 @@ #define IO_SPACE_LIMIT 0xffffffff -#define __io(a) ((void __iomem *)(a)) +static inline void __iomem *__io(unsigned long addr) +{ + return (void __iomem *)addr; +} +#define __io(a) __io(a) #define __mem_pci(a) (a) #define __mem_isa(a) (a) -- cgit v1.2.3 From 272cd2b71d478371e0a5bf2c76a1e50cbf178698 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Thu, 29 Sep 2005 00:10:01 +0100 Subject: [PATCH] arm/rpc iomem annotations Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- include/asm-arm/arch-rpc/hardware.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/include/asm-arm/arch-rpc/hardware.h b/include/asm-arm/arch-rpc/hardware.h index be9754a05c1..9d7f87375aa 100644 --- a/include/asm-arm/arch-rpc/hardware.h +++ b/include/asm-arm/arch-rpc/hardware.h @@ -15,7 +15,7 @@ #include #ifndef __ASSEMBLY__ -#define IOMEM(x) ((void __iomem *)(x)) +#define IOMEM(x) ((void __iomem *)(unsigned long)(x)) #else #define IOMEM(x) x #endif /* __ASSEMBLY__ */ @@ -52,7 +52,7 @@ /* * IO Addresses */ -#define VIDC_BASE (void __iomem *)0xe0400000 +#define VIDC_BASE IOMEM(0xe0400000) #define EXPMASK_BASE 0xe0360000 #define IOMD_BASE IOMEM(0xe0200000) #define IOC_BASE IOMEM(0xe0200000) -- cgit v1.2.3 From 0cc13a5442901835192ba47427f0f4e4d525d935 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Thu, 29 Sep 2005 00:12:13 +0100 Subject: [PATCH] ia64 basic __user annotations - document places where we pass kernel address to low-level primitive that deals with kernel/user addresses - uintptr_t is unsigned long, not long Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- include/asm-ia64/uaccess.h | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/include/asm-ia64/uaccess.h b/include/asm-ia64/uaccess.h index 3a7829bb595..9adb51211c2 100644 --- a/include/asm-ia64/uaccess.h +++ b/include/asm-ia64/uaccess.h @@ -187,8 +187,8 @@ extern void __get_user_unknown (void); ({ \ const __typeof__(*(ptr)) __user *__gu_ptr = (ptr); \ __typeof__ (size) __gu_size = (size); \ - long __gu_err = -EFAULT, __gu_val = 0; \ - \ + long __gu_err = -EFAULT; \ + unsigned long __gu_val = 0; \ if (!check || __access_ok(__gu_ptr, size, segment)) \ switch (__gu_size) { \ case 1: __get_user_size(__gu_val, __gu_ptr, 1, __gu_err); break; \ @@ -240,13 +240,13 @@ extern unsigned long __must_check __copy_user (void __user *to, const void __use static inline unsigned long __copy_to_user (void __user *to, const void *from, unsigned long count) { - return __copy_user(to, (void __user *) from, count); + return __copy_user(to, (__force void __user *) from, count); } static inline unsigned long __copy_from_user (void *to, const void __user *from, unsigned long count) { - return __copy_user((void __user *) to, from, count); + return __copy_user((__force void __user *) to, from, count); } #define __copy_to_user_inatomic __copy_to_user @@ -258,7 +258,7 @@ __copy_from_user (void *to, const void __user *from, unsigned long count) long __cu_len = (n); \ \ if (__access_ok(__cu_to, __cu_len, get_fs())) \ - __cu_len = __copy_user(__cu_to, (void __user *) __cu_from, __cu_len); \ + __cu_len = __copy_user(__cu_to, (__force void __user *) __cu_from, __cu_len); \ __cu_len; \ }) @@ -270,7 +270,7 @@ __copy_from_user (void *to, const void __user *from, unsigned long count) \ __chk_user_ptr(__cu_from); \ if (__access_ok(__cu_from, __cu_len, get_fs())) \ - __cu_len = __copy_user((void __user *) __cu_to, __cu_from, __cu_len); \ + __cu_len = __copy_user((__force void __user *) __cu_to, __cu_from, __cu_len); \ __cu_len; \ }) -- cgit v1.2.3 From c28144763a7dcdceb2c16a5ac9c8e0022d547d28 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Thu, 29 Sep 2005 00:16:02 +0100 Subject: [PATCH] s390 signal annotations Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- arch/s390/kernel/compat_signal.c | 6 +++--- arch/s390/kernel/signal.c | 4 ++-- include/asm-s390/sigcontext.h | 2 +- include/asm-s390/signal.h | 2 +- 4 files changed, 7 insertions(+), 7 deletions(-) diff --git a/arch/s390/kernel/compat_signal.c b/arch/s390/kernel/compat_signal.c index 7358cdb8441..4ff6808456e 100644 --- a/arch/s390/kernel/compat_signal.c +++ b/arch/s390/kernel/compat_signal.c @@ -143,7 +143,7 @@ int copy_siginfo_from_user32(siginfo_t *to, compat_siginfo_t __user *from) break; case __SI_FAULT >> 16: err |= __get_user(tmp, &from->si_addr); - to->si_addr = (void *)(u64) (tmp & PSW32_ADDR_INSN); + to->si_addr = (void __user *)(u64) (tmp & PSW32_ADDR_INSN); break; case __SI_POLL >> 16: err |= __get_user(to->si_band, &from->si_band); @@ -338,7 +338,7 @@ sys32_sigaltstack(const stack_t32 __user *uss, stack_t32 __user *uoss, err |= __get_user(kss.ss_flags, &uss->ss_flags); if (err) return -EFAULT; - kss.ss_sp = (void *) ss_sp; + kss.ss_sp = (void __user *) ss_sp; } set_fs (KERNEL_DS); @@ -461,7 +461,7 @@ asmlinkage long sys32_rt_sigreturn(struct pt_regs *regs) goto badframe; err = __get_user(ss_sp, &frame->uc.uc_stack.ss_sp); - st.ss_sp = (void *) A((unsigned long)ss_sp); + st.ss_sp = compat_ptr(ss_sp); err |= __get_user(st.ss_size, &frame->uc.uc_stack.ss_size); err |= __get_user(st.ss_flags, &frame->uc.uc_stack.ss_flags); if (err) diff --git a/arch/s390/kernel/signal.c b/arch/s390/kernel/signal.c index 6a3f5b7473a..6e0110d7119 100644 --- a/arch/s390/kernel/signal.c +++ b/arch/s390/kernel/signal.c @@ -376,8 +376,8 @@ static void setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info, /* Create the ucontext. */ err |= __put_user(0, &frame->uc.uc_flags); - err |= __put_user(0, &frame->uc.uc_link); - err |= __put_user((void *)current->sas_ss_sp, &frame->uc.uc_stack.ss_sp); + err |= __put_user(NULL, &frame->uc.uc_link); + err |= __put_user((void __user *)current->sas_ss_sp, &frame->uc.uc_stack.ss_sp); err |= __put_user(sas_ss_flags(regs->gprs[15]), &frame->uc.uc_stack.ss_flags); err |= __put_user(current->sas_ss_size, &frame->uc.uc_stack.ss_size); diff --git a/include/asm-s390/sigcontext.h b/include/asm-s390/sigcontext.h index d57bc0cebdc..803545351dd 100644 --- a/include/asm-s390/sigcontext.h +++ b/include/asm-s390/sigcontext.h @@ -61,7 +61,7 @@ typedef struct struct sigcontext { unsigned long oldmask[_SIGCONTEXT_NSIG_WORDS]; - _sigregs *sregs; + _sigregs __user *sregs; }; diff --git a/include/asm-s390/signal.h b/include/asm-s390/signal.h index 3d6e11c6c1f..7084626de21 100644 --- a/include/asm-s390/signal.h +++ b/include/asm-s390/signal.h @@ -165,7 +165,7 @@ struct sigaction { #endif /* __KERNEL__ */ typedef struct sigaltstack { - void *ss_sp; + void __user *ss_sp; int ss_flags; size_t ss_size; } stack_t; -- cgit v1.2.3 From ea8a918eb71b503be13b861dbe18b93932fd6b62 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Thu, 29 Sep 2005 00:17:49 +0100 Subject: [PATCH] ppc64 get_user annotations long is not uintptr_t, unsigned long is. Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- include/asm-ppc64/uaccess.h | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/include/asm-ppc64/uaccess.h b/include/asm-ppc64/uaccess.h index c181a60d868..132c1276547 100644 --- a/include/asm-ppc64/uaccess.h +++ b/include/asm-ppc64/uaccess.h @@ -164,7 +164,8 @@ do { \ #define __get_user_nocheck(x,ptr,size) \ ({ \ - long __gu_err, __gu_val; \ + long __gu_err; \ + unsigned long __gu_val; \ might_sleep(); \ __get_user_size(__gu_val,(ptr),(size),__gu_err,-EFAULT);\ (x) = (__typeof__(*(ptr)))__gu_val; \ @@ -173,7 +174,8 @@ do { \ #define __get_user_check(x,ptr,size) \ ({ \ - long __gu_err = -EFAULT, __gu_val = 0; \ + long __gu_err = -EFAULT; \ + unsigned long __gu_val = 0; \ const __typeof__(*(ptr)) __user *__gu_addr = (ptr); \ might_sleep(); \ if (access_ok(VERIFY_READ,__gu_addr,size)) \ -- cgit v1.2.3 From 9fcdfcd90526c8c5c2bd117fd3713f8f0f1a46a8 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Thu, 29 Sep 2005 00:31:14 +0100 Subject: [PATCH] ppc32 ld.script fix for building on ppc64 In arch/ppc/boot/ld.script we need OUTPUT_ARCH(powerpc:common) for the same reasons why we need it in vmlinux.lds.S; when we build on ppc64 box, we need to be explicit about the target. See http://linus.bkbits.net:8080/linux-2.5/cset@1.1784.8.10 for the corresponding fix in vmlinux.lds.S. Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- arch/ppc/boot/ld.script | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/ppc/boot/ld.script b/arch/ppc/boot/ld.script index 9362193742a..d4dd8f15395 100644 --- a/arch/ppc/boot/ld.script +++ b/arch/ppc/boot/ld.script @@ -1,4 +1,4 @@ -OUTPUT_ARCH(powerpc) +OUTPUT_ARCH(powerpc:common) SECTIONS { /* Read-only sections, merged into text segment: */ -- cgit v1.2.3 From a7625d6e49cb4fd94be7576d85422c33003101b7 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Thu, 29 Sep 2005 00:34:30 +0100 Subject: [PATCH] mv64x60 iomem annotations Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- arch/ppc/syslib/mv64x60.c | 4 ++-- include/asm-ppc/mv64x60.h | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/arch/ppc/syslib/mv64x60.c b/arch/ppc/syslib/mv64x60.c index 839f8872826..4849850a59e 100644 --- a/arch/ppc/syslib/mv64x60.c +++ b/arch/ppc/syslib/mv64x60.c @@ -34,7 +34,7 @@ u8 mv64x60_pci_exclude_bridge = 1; DEFINE_SPINLOCK(mv64x60_lock); static phys_addr_t mv64x60_bridge_pbase; -static void *mv64x60_bridge_vbase; +static void __iomem *mv64x60_bridge_vbase; static u32 mv64x60_bridge_type = MV64x60_TYPE_INVALID; static u32 mv64x60_bridge_rev; #if defined(CONFIG_SYSFS) && !defined(CONFIG_GT64260) @@ -938,7 +938,7 @@ mv64x60_setup_for_chip(struct mv64x60_handle *bh) * * Return the virtual address of the bridge's registers. */ -void * +void __iomem * mv64x60_get_bridge_vbase(void) { return mv64x60_bridge_vbase; diff --git a/include/asm-ppc/mv64x60.h b/include/asm-ppc/mv64x60.h index 75c2ffa26b2..ee2f9188cc6 100644 --- a/include/asm-ppc/mv64x60.h +++ b/include/asm-ppc/mv64x60.h @@ -233,7 +233,7 @@ struct mv64x60_chip_info { struct mv64x60_handle { u32 type; /* type of bridge */ u32 rev; /* revision of bridge */ - void *v_base; /* virtual base addr of bridge regs */ + void __iomem *v_base;/* virtual base addr of bridge regs */ phys_addr_t p_base; /* physical base addr of bridge regs */ u32 pci_mode_a; /* pci 0 mode: conventional pci, pci-x*/ @@ -303,7 +303,7 @@ void mv64x60_alloc_hose(struct mv64x60_handle *bh, u32 cfg_addr, u32 cfg_data, struct pci_controller **hose); int mv64x60_get_type(struct mv64x60_handle *bh); int mv64x60_setup_for_chip(struct mv64x60_handle *bh); -void *mv64x60_get_bridge_vbase(void); +void __iomem *mv64x60_get_bridge_vbase(void); u32 mv64x60_get_bridge_type(void); u32 mv64x60_get_bridge_rev(void); void mv64x60_get_mem_windows(struct mv64x60_handle *bh, -- cgit v1.2.3 From be88ec74cb48d1f60d0c0f059843f846f4481d87 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Thu, 29 Sep 2005 00:36:10 +0100 Subject: [PATCH] i810-i2c iomem annotations Signed-off-by: Al Viro Acked-by: Antonino Daplas Signed-off-by: Linus Torvalds --- drivers/video/i810/i810-i2c.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/video/i810/i810-i2c.c b/drivers/video/i810/i810-i2c.c index fda53aac1fc..689d2586366 100644 --- a/drivers/video/i810/i810-i2c.c +++ b/drivers/video/i810/i810-i2c.c @@ -44,7 +44,7 @@ static void i810i2c_setscl(void *data, int state) { struct i810fb_i2c_chan *chan = (struct i810fb_i2c_chan *)data; struct i810fb_par *par = chan->par; - u8 *mmio = par->mmio_start_virtual; + u8 __iomem *mmio = par->mmio_start_virtual; i810_writel(mmio, GPIOB, (state ? SCL_VAL_OUT : 0) | SCL_DIR | SCL_DIR_MASK | SCL_VAL_MASK); @@ -55,7 +55,7 @@ static void i810i2c_setsda(void *data, int state) { struct i810fb_i2c_chan *chan = (struct i810fb_i2c_chan *)data; struct i810fb_par *par = chan->par; - u8 *mmio = par->mmio_start_virtual; + u8 __iomem *mmio = par->mmio_start_virtual; i810_writel(mmio, GPIOB, (state ? SDA_VAL_OUT : 0) | SDA_DIR | SDA_DIR_MASK | SDA_VAL_MASK); @@ -66,7 +66,7 @@ static int i810i2c_getscl(void *data) { struct i810fb_i2c_chan *chan = (struct i810fb_i2c_chan *)data; struct i810fb_par *par = chan->par; - u8 *mmio = par->mmio_start_virtual; + u8 __iomem *mmio = par->mmio_start_virtual; i810_writel(mmio, GPIOB, SCL_DIR_MASK); i810_writel(mmio, GPIOB, 0); @@ -77,7 +77,7 @@ static int i810i2c_getsda(void *data) { struct i810fb_i2c_chan *chan = (struct i810fb_i2c_chan *)data; struct i810fb_par *par = chan->par; - u8 *mmio = par->mmio_start_virtual; + u8 __iomem *mmio = par->mmio_start_virtual; i810_writel(mmio, GPIOB, SDA_DIR_MASK); i810_writel(mmio, GPIOB, 0); @@ -88,7 +88,7 @@ static void i810ddc_setscl(void *data, int state) { struct i810fb_i2c_chan *chan = (struct i810fb_i2c_chan *)data; struct i810fb_par *par = chan->par; - u8 *mmio = par->mmio_start_virtual; + u8 __iomem *mmio = par->mmio_start_virtual; i810_writel(mmio, GPIOA, (state ? SCL_VAL_OUT : 0) | SCL_DIR | SCL_DIR_MASK | SCL_VAL_MASK); @@ -99,7 +99,7 @@ static void i810ddc_setsda(void *data, int state) { struct i810fb_i2c_chan *chan = (struct i810fb_i2c_chan *)data; struct i810fb_par *par = chan->par; - u8 *mmio = par->mmio_start_virtual; + u8 __iomem *mmio = par->mmio_start_virtual; i810_writel(mmio, GPIOA, (state ? SDA_VAL_OUT : 0) | SDA_DIR | SDA_DIR_MASK | SDA_VAL_MASK); @@ -110,7 +110,7 @@ static int i810ddc_getscl(void *data) { struct i810fb_i2c_chan *chan = (struct i810fb_i2c_chan *)data; struct i810fb_par *par = chan->par; - u8 *mmio = par->mmio_start_virtual; + u8 __iomem *mmio = par->mmio_start_virtual; i810_writel(mmio, GPIOA, SCL_DIR_MASK); i810_writel(mmio, GPIOA, 0); @@ -121,7 +121,7 @@ static int i810ddc_getsda(void *data) { struct i810fb_i2c_chan *chan = (struct i810fb_i2c_chan *)data; struct i810fb_par *par = chan->par; - u8 *mmio = par->mmio_start_virtual; + u8 __iomem *mmio = par->mmio_start_virtual; i810_writel(mmio, GPIOA, SDA_DIR_MASK); i810_writel(mmio, GPIOA, 0); -- cgit v1.2.3 From ae8aed0314064da3002879fedc2d262c72865a17 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Thu, 29 Sep 2005 00:37:34 +0100 Subject: [PATCH] saa6588 __user annotations Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- drivers/media/video/rds.h | 2 +- drivers/media/video/saa6588.c | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/drivers/media/video/rds.h b/drivers/media/video/rds.h index 30337d0f1a8..0d30eb744e6 100644 --- a/drivers/media/video/rds.h +++ b/drivers/media/video/rds.h @@ -31,7 +31,7 @@ struct rds_command { unsigned int block_count; int result; - unsigned char *buffer; + unsigned char __user *buffer; struct file *instance; poll_table *event_list; }; diff --git a/drivers/media/video/saa6588.c b/drivers/media/video/saa6588.c index 1a657a70ff4..72b70eb5da1 100644 --- a/drivers/media/video/saa6588.c +++ b/drivers/media/video/saa6588.c @@ -157,7 +157,7 @@ static struct i2c_client client_template; /* ---------------------------------------------------------------------- */ -static int block_to_user_buf(struct saa6588 *s, unsigned char *user_buf) +static int block_to_user_buf(struct saa6588 *s, unsigned char __user *user_buf) { int i; @@ -191,7 +191,7 @@ static void read_from_buf(struct saa6588 *s, struct rds_command *a) { unsigned long flags; - unsigned char *buf_ptr = a->buffer; /* This is a user space buffer! */ + unsigned char __user *buf_ptr = a->buffer; unsigned int i; unsigned int rd_blocks; -- cgit v1.2.3 From b2846dfa4aa1bbbf3f9977d67566952d7f621009 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Thu, 29 Sep 2005 00:42:27 +0100 Subject: [PATCH] mv64x60_wdt __user annotations and cleanups - use nonseekable_open() instead of messing with if (*ppos != file->f_pos) return -EISPIPE in ->write() (->read is NULL). - trivial __user annotations Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- drivers/char/watchdog/mv64x60_wdt.c | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/drivers/char/watchdog/mv64x60_wdt.c b/drivers/char/watchdog/mv64x60_wdt.c index 1436aea3b28..6d3ff0836c4 100644 --- a/drivers/char/watchdog/mv64x60_wdt.c +++ b/drivers/char/watchdog/mv64x60_wdt.c @@ -87,6 +87,8 @@ static int mv64x60_wdt_open(struct inode *inode, struct file *file) mv64x60_wdt_service(); mv64x60_wdt_handler_enable(); + nonseekable_open(inode, file); + return 0; } @@ -103,12 +105,9 @@ static int mv64x60_wdt_release(struct inode *inode, struct file *file) return 0; } -static ssize_t mv64x60_wdt_write(struct file *file, const char *data, +static ssize_t mv64x60_wdt_write(struct file *file, const char __user *data, size_t len, loff_t * ppos) { - if (*ppos != file->f_pos) - return -ESPIPE; - if (len) mv64x60_wdt_service(); @@ -119,6 +118,7 @@ static int mv64x60_wdt_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg) { int timeout; + void __user *argp = (void __user *)arg; static struct watchdog_info info = { .options = WDIOF_KEEPALIVEPING, .firmware_version = 0, @@ -127,13 +127,13 @@ static int mv64x60_wdt_ioctl(struct inode *inode, struct file *file, switch (cmd) { case WDIOC_GETSUPPORT: - if (copy_to_user((void *)arg, &info, sizeof(info))) + if (copy_to_user(argp, &info, sizeof(info))) return -EFAULT; break; case WDIOC_GETSTATUS: case WDIOC_GETBOOTSTATUS: - if (put_user(wdt_status, (int *)arg)) + if (put_user(wdt_status, (int __user *)argp)) return -EFAULT; wdt_status &= ~WDIOF_KEEPALIVEPING; break; @@ -154,7 +154,7 @@ static int mv64x60_wdt_ioctl(struct inode *inode, struct file *file, case WDIOC_GETTIMEOUT: timeout = mv64x60_wdt_timeout * HZ; - if (put_user(timeout, (int *)arg)) + if (put_user(timeout, (int __user *)argp)) return -EFAULT; break; -- cgit v1.2.3 From 375726d7ed08bd8cf2fe3cfe6b164ffb37fa7e90 Mon Sep 17 00:00:00 2001 From: "Antonino A. Daplas" Date: Thu, 29 Sep 2005 05:19:51 +0800 Subject: [PATCH] intelfb: Fix regression (blank display) from ioremap patch - Workaround for the ioremap patch that produces a blank display on some chipsets - Make hwcursor = 0 the default. The hardware cursor does not work with all hardware. Signed-off-by: Antonino Daplas Signed-off-by: Linus Torvalds --- drivers/video/Kconfig | 1 + drivers/video/intelfb/intelfbdrv.c | 21 ++++++++++----------- 2 files changed, 11 insertions(+), 11 deletions(-) diff --git a/drivers/video/Kconfig b/drivers/video/Kconfig index 773ae11b4a1..1cd942abb58 100644 --- a/drivers/video/Kconfig +++ b/drivers/video/Kconfig @@ -768,6 +768,7 @@ config FB_INTEL select FB_CFB_FILLRECT select FB_CFB_COPYAREA select FB_CFB_IMAGEBLIT + select FB_SOFT_CURSOR help This driver supports the on-board graphics built in to the Intel 830M/845G/852GM/855GM/865G chipsets. diff --git a/drivers/video/intelfb/intelfbdrv.c b/drivers/video/intelfb/intelfbdrv.c index bf62e6ed038..80a09344f1a 100644 --- a/drivers/video/intelfb/intelfbdrv.c +++ b/drivers/video/intelfb/intelfbdrv.c @@ -226,7 +226,7 @@ MODULE_DEVICE_TABLE(pci, intelfb_pci_table); static int accel = 1; static int vram = 4; -static int hwcursor = 1; +static int hwcursor = 0; static int mtrr = 1; static int fixed = 0; static int noinit = 0; @@ -609,15 +609,9 @@ intelfb_pci_register(struct pci_dev *pdev, const struct pci_device_id *ent) dinfo->accel = 0; } - if (MB(voffset) < stolen_size) - offset = (stolen_size >> 12); - else - offset = ROUND_UP_TO_PAGE(MB(voffset))/GTT_PAGE_SIZE; - /* Framebuffer parameters - Use all the stolen memory if >= vram */ - if (ROUND_UP_TO_PAGE(stolen_size) >= ((offset << 12) + MB(vram))) { + if (ROUND_UP_TO_PAGE(stolen_size) >= MB(vram)) { dinfo->fb.size = ROUND_UP_TO_PAGE(stolen_size); - dinfo->fb.offset = 0; dinfo->fbmem_gart = 0; } else { dinfo->fb.size = MB(vram); @@ -648,6 +642,11 @@ intelfb_pci_register(struct pci_dev *pdev, const struct pci_device_id *ent) return -ENODEV; } + if (MB(voffset) < stolen_size) + offset = (stolen_size >> 12); + else + offset = ROUND_UP_TO_PAGE(MB(voffset))/GTT_PAGE_SIZE; + /* set the mem offsets - set them after the already used pages */ if (dinfo->accel) { dinfo->ring.offset = offset + gtt_info.current_memory; @@ -662,10 +661,11 @@ intelfb_pci_register(struct pci_dev *pdev, const struct pci_device_id *ent) + (dinfo->cursor.size >> 12); } + /* Allocate memories (which aren't stolen) */ /* Map the fb and MMIO regions */ /* ioremap only up to the end of used aperture */ dinfo->aperture.virtual = (u8 __iomem *)ioremap_nocache - (dinfo->aperture.physical, (dinfo->fb.offset << 12) + (dinfo->aperture.physical, ((offset + dinfo->fb.offset) << 12) + dinfo->fb.size); if (!dinfo->aperture.virtual) { ERR_MSG("Cannot remap FB region.\n"); @@ -682,7 +682,6 @@ intelfb_pci_register(struct pci_dev *pdev, const struct pci_device_id *ent) return -ENODEV; } - /* Allocate memories (which aren't stolen) */ if (dinfo->accel) { if (!(dinfo->gtt_ring_mem = agp_allocate_memory(bridge, dinfo->ring.size >> 12, @@ -1484,7 +1483,7 @@ intelfb_cursor(struct fb_info *info, struct fb_cursor *cursor) #endif if (!dinfo->hwcursor) - return -ENXIO; + return soft_cursor(info, cursor); intelfbhw_cursor_hide(dinfo); -- cgit v1.2.3 From fe984bba30a29398578da3d8c0503fa39e84b838 Mon Sep 17 00:00:00 2001 From: Ben Dooks Date: Thu, 29 Sep 2005 05:24:38 +0800 Subject: [PATCH] s3c2410fb: Minor warning fix The function s3c2410fb_activate_var does not return a value, therefore it should be declared void. Signed-off-by: Ben Dooks Signed-off-by: Antonino Daplas Signed-off-by: Linus Torvalds --- drivers/video/s3c2410fb.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/video/s3c2410fb.c b/drivers/video/s3c2410fb.c index 00c0223a352..5ab79afb53b 100644 --- a/drivers/video/s3c2410fb.c +++ b/drivers/video/s3c2410fb.c @@ -228,8 +228,8 @@ static int s3c2410fb_check_var(struct fb_var_screeninfo *var, * information */ -static int s3c2410fb_activate_var(struct s3c2410fb_info *fbi, - struct fb_var_screeninfo *var) +static void s3c2410fb_activate_var(struct s3c2410fb_info *fbi, + struct fb_var_screeninfo *var) { fbi->regs.lcdcon1 &= ~S3C2410_LCDCON1_MODEMASK; -- cgit v1.2.3 From 82810a906f8734ae6503ea11436a7164d2f86f2e Mon Sep 17 00:00:00 2001 From: Deepak Saxena Date: Wed, 28 Sep 2005 16:42:54 -0700 Subject: [PATCH] Fix ixp4xx MTD driver module build Missing ';' breaks module build. Signed-off-by: Deepak Saxena Signed-off-by: Linus Torvalds --- drivers/mtd/maps/ixp4xx.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/mtd/maps/ixp4xx.c b/drivers/mtd/maps/ixp4xx.c index 5afe660aa2c..bbb0e6e569a 100644 --- a/drivers/mtd/maps/ixp4xx.c +++ b/drivers/mtd/maps/ixp4xx.c @@ -254,6 +254,6 @@ module_init(ixp4xx_flash_init); module_exit(ixp4xx_flash_exit); MODULE_LICENSE("GPL"); -MODULE_DESCRIPTION("MTD map driver for Intel IXP4xx systems") +MODULE_DESCRIPTION("MTD map driver for Intel IXP4xx systems"); MODULE_AUTHOR("Deepak Saxena"); -- cgit v1.2.3 From b38708fca9cc60d8a073a67c3b366116e38011c5 Mon Sep 17 00:00:00 2001 From: Deepak Saxena Date: Wed, 28 Sep 2005 18:07:01 -0700 Subject: [PATCH] Fix thinko in previous ARM 2917/1 patch Previous patch accidently add IXDP425 mach entry when IXDP465 is configured. Signed-off-by: Deepak Saxena Signed-off-by: Linus Torvalds --- arch/arm/mach-ixp4xx/ixdp425-setup.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/arm/mach-ixp4xx/ixdp425-setup.c b/arch/arm/mach-ixp4xx/ixdp425-setup.c index 39b06ed8064..0a41080d226 100644 --- a/arch/arm/mach-ixp4xx/ixdp425-setup.c +++ b/arch/arm/mach-ixp4xx/ixdp425-setup.c @@ -123,7 +123,7 @@ static void __init ixdp425_init(void) platform_add_devices(ixdp425_devices, ARRAY_SIZE(ixdp425_devices)); } -#ifdef CONFIG_ARCH_IXDP465 +#ifdef CONFIG_ARCH_IXDP425 MACHINE_START(IXDP425, "Intel IXDP425 Development Platform") /* Maintainer: MontaVista Software, Inc. */ .phys_ram = PHYS_OFFSET, -- cgit v1.2.3 From aa55a08687059aa169d10a313c41f238c2070488 Mon Sep 17 00:00:00 2001 From: Oleg Nesterov Date: Thu, 29 Sep 2005 19:58:53 +0400 Subject: [PATCH] fix TASK_STOPPED vs TASK_NONINTERACTIVE interaction do_signal_stop: for_each_thread(t) { if (t->state < TASK_STOPPED) ++sig->group_stop_count; } However, TASK_NONINTERACTIVE > TASK_STOPPED, so this loop will not count TASK_INTERRUPTIBLE | TASK_NONINTERACTIVE threads. See also wait_task_stopped(), which checks ->state > TASK_STOPPED. Signed-off-by: Oleg Nesterov [ We really probably should always use the appropriate bitmasks to test task states, not do it like this. Using something like #define TASK_RUNNABLE (TASK_RUNNING | TASK_INTERRUPTIBLE | \ TASK_UNINTERRUPTIBLE | TASK_NONINTERACTIVE) and then doing "if (task->state & TASK_RUNNABLE)" or similar. But the ordering of the task states is historical, and keeping the ordering does make sense regardless. ] Signed-off-by: Linus Torvalds --- include/linux/sched.h | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/include/linux/sched.h b/include/linux/sched.h index 49e617fa0f6..afe6c61f13e 100644 --- a/include/linux/sched.h +++ b/include/linux/sched.h @@ -110,11 +110,11 @@ extern unsigned long nr_iowait(void); #define TASK_RUNNING 0 #define TASK_INTERRUPTIBLE 1 #define TASK_UNINTERRUPTIBLE 2 -#define TASK_STOPPED 4 -#define TASK_TRACED 8 -#define EXIT_ZOMBIE 16 -#define EXIT_DEAD 32 -#define TASK_NONINTERACTIVE 64 +#define TASK_NONINTERACTIVE 4 +#define TASK_STOPPED 8 +#define TASK_TRACED 16 +#define EXIT_ZOMBIE 32 +#define EXIT_DEAD 64 #define __set_task_state(tsk, state_value) \ do { (tsk)->state = (state_value); } while (0) -- cgit v1.2.3 From 4a8342d233a39ee582e9f7260e12d2f5fd194a05 Mon Sep 17 00:00:00 2001 From: Linus Torvalds Date: Thu, 29 Sep 2005 15:18:21 -0700 Subject: Revert task flag re-ordering, add comments Roland points out that the flags end up having non-obvious dependencies elsewhere, so revert aa55a08687059aa169d10a313c41f238c2070488 and add some comments about why things are as they are. We'll just have to fix up the broken comparisons. Roland has a patch. Signed-off-by: Linus Torvalds --- include/linux/sched.h | 22 +++++++++++++++++----- 1 file changed, 17 insertions(+), 5 deletions(-) diff --git a/include/linux/sched.h b/include/linux/sched.h index afe6c61f13e..c3ba31f210a 100644 --- a/include/linux/sched.h +++ b/include/linux/sched.h @@ -107,14 +107,26 @@ extern unsigned long nr_iowait(void); #include +/* + * Task state bitmask. NOTE! These bits are also + * encoded in fs/proc/array.c: get_task_state(). + * + * We have two separate sets of flags: task->state + * is about runnability, while task->exit_state are + * about the task exiting. Confusing, but this way + * modifying one set can't modify the other one by + * mistake. + */ #define TASK_RUNNING 0 #define TASK_INTERRUPTIBLE 1 #define TASK_UNINTERRUPTIBLE 2 -#define TASK_NONINTERACTIVE 4 -#define TASK_STOPPED 8 -#define TASK_TRACED 16 -#define EXIT_ZOMBIE 32 -#define EXIT_DEAD 64 +#define TASK_STOPPED 4 +#define TASK_TRACED 8 +/* in tsk->exit_state */ +#define EXIT_ZOMBIE 16 +#define EXIT_DEAD 32 +/* in tsk->state again */ +#define TASK_NONINTERACTIVE 64 #define __set_task_state(tsk, state_value) \ do { (tsk)->state = (state_value); } while (0) -- cgit v1.2.3 From 5acbc5cb507e6c381b70093b1081854708e82b16 Mon Sep 17 00:00:00 2001 From: Roland McGrath Date: Thu, 29 Sep 2005 14:54:42 -0700 Subject: [PATCH] Fix task state testing properly in do_signal_stop() Any tests using < TASK_STOPPED or the like are left over from the time when the TASK_ZOMBIE and TASK_DEAD bits were in the same word, and it served to check for "stopped or dead". I think this one in do_signal_stop is the only such case. It has been buggy ever since exit_state was separated, and isn't testing the exit_state value. Signed-off-by: Roland McGrath Signed-off-by: Linus Torvalds --- kernel/signal.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/kernel/signal.c b/kernel/signal.c index 5a274705ba1..619b027e92b 100644 --- a/kernel/signal.c +++ b/kernel/signal.c @@ -1763,7 +1763,8 @@ do_signal_stop(int signr) * stop is always done with the siglock held, * so this check has no races. */ - if (t->state < TASK_STOPPED) { + if (!t->exit_state && + !(t->state & (TASK_STOPPED|TASK_TRACED))) { stop_count++; signal_wake_up(t, 0); } -- cgit v1.2.3 From 7d318d774789657c37a5e994a4a2cf59d4879ae7 Mon Sep 17 00:00:00 2001 From: Andi Kleen Date: Thu, 29 Sep 2005 22:05:55 +0200 Subject: [PATCH] Fix up TLB flush filter disabling I checked with AMD and they requested to only disable it for family 15. Also disable it for i386 too. And some style fixes. Signed-off-by: Andi Kleen Signed-off-by: Linus Torvalds --- arch/i386/kernel/cpu/amd.c | 16 ++++++++++++++++ arch/x86_64/kernel/setup.c | 22 ++++++++++++---------- include/asm-x86_64/msr.h | 1 + 3 files changed, 29 insertions(+), 10 deletions(-) diff --git a/arch/i386/kernel/cpu/amd.c b/arch/i386/kernel/cpu/amd.c index 73aeaf5a9d4..4c1ddf2b57c 100644 --- a/arch/i386/kernel/cpu/amd.c +++ b/arch/i386/kernel/cpu/amd.c @@ -28,6 +28,22 @@ static void __init init_amd(struct cpuinfo_x86 *c) int mbytes = num_physpages >> (20-PAGE_SHIFT); int r; +#ifdef CONFIG_SMP + unsigned long value; + + /* Disable TLB flush filter by setting HWCR.FFDIS on K8 + * bit 6 of msr C001_0015 + * + * Errata 63 for SH-B3 steppings + * Errata 122 for all steppings (F+ have it disabled by default) + */ + if (c->x86 == 15) { + rdmsrl(MSR_K7_HWCR, value); + value |= 1 << 6; + wrmsrl(MSR_K7_HWCR, value); + } +#endif + /* * FIXME: We should handle the K5 here. Set up the write * range and also turn on MSR 83 bits 4 and 31 (write alloc, diff --git a/arch/x86_64/kernel/setup.c b/arch/x86_64/kernel/setup.c index 238f73e1a83..257f5ba1790 100644 --- a/arch/x86_64/kernel/setup.c +++ b/arch/x86_64/kernel/setup.c @@ -831,8 +831,6 @@ static void __init amd_detect_cmp(struct cpuinfo_x86 *c) #endif } -#define HWCR 0xc0010015 - static int __init init_amd(struct cpuinfo_x86 *c) { int r; @@ -841,14 +839,18 @@ static int __init init_amd(struct cpuinfo_x86 *c) #ifdef CONFIG_SMP unsigned long value; - // Disable TLB flush filter by setting HWCR.FFDIS: - // bit 6 of msr C001_0015 - // - // Errata 63 for SH-B3 steppings - // Errata 122 for all(?) steppings - rdmsrl(HWCR, value); - value |= 1 << 6; - wrmsrl(HWCR, value); + /* + * Disable TLB flush filter by setting HWCR.FFDIS on K8 + * bit 6 of msr C001_0015 + * + * Errata 63 for SH-B3 steppings + * Errata 122 for all steppings (F+ have it disabled by default) + */ + if (c->x86 == 15) { + rdmsrl(MSR_K8_HWCR, value); + value |= 1 << 6; + wrmsrl(MSR_K8_HWCR, value); + } #endif /* Bit 31 in normal CPUID used for nonstandard 3DNow ID; diff --git a/include/asm-x86_64/msr.h b/include/asm-x86_64/msr.h index 4d727f3f555..5a7fe3c6c3d 100644 --- a/include/asm-x86_64/msr.h +++ b/include/asm-x86_64/msr.h @@ -234,6 +234,7 @@ static inline unsigned int cpuid_edx(unsigned int op) #define MSR_K8_TOP_MEM1 0xC001001A #define MSR_K8_TOP_MEM2 0xC001001D #define MSR_K8_SYSCFG 0xC0010010 +#define MSR_K8_HWCR 0xC0010015 /* K6 MSRs */ #define MSR_K6_EFER 0xC0000080 -- cgit v1.2.3 From 7644143cd6f7e029f3a8ea64f5fb0ab33ec39f72 Mon Sep 17 00:00:00 2001 From: Mike Waychison Date: Fri, 30 Sep 2005 00:01:27 +0200 Subject: [PATCH] x86_64: Fix mce_log The attempt to fixup the lockless mce log buffer introduced an infinite loop when trying to find a free entry. And: Using rcu_dereference() to load mcelog.next doesn't seem to be sufficient enough to ensure that mcelog.next is loaded each time around the loop in mce_log(). Instead, use an explicit rmb() to ensure that the compiler gets it right. AK: turned the smp_wmbs into true wmbs to make sure they are not reordered by the compiler on UP. Signed-off-by: Mike Waychison Signed-off-by: Andi Kleen Signed-off-by: Linus Torvalds --- arch/x86_64/kernel/mce.c | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/arch/x86_64/kernel/mce.c b/arch/x86_64/kernel/mce.c index 08203b07f4b..69541db5ff2 100644 --- a/arch/x86_64/kernel/mce.c +++ b/arch/x86_64/kernel/mce.c @@ -54,9 +54,12 @@ void mce_log(struct mce *mce) { unsigned next, entry; mce->finished = 0; - smp_wmb(); + wmb(); for (;;) { entry = rcu_dereference(mcelog.next); + /* The rmb forces the compiler to reload next in each + iteration */ + rmb(); for (;;) { /* When the buffer fills up discard new entries. Assume that the earlier errors are the more interesting. */ @@ -69,6 +72,7 @@ void mce_log(struct mce *mce) entry++; continue; } + break; } smp_rmb(); next = entry + 1; @@ -76,9 +80,9 @@ void mce_log(struct mce *mce) break; } memcpy(mcelog.entry + entry, mce, sizeof(struct mce)); - smp_wmb(); + wmb(); mcelog.entry[entry].finished = 1; - smp_wmb(); + wmb(); if (!test_and_set_bit(0, &console_logged)) notify_user = 1; -- cgit v1.2.3 From 411b67b4b6a4dd1e0292a6a58dd753978179d173 Mon Sep 17 00:00:00 2001 From: Kostik Belousov Date: Wed, 28 Sep 2005 18:21:28 +0300 Subject: [PATCH] readv/writev syscalls are not checked by lsm it seems that readv(2)/writev(2) syscalls do not call file_permission callback. Looks like this is overlook. I have filled the issue into redhat bugzilla as https://bugzilla.redhat.com/bugzilla/show_bug.cgi?id=169433 and got the recommendation to post this on lsm mailing list. The following trivial patch solves the problem. Signed-off-by: Kostik Belousov Signed-off-by: Chris Wright --- fs/read_write.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/fs/read_write.c b/fs/read_write.c index b60324aaa2b..a091ee4f430 100644 --- a/fs/read_write.c +++ b/fs/read_write.c @@ -497,6 +497,9 @@ static ssize_t do_readv_writev(int type, struct file *file, } ret = rw_verify_area(type, file, pos, tot_len); + if (ret) + goto out; + ret = security_file_permission(file, type == READ ? MAY_READ : MAY_WRITE); if (ret) goto out; -- cgit v1.2.3 From a44fe13eab664ac488ced0845d9885b019bd24c5 Mon Sep 17 00:00:00 2001 From: Benjamin Herrenschmidt Date: Fri, 30 Sep 2005 08:25:17 +1000 Subject: [PATCH] Fix ppc64 smu driver locking The SMU driver has a small mistake in the locking of the interrupt code, if polled access and interrupt access race, interrupt may take a lock and return without releasing it. This fixes it. With that patch, the driver is rock solid with my experimental thermal control (which bangs it pretty hard) racing with real time clock and cpufreq handling. Signed-off-by: Benjamin Herrenschmidt Signed-off-by: Linus Torvalds --- drivers/macintosh/smu.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/macintosh/smu.c b/drivers/macintosh/smu.c index a85ac18dd21..9b38674fbf7 100644 --- a/drivers/macintosh/smu.c +++ b/drivers/macintosh/smu.c @@ -153,8 +153,10 @@ static irqreturn_t smu_db_intr(int irq, void *arg, struct pt_regs *regs) spin_lock_irqsave(&smu->lock, flags); gpio = pmac_do_feature_call(PMAC_FTR_READ_GPIO, NULL, smu->doorbell); - if ((gpio & 7) != 7) + if ((gpio & 7) != 7) { + spin_unlock_irqrestore(&smu->lock, flags); return IRQ_HANDLED; + } cmd = smu->cmd_cur; smu->cmd_cur = NULL; -- cgit v1.2.3 From dce79affd5d04e9cbabe35016eda55213b9b36f6 Mon Sep 17 00:00:00 2001 From: Daniel Jacobowitz Date: Fri, 30 Sep 2005 00:17:35 +0100 Subject: [ARM] 2941/1: Fix running legacy binaries from a soft-float root filesystem with CONFIG_IWMMXT. Patch from Daniel Jacobowitz Thread flags are inherited on fork(). In order for a binary which has the iWMMXt coprocessor enabled to run a binary which needs the FPA emulation, we need to explicitly clear TIF_USING_IWMMXT if we are not going to set it. Signed-off-by: Daniel Jacobowitz Signed-off-by: Russell King --- include/asm-arm/elf.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/include/asm-arm/elf.h b/include/asm-arm/elf.h index a1696ba238d..7da97a93754 100644 --- a/include/asm-arm/elf.h +++ b/include/asm-arm/elf.h @@ -124,6 +124,8 @@ do { \ if (((ex).e_flags & EF_ARM_EABI_MASK) || \ ((ex).e_flags & EF_ARM_SOFT_FLOAT)) \ set_thread_flag(TIF_USING_IWMMXT); \ + else \ + clear_thread_flag(TIF_USING_IWMMXT); \ } while (0) #endif -- cgit v1.2.3 From 01ff367e62f0474e4d39aa5812cbe2a30d96e1e9 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Thu, 29 Sep 2005 17:07:20 -0700 Subject: [TCP]: Revert 6b251858d377196b8cea20e65cae60f584a42735 But retain the comment fix. Alexey Kuznetsov has explained the situation as follows: -------------------- I think the fix is incorrect. Look, the RFC function init_cwnd(mss) is not continuous: f.e. for mss=1095 it needs initial window 1095*4, but for mss=1096 it is 1096*3. We do not know exactly what mss sender used for calculations. If we advertised 1096 (and calculate initial window 3*1096), the sender could limit it to some value < 1096 and then it will need window his_mss*4 > 3*1096 to send initial burst. See? So, the honest function for inital rcv_wnd derived from tcp_init_cwnd() is: init_rcv_wnd(mss)= min { init_cwnd(mss1)*mss1 for mss1 <= mss } It is something sort of: if (mss < 1096) return mss*4; if (mss < 1096*2) return 1096*4; return mss*2; (I just scrablled a graph of piece of paper, it is difficult to see or to explain without this) I selected it differently giving more window than it is strictly required. Initial receive window must be large enough to allow sender following to the rfc (or just setting initial cwnd to 2) to send initial burst. But besides that it is arbitrary, so I decided to give slack space of one segment. Actually, the logic was: If mss is low/normal (<=ethernet), set window to receive more than initial burst allowed by rfc under the worst conditions i.e. mss*4. This gives slack space of 1 segment for ethernet frames. For msses slighlty more than ethernet frame, take 3. Try to give slack space of 1 frame again. If mss is huge, force 2*mss. No slack space. Value 1460*3 is really confusing. Minimal one is 1096*2, but besides that it is an arbitrary value. It was meant to be ~4096. 1460*3 is just the magic number from RFC, 1460*3 = 1095*4 is the magic :-), so that I guess hands typed this themselves. -------------------- Signed-off-by: David S. Miller --- net/ipv4/tcp_output.c | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/net/ipv4/tcp_output.c b/net/ipv4/tcp_output.c index caf2e2cff29..c5b911f9b66 100644 --- a/net/ipv4/tcp_output.c +++ b/net/ipv4/tcp_output.c @@ -194,12 +194,11 @@ void tcp_select_initial_window(int __space, __u32 mss, * will be satisfied with 2. */ if (mss > (1<<*rcv_wscale)) { - int init_cwnd; - - if (mss > 1460) + int init_cwnd = 4; + if (mss > 1460*3) init_cwnd = 2; - else - init_cwnd = (mss > 1095) ? 3 : 4; + else if (mss > 1460) + init_cwnd = 3; if (*rcv_wnd > init_cwnd*mss) *rcv_wnd = init_cwnd*mss; } -- cgit v1.2.3 From 09e9ec87111ba818d8171262b15ba4c357eb1d27 Mon Sep 17 00:00:00 2001 From: Alexey Kuznetsov Date: Thu, 29 Sep 2005 17:17:15 -0700 Subject: [TCP]: Don't over-clamp window in tcp_clamp_window() From: Alexey Kuznetsov Handle better the case where the sender sends full sized frames initially, then moves to a mode where it trickles out small amounts of data at a time. This known problem is even mentioned in the comments above tcp_grow_window() in tcp_input.c, specifically: ... * The scheme does not work when sender sends good segments opening * window and then starts to feed us spagetti. But it should work * in common situations. Otherwise, we have to rely on queue collapsing. ... When the sender gives full sized frames, the "struct sk_buff" overhead from each packet is small. So we'll advertize a larger window. If the sender moves to a mode where small segments are sent, this ratio becomes tilted to the other extreme and we start overrunning the socket buffer space. tcp_clamp_window() tries to address this, but it's clamping of tp->window_clamp is a wee bit too aggressive for this particular case. Fix confirmed by Ion Badulescu. Signed-off-by: David S. Miller --- net/ipv4/tcp_input.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/net/ipv4/tcp_input.c b/net/ipv4/tcp_input.c index a7537c7bbd0..677419d0c9a 100644 --- a/net/ipv4/tcp_input.c +++ b/net/ipv4/tcp_input.c @@ -355,8 +355,6 @@ static void tcp_clamp_window(struct sock *sk, struct tcp_sock *tp) app_win -= icsk->icsk_ack.rcv_mss; app_win = max(app_win, 2U*tp->advmss); - if (!ofo_win) - tp->window_clamp = min(tp->window_clamp, app_win); tp->rcv_ssthresh = min(tp->window_clamp, 2U*tp->advmss); } } -- cgit v1.2.3 From 4a7097fcc431ab2ccf509d8342831873138c814a Mon Sep 17 00:00:00 2001 From: Scott Talbert Date: Thu, 29 Sep 2005 17:30:54 -0700 Subject: [ATM]: [lec] attempt to support cisco failover From: Scott Talbert Signed-off-by: Chas Williams Signed-off-by: David S. Miller --- net/atm/lec.c | 37 ++++++++++++++++++++++++++++++++++--- 1 file changed, 34 insertions(+), 3 deletions(-) diff --git a/net/atm/lec.c b/net/atm/lec.c index a0752487026..47e1eae9746 100644 --- a/net/atm/lec.c +++ b/net/atm/lec.c @@ -686,9 +686,19 @@ static unsigned char lec_ctrl_magic[] = { 0x01, 0x01 }; +#define LEC_DATA_DIRECT_8023 2 +#define LEC_DATA_DIRECT_8025 3 + +static int lec_is_data_direct(struct atm_vcc *vcc) +{ + return ((vcc->sap.blli[0].l3.tr9577.snap[4] == LEC_DATA_DIRECT_8023) || + (vcc->sap.blli[0].l3.tr9577.snap[4] == LEC_DATA_DIRECT_8025)); +} + static void lec_push(struct atm_vcc *vcc, struct sk_buff *skb) { + unsigned long flags; struct net_device *dev = (struct net_device *)vcc->proto_data; struct lec_priv *priv = (struct lec_priv *)dev->priv; @@ -728,7 +738,8 @@ lec_push(struct atm_vcc *vcc, struct sk_buff *skb) skb_queue_tail(&sk->sk_receive_queue, skb); sk->sk_data_ready(sk, skb->len); } else { /* Data frame, queue to protocol handlers */ - unsigned char *dst; + struct lec_arp_table *entry; + unsigned char *src, *dst; atm_return(vcc,skb->truesize); if (*(uint16_t *)skb->data == htons(priv->lecid) || @@ -741,10 +752,30 @@ lec_push(struct atm_vcc *vcc, struct sk_buff *skb) return; } #ifdef CONFIG_TR - if (priv->is_trdev) dst = ((struct lecdatahdr_8025 *)skb->data)->h_dest; + if (priv->is_trdev) + dst = ((struct lecdatahdr_8025 *) skb->data)->h_dest; else #endif - dst = ((struct lecdatahdr_8023 *)skb->data)->h_dest; + dst = ((struct lecdatahdr_8023 *) skb->data)->h_dest; + + /* If this is a Data Direct VCC, and the VCC does not match + * the LE_ARP cache entry, delete the LE_ARP cache entry. + */ + spin_lock_irqsave(&priv->lec_arp_lock, flags); + if (lec_is_data_direct(vcc)) { +#ifdef CONFIG_TR + if (priv->is_trdev) + src = ((struct lecdatahdr_8025 *) skb->data)->h_source; + else +#endif + src = ((struct lecdatahdr_8023 *) skb->data)->h_source; + entry = lec_arp_find(priv, src); + if (entry && entry->vcc != vcc) { + lec_arp_remove(priv, entry); + kfree(entry); + } + } + spin_unlock_irqrestore(&priv->lec_arp_lock, flags); if (!(dst[0]&0x01) && /* Never filter Multi/Broadcast */ !priv->is_proxy && /* Proxy wants all the packets */ -- cgit v1.2.3 From 75b895c15b3ea2a3cd5c8e8f3c62e4598ef4d2ba Mon Sep 17 00:00:00 2001 From: Scott Talbert Date: Thu, 29 Sep 2005 17:31:30 -0700 Subject: [ATM]: [lec] reset retry counter when new arp issued From: Scott Talbert Signed-off-by: Chas Williams Signed-off-by: David S. Miller --- net/atm/lec.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/net/atm/lec.c b/net/atm/lec.c index 47e1eae9746..ad840b9afba 100644 --- a/net/atm/lec.c +++ b/net/atm/lec.c @@ -2021,6 +2021,12 @@ lec_arp_resolve(struct lec_priv *priv, unsigned char *mac_to_find, found = entry->vcc; goto out; } + /* If the LE_ARP cache entry is still pending, reset count to 0 + * so another LE_ARP request can be made for this frame. + */ + if (entry->status == ESI_ARP_PENDING) { + entry->no_tries = 0; + } /* Data direct VC not yet set up, check to see if the unknown frame count is greater than the limit. If the limit has not been reached, allow the caller to send packet to -- cgit v1.2.3 From 13edad7a5cef1c952459742482482a6b05e1a8a1 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Thu, 29 Sep 2005 17:58:26 -0700 Subject: [SPARC64]: Rewrite convoluted physical memory probing. Delete all of the code working with sp_banks[] and replace with clean acquisition and sorting of physical memory parameters from the firmware. Signed-off-by: David S. Miller --- arch/sparc64/kernel/traps.c | 2 +- arch/sparc64/mm/init.c | 302 +++++++++++++++-------------------------- include/asm-sparc64/openprom.h | 4 +- 3 files changed, 114 insertions(+), 194 deletions(-) diff --git a/arch/sparc64/kernel/traps.c b/arch/sparc64/kernel/traps.c index 7f190fc5754..5570e7bb22b 100644 --- a/arch/sparc64/kernel/traps.c +++ b/arch/sparc64/kernel/traps.c @@ -1333,7 +1333,7 @@ static int cheetah_check_main_memory(unsigned long paddr) { unsigned long vaddr = PAGE_OFFSET + paddr; - if (vaddr > high_memory) + if (vaddr > (unsigned long) high_memory) return 0; return kern_addr_valid(vaddr); diff --git a/arch/sparc64/mm/init.c b/arch/sparc64/mm/init.c index 48851a2e4fe..5db50524f20 100644 --- a/arch/sparc64/mm/init.c +++ b/arch/sparc64/mm/init.c @@ -21,6 +21,7 @@ #include #include #include +#include #include #include @@ -41,14 +42,72 @@ extern void device_scan(void); -struct sparc_phys_banks { - unsigned long base_addr; - unsigned long num_bytes; -}; +#define MAX_BANKS 32 + +static struct linux_prom64_registers pavail[MAX_BANKS] __initdata; +static struct linux_prom64_registers pavail_rescan[MAX_BANKS] __initdata; +static int pavail_ents __initdata; +static int pavail_rescan_ents __initdata; + +static int cmp_p64(const void *a, const void *b) +{ + const struct linux_prom64_registers *x = a, *y = b; + + if (x->phys_addr > y->phys_addr) + return 1; + if (x->phys_addr < y->phys_addr) + return -1; + return 0; +} + +static void __init read_obp_memory(const char *property, + struct linux_prom64_registers *regs, + int *num_ents) +{ + int node = prom_finddevice("/memory"); + int prop_size = prom_getproplen(node, property); + int ents, ret, i; + + ents = prop_size / sizeof(struct linux_prom64_registers); + if (ents > MAX_BANKS) { + prom_printf("The machine has more %s property entries than " + "this kernel can support (%d).\n", + property, MAX_BANKS); + prom_halt(); + } + + ret = prom_getproperty(node, property, (char *) regs, prop_size); + if (ret == -1) { + prom_printf("Couldn't get %s property from /memory.\n"); + prom_halt(); + } + + *num_ents = ents; -#define SPARC_PHYS_BANKS 32 + /* Sanitize what we got from the firmware, by page aligning + * everything. + */ + for (i = 0; i < ents; i++) { + unsigned long base, size; + + base = regs[i].phys_addr; + size = regs[i].reg_size; -static struct sparc_phys_banks sp_banks[SPARC_PHYS_BANKS]; + size &= PAGE_MASK; + if (base & ~PAGE_MASK) { + unsigned long new_base = PAGE_ALIGN(base); + + size -= new_base - base; + if ((long) size < 0L) + size = 0UL; + base = new_base; + } + regs[i].phys_addr = base; + regs[i].reg_size = size; + } + sort(regs, ents, sizeof(struct linux_prom64_registers), + cmp_p64, NULL); +} unsigned long *sparc64_valid_addr_bitmap __read_mostly; @@ -1213,14 +1272,14 @@ unsigned long __init bootmem_init(unsigned long *pages_avail) int i; #ifdef CONFIG_DEBUG_BOOTMEM - prom_printf("bootmem_init: Scan sp_banks, "); + prom_printf("bootmem_init: Scan pavail, "); #endif bytes_avail = 0UL; - for (i = 0; sp_banks[i].num_bytes != 0; i++) { - end_of_phys_memory = sp_banks[i].base_addr + - sp_banks[i].num_bytes; - bytes_avail += sp_banks[i].num_bytes; + for (i = 0; i < pavail_ents; i++) { + end_of_phys_memory = pavail[i].phys_addr + + pavail[i].reg_size; + bytes_avail += pavail[i].reg_size; if (cmdline_memory_size) { if (bytes_avail > cmdline_memory_size) { unsigned long slack = bytes_avail - cmdline_memory_size; @@ -1228,12 +1287,15 @@ unsigned long __init bootmem_init(unsigned long *pages_avail) bytes_avail -= slack; end_of_phys_memory -= slack; - sp_banks[i].num_bytes -= slack; - if (sp_banks[i].num_bytes == 0) { - sp_banks[i].base_addr = 0xdeadbeef; + pavail[i].reg_size -= slack; + if ((long)pavail[i].reg_size <= 0L) { + pavail[i].phys_addr = 0xdeadbeefUL; + pavail[i].reg_size = 0UL; + pavail_ents = i; } else { - sp_banks[i+1].num_bytes = 0; - sp_banks[i+1].base_addr = 0xdeadbeef; + pavail[i+1].reg_size = 0Ul; + pavail[i+1].phys_addr = 0xdeadbeefUL; + pavail_ents = i + 1; } break; } @@ -1287,12 +1349,12 @@ unsigned long __init bootmem_init(unsigned long *pages_avail) /* Now register the available physical memory with the * allocator. */ - for (i = 0; sp_banks[i].num_bytes != 0; i++) { + for (i = 0; i < pavail_ents; i++) { #ifdef CONFIG_DEBUG_BOOTMEM - prom_printf("free_bootmem(sp_banks:%d): base[%lx] size[%lx]\n", - i, sp_banks[i].base_addr, sp_banks[i].num_bytes); + prom_printf("free_bootmem(pavail:%d): base[%lx] size[%lx]\n", + i, pavail[i].phys_addr, pavail[i].reg_size); #endif - free_bootmem(sp_banks[i].base_addr, sp_banks[i].num_bytes); + free_bootmem(pavail[i].phys_addr, pavail[i].reg_size); } #ifdef CONFIG_BLK_DEV_INITRD @@ -1341,7 +1403,7 @@ static unsigned long kernel_map_range(unsigned long pstart, unsigned long pend, unsigned long alloc_bytes = 0UL; if ((vstart & ~PAGE_MASK) || (vend & ~PAGE_MASK)) { - prom_printf("kernel_map: Unaligned sp_banks[%lx:%lx]\n", + prom_printf("kernel_map: Unaligned physmem[%lx:%lx]\n", vstart, vend); prom_halt(); } @@ -1388,23 +1450,24 @@ static unsigned long kernel_map_range(unsigned long pstart, unsigned long pend, return alloc_bytes; } -extern struct linux_mlist_p1275 *prom_ptot_ptr; +static struct linux_prom64_registers pall[MAX_BANKS] __initdata; +static int pall_ents __initdata; + extern unsigned int kvmap_linear_patch[1]; static void __init kernel_physical_mapping_init(void) { - struct linux_mlist_p1275 *p = prom_ptot_ptr; - unsigned long mem_alloced = 0UL; + unsigned long i, mem_alloced = 0UL; - while (p) { + read_obp_memory("reg", &pall[0], &pall_ents); + + for (i = 0; i < pall_ents; i++) { unsigned long phys_start, phys_end; - phys_start = p->start_adr; - phys_end = phys_start + p->num_bytes; + phys_start = pall[i].phys_addr; + phys_end = phys_start + pall[i].reg_size; mem_alloced += kernel_map_range(phys_start, phys_end, PAGE_KERNEL); - - p = p->theres_more; } printk("Allocated %ld bytes for kernel page tables.\n", @@ -1434,60 +1497,14 @@ void kernel_map_pages(struct page *page, int numpages, int enable) unsigned long __init find_ecache_flush_span(unsigned long size) { - unsigned long i; - - for (i = 0; ; i++) { - if (sp_banks[i].num_bytes == 0) - break; - if (sp_banks[i].num_bytes >= size) - return sp_banks[i].base_addr; - } - - return ~0UL; -} - -static void __init prom_probe_memory(void) -{ - struct linux_mlist_p1275 *mlist; - unsigned long bytes, base_paddr, tally; int i; - i = 0; - mlist = *prom_meminfo()->p1275_available; - bytes = tally = mlist->num_bytes; - base_paddr = mlist->start_adr; - - sp_banks[0].base_addr = base_paddr; - sp_banks[0].num_bytes = bytes; - - while (mlist->theres_more != (void *) 0) { - i++; - mlist = mlist->theres_more; - bytes = mlist->num_bytes; - tally += bytes; - if (i >= SPARC_PHYS_BANKS-1) { - printk ("The machine has more banks than " - "this kernel can support\n" - "Increase the SPARC_PHYS_BANKS " - "setting (currently %d)\n", - SPARC_PHYS_BANKS); - i = SPARC_PHYS_BANKS-1; - break; - } - - sp_banks[i].base_addr = mlist->start_adr; - sp_banks[i].num_bytes = mlist->num_bytes; + for (i = 0; i < pavail_ents; i++) { + if (pavail[i].reg_size >= size) + return pavail[i].phys_addr; } - i++; - sp_banks[i].base_addr = 0xdeadbeefbeefdeadUL; - sp_banks[i].num_bytes = 0; - - /* Now mask all bank sizes on a page boundary, it is all we can - * use anyways. - */ - for (i = 0; sp_banks[i].num_bytes != 0; i++) - sp_banks[i].num_bytes &= PAGE_MASK; + return ~0UL; } /* paging_init() sets up the page tables */ @@ -1502,17 +1519,13 @@ void __init paging_init(void) unsigned long end_pfn, pages_avail, shift; unsigned long real_end, i; - prom_probe_memory(); + /* Find available physical memory... */ + read_obp_memory("available", &pavail[0], &pavail_ents); phys_base = 0xffffffffffffffffUL; - for (i = 0; sp_banks[i].num_bytes != 0; i++) { - unsigned long top; + for (i = 0; i < pavail_ents; i++) + phys_base = min(phys_base, pavail[i].phys_addr); - if (sp_banks[i].base_addr < phys_base) - phys_base = sp_banks[i].base_addr; - top = sp_banks[i].base_addr + - sp_banks[i].num_bytes; - } pfn_base = phys_base >> PAGE_SHIFT; kern_base = (prom_boot_mapping_phys_low >> 22UL) << 22UL; @@ -1588,128 +1601,35 @@ void __init paging_init(void) device_scan(); } -/* Ok, it seems that the prom can allocate some more memory chunks - * as a side effect of some prom calls we perform during the - * boot sequence. My most likely theory is that it is from the - * prom_set_traptable() call, and OBP is allocating a scratchpad - * for saving client program register state etc. - */ -static void __init sort_memlist(struct linux_mlist_p1275 *thislist) -{ - int swapi = 0; - int i, mitr; - unsigned long tmpaddr, tmpsize; - unsigned long lowest; - - for (i = 0; thislist[i].theres_more != 0; i++) { - lowest = thislist[i].start_adr; - for (mitr = i+1; thislist[mitr-1].theres_more != 0; mitr++) - if (thislist[mitr].start_adr < lowest) { - lowest = thislist[mitr].start_adr; - swapi = mitr; - } - if (lowest == thislist[i].start_adr) - continue; - tmpaddr = thislist[swapi].start_adr; - tmpsize = thislist[swapi].num_bytes; - for (mitr = swapi; mitr > i; mitr--) { - thislist[mitr].start_adr = thislist[mitr-1].start_adr; - thislist[mitr].num_bytes = thislist[mitr-1].num_bytes; - } - thislist[i].start_adr = tmpaddr; - thislist[i].num_bytes = tmpsize; - } -} - -void __init rescan_sp_banks(void) -{ - struct linux_prom64_registers memlist[64]; - struct linux_mlist_p1275 avail[64], *mlist; - unsigned long bytes, base_paddr; - int num_regs, node = prom_finddevice("/memory"); - int i; - - num_regs = prom_getproperty(node, "available", - (char *) memlist, sizeof(memlist)); - num_regs = (num_regs / sizeof(struct linux_prom64_registers)); - for (i = 0; i < num_regs; i++) { - avail[i].start_adr = memlist[i].phys_addr; - avail[i].num_bytes = memlist[i].reg_size; - avail[i].theres_more = &avail[i + 1]; - } - avail[i - 1].theres_more = NULL; - sort_memlist(avail); - - mlist = &avail[0]; - i = 0; - bytes = mlist->num_bytes; - base_paddr = mlist->start_adr; - - sp_banks[0].base_addr = base_paddr; - sp_banks[0].num_bytes = bytes; - - while (mlist->theres_more != NULL){ - i++; - mlist = mlist->theres_more; - bytes = mlist->num_bytes; - if (i >= SPARC_PHYS_BANKS-1) { - printk ("The machine has more banks than " - "this kernel can support\n" - "Increase the SPARC_PHYS_BANKS " - "setting (currently %d)\n", - SPARC_PHYS_BANKS); - i = SPARC_PHYS_BANKS-1; - break; - } - - sp_banks[i].base_addr = mlist->start_adr; - sp_banks[i].num_bytes = mlist->num_bytes; - } - - i++; - sp_banks[i].base_addr = 0xdeadbeefbeefdeadUL; - sp_banks[i].num_bytes = 0; - - for (i = 0; sp_banks[i].num_bytes != 0; i++) - sp_banks[i].num_bytes &= PAGE_MASK; -} - static void __init taint_real_pages(void) { - struct sparc_phys_banks saved_sp_banks[SPARC_PHYS_BANKS]; int i; - for (i = 0; i < SPARC_PHYS_BANKS; i++) { - saved_sp_banks[i].base_addr = - sp_banks[i].base_addr; - saved_sp_banks[i].num_bytes = - sp_banks[i].num_bytes; - } - - rescan_sp_banks(); + read_obp_memory("available", &pavail_rescan[0], &pavail_rescan_ents); - /* Find changes discovered in the sp_bank rescan and + /* Find changes discovered in the physmem available rescan and * reserve the lost portions in the bootmem maps. */ - for (i = 0; saved_sp_banks[i].num_bytes; i++) { + for (i = 0; i < pavail_ents; i++) { unsigned long old_start, old_end; - old_start = saved_sp_banks[i].base_addr; + old_start = pavail[i].phys_addr; old_end = old_start + - saved_sp_banks[i].num_bytes; + pavail[i].reg_size; while (old_start < old_end) { int n; - for (n = 0; sp_banks[n].num_bytes; n++) { + for (n = 0; pavail_rescan_ents; n++) { unsigned long new_start, new_end; - new_start = sp_banks[n].base_addr; - new_end = new_start + sp_banks[n].num_bytes; + new_start = pavail_rescan[n].phys_addr; + new_end = new_start + + pavail_rescan[n].reg_size; if (new_start <= old_start && new_end >= (old_start + PAGE_SIZE)) { - set_bit (old_start >> 22, - sparc64_valid_addr_bitmap); + set_bit(old_start >> 22, + sparc64_valid_addr_bitmap); goto do_next_page; } } diff --git a/include/asm-sparc64/openprom.h b/include/asm-sparc64/openprom.h index 0a336901d58..b4959d2b0d9 100644 --- a/include/asm-sparc64/openprom.h +++ b/include/asm-sparc64/openprom.h @@ -186,8 +186,8 @@ struct linux_prom_registers { }; struct linux_prom64_registers { - long phys_addr; - long reg_size; + unsigned long phys_addr; + unsigned long reg_size; }; struct linux_prom_irqs { -- cgit v1.2.3 From 4cb29d18129fb425c6202ab535c3fc1856391b99 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Thu, 29 Sep 2005 18:05:28 -0700 Subject: [SPARC64]: Kill arch/sparc64/prom/memory.c No longer used. Signed-off-by: David S. Miller --- arch/sparc64/prom/Makefile | 2 +- arch/sparc64/prom/init.c | 3 - arch/sparc64/prom/memory.c | 152 -------------------------------------------- include/asm-sparc64/oplib.h | 14 ---- 4 files changed, 1 insertion(+), 170 deletions(-) delete mode 100644 arch/sparc64/prom/memory.c diff --git a/arch/sparc64/prom/Makefile b/arch/sparc64/prom/Makefile index c7898a5ee45..3d33ed27bc2 100644 --- a/arch/sparc64/prom/Makefile +++ b/arch/sparc64/prom/Makefile @@ -6,5 +6,5 @@ EXTRA_AFLAGS := -ansi EXTRA_CFLAGS := -Werror -lib-y := bootstr.o devops.o init.o memory.o misc.o \ +lib-y := bootstr.o devops.o init.o misc.o \ tree.o console.o printf.o p1275.o cif.o diff --git a/arch/sparc64/prom/init.c b/arch/sparc64/prom/init.c index 8b4b622d090..f3cc2d8578b 100644 --- a/arch/sparc64/prom/init.c +++ b/arch/sparc64/prom/init.c @@ -27,7 +27,6 @@ int prom_chosen_node; * failure. It gets passed the pointer to the PROM vector. */ -extern void prom_meminit(void); extern void prom_cif_init(void *, void *); void __init prom_init(void *cif_handler, void *cif_stack) @@ -90,8 +89,6 @@ void __init prom_init(void *cif_handler, void *cif_stack) printk ("PROMLIB: Sun IEEE Boot Prom %s\n", buffer + bufadjust); - prom_meminit(); - /* Initialization successful. */ return; diff --git a/arch/sparc64/prom/memory.c b/arch/sparc64/prom/memory.c deleted file mode 100644 index f4a8143e052..00000000000 --- a/arch/sparc64/prom/memory.c +++ /dev/null @@ -1,152 +0,0 @@ -/* $Id: memory.c,v 1.5 1999/08/31 06:55:04 davem Exp $ - * memory.c: Prom routine for acquiring various bits of information - * about RAM on the machine, both virtual and physical. - * - * Copyright (C) 1995 David S. Miller (davem@caip.rutgers.edu) - * Copyright (C) 1997 Jakub Jelinek (jj@sunsite.mff.cuni.cz) - */ - -#include -#include - -#include -#include - -/* This routine, for consistency, returns the ram parameters in the - * V0 prom memory descriptor format. I choose this format because I - * think it was the easiest to work with. I feel the religious - * arguments now... ;) Also, I return the linked lists sorted to - * prevent paging_init() upset stomach as I have not yet written - * the pepto-bismol kernel module yet. - */ - -struct linux_prom64_registers prom_reg_memlist[64]; -struct linux_prom64_registers prom_reg_tmp[64]; - -struct linux_mlist_p1275 prom_phys_total[64]; -struct linux_mlist_p1275 prom_prom_taken[64]; -struct linux_mlist_p1275 prom_phys_avail[64]; - -struct linux_mlist_p1275 *prom_ptot_ptr = prom_phys_total; -struct linux_mlist_p1275 *prom_ptak_ptr = prom_prom_taken; -struct linux_mlist_p1275 *prom_pavl_ptr = prom_phys_avail; - -struct linux_mem_p1275 prom_memlist; - - -/* Internal Prom library routine to sort a linux_mlist_p1275 memory - * list. Used below in initialization. - */ -static void __init -prom_sortmemlist(struct linux_mlist_p1275 *thislist) -{ - int swapi = 0; - int i, mitr; - unsigned long tmpaddr, tmpsize; - unsigned long lowest; - - for(i=0; thislist[i].theres_more; i++) { - lowest = thislist[i].start_adr; - for(mitr = i+1; thislist[mitr-1].theres_more; mitr++) - if(thislist[mitr].start_adr < lowest) { - lowest = thislist[mitr].start_adr; - swapi = mitr; - } - if(lowest == thislist[i].start_adr) continue; - tmpaddr = thislist[swapi].start_adr; - tmpsize = thislist[swapi].num_bytes; - for(mitr = swapi; mitr > i; mitr--) { - thislist[mitr].start_adr = thislist[mitr-1].start_adr; - thislist[mitr].num_bytes = thislist[mitr-1].num_bytes; - } - thislist[i].start_adr = tmpaddr; - thislist[i].num_bytes = tmpsize; - } -} - -/* Initialize the memory lists based upon the prom version. */ -void __init prom_meminit(void) -{ - int node = 0; - unsigned int iter, num_regs; - - node = prom_finddevice("/memory"); - num_regs = prom_getproperty(node, "available", - (char *) prom_reg_memlist, - sizeof(prom_reg_memlist)); - num_regs = (num_regs/sizeof(struct linux_prom64_registers)); - for(iter=0; iter Date: Thu, 29 Sep 2005 18:50:34 -0700 Subject: [SPARC64]: Fix several bugs in flush_ptrace_access(). 1) Use cpudata cache line sizes, not magic constants. 2) Align start address in cheetah case so we do not get unaligned address traps. (pgrep was good at triggering this, via /proc/${pid}/cmdline accesses) Signed-off-by: David S. Miller --- arch/sparc64/kernel/ptrace.c | 14 +++++++++++--- 1 file changed, 11 insertions(+), 3 deletions(-) diff --git a/arch/sparc64/kernel/ptrace.c b/arch/sparc64/kernel/ptrace.c index 5efbff90d66..774ecbb8a03 100644 --- a/arch/sparc64/kernel/ptrace.c +++ b/arch/sparc64/kernel/ptrace.c @@ -31,6 +31,7 @@ #include #include #include +#include /* Returning from ptrace is a bit tricky because the syscall return * low level code assumes any value returned which is negative and @@ -132,12 +133,16 @@ void flush_ptrace_access(struct vm_area_struct *vma, struct page *page, if ((uaddr ^ (unsigned long) kaddr) & (1UL << 13)) { unsigned long start = __pa(kaddr); unsigned long end = start + len; + unsigned long dcache_line_size; + + dcache_line_size = local_cpu_data().dcache_line_size; if (tlb_type == spitfire) { - for (; start < end; start += 32) + for (; start < end; start += dcache_line_size) spitfire_put_dcache_tag(start & 0x3fe0, 0x0); } else { - for (; start < end; start += 32) + start &= ~(dcache_line_size - 1); + for (; start < end; start += dcache_line_size) __asm__ __volatile__( "stxa %%g0, [%0] %1\n\t" "membar #Sync" @@ -150,8 +155,11 @@ void flush_ptrace_access(struct vm_area_struct *vma, struct page *page, if (write && tlb_type == spitfire) { unsigned long start = (unsigned long) kaddr; unsigned long end = start + len; + unsigned long icache_line_size; + + icache_line_size = local_cpu_data().icache_line_size; - for (; start < end; start += 32) + for (; start < end; start += icache_line_size) flushi(start); } } -- cgit v1.2.3 From 017fb98e70351e9fb5635c299c4d1c50e2f8b823 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Thu, 29 Sep 2005 19:26:51 -0700 Subject: [RADEON]: Fix unaligned I/O port access during probe. The driver does a readl() on DEVICE_ID which is 2-byte aligned and 2-bytes in size. It's doing this read just to flush write buffers. Create IN16() and OUT16() macros, and use the former to do this I/O load. Signed-off-by: David S. Miller --- drivers/video/aty/radeon_base.c | 2 +- drivers/video/aty/radeonfb.h | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/video/aty/radeon_base.c b/drivers/video/aty/radeon_base.c index 046b4786026..8a24a66d9ba 100644 --- a/drivers/video/aty/radeon_base.c +++ b/drivers/video/aty/radeon_base.c @@ -475,7 +475,7 @@ static int __devinit radeon_probe_pll_params(struct radeonfb_info *rinfo) */ /* Flush PCI buffers ? */ - tmp = INREG(DEVICE_ID); + tmp = INREG16(DEVICE_ID); local_irq_disable(); diff --git a/drivers/video/aty/radeonfb.h b/drivers/video/aty/radeonfb.h index 659bc9f6224..01b8b2f7851 100644 --- a/drivers/video/aty/radeonfb.h +++ b/drivers/video/aty/radeonfb.h @@ -395,6 +395,8 @@ static inline void _radeon_msleep(struct radeonfb_info *rinfo, unsigned long ms) #define INREG8(addr) readb((rinfo->mmio_base)+addr) #define OUTREG8(addr,val) writeb(val, (rinfo->mmio_base)+addr) +#define INREG16(addr) readw((rinfo->mmio_base)+addr) +#define OUTREG16(addr,val) writew(val, (rinfo->mmio_base)+addr) #define INREG(addr) readl((rinfo->mmio_base)+addr) #define OUTREG(addr,val) writel(val, (rinfo->mmio_base)+addr) -- cgit v1.2.3 From 9d30c1718b8baf9a3bb1b81d78afc1e667863477 Mon Sep 17 00:00:00 2001 From: Horms Date: Thu, 29 Sep 2005 19:47:06 -0700 Subject: [IPVS]: Add netdev and me as maintainer contacts Signed-off-by: Horms Signed-off-by: David S. Miller --- MAINTAINERS | 3 +++ 1 file changed, 3 insertions(+) diff --git a/MAINTAINERS b/MAINTAINERS index c1bc9a86a99..f3d9adec5aa 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -1743,8 +1743,11 @@ S: Maintained IPVS P: Wensong Zhang M: wensong@linux-vs.org +P: Simon Horman +M: horms@verge.net.au P: Julian Anastasov M: ja@ssi.bg +L: netdev@vger.kernel.org S: Maintained NFS CLIENT -- cgit v1.2.3 From a4199b0b9aa540a27935251de788cd0f5f5a87aa Mon Sep 17 00:00:00 2001 From: Al Viro Date: Thu, 29 Sep 2005 19:49:17 -0700 Subject: [CASSINI]: sparse annotations and fixes - __user annotations - NULL noise removal - C99 initializers - s/u32/pm_message_t/ in ->suspend() - removal of bogus casts in iounmap() arguments - if_mii() instead of open-coded variant Remains to be done: ethtool conversion. Signed-off-by: Al Viro Signed-off-by: David S. Miller --- drivers/net/cassini.c | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/drivers/net/cassini.c b/drivers/net/cassini.c index 69cb368247e..45831fb377a 100644 --- a/drivers/net/cassini.c +++ b/drivers/net/cassini.c @@ -3244,7 +3244,7 @@ static int cas_get_vpd_info(struct cas *cp, unsigned char *dev_addr, goto use_random_mac_addr; /* search for beginning of vpd */ - base = 0; + base = NULL; for (i = 2; i < EXPANSION_ROM_SIZE; i++) { /* check for PCIR */ if ((readb(p + i + 0) == 0x50) && @@ -4564,7 +4564,7 @@ static void cas_set_multicast(struct net_device *dev) /* Eventually add support for changing the advertisement * on autoneg. */ -static int cas_ethtool_ioctl(struct net_device *dev, void *ep_user) +static int cas_ethtool_ioctl(struct net_device *dev, void __user *ep_user) { struct cas *cp = netdev_priv(dev); u16 bmcr; @@ -4578,7 +4578,7 @@ static int cas_ethtool_ioctl(struct net_device *dev, void *ep_user) switch(ecmd.cmd) { case ETHTOOL_GDRVINFO: { - struct ethtool_drvinfo info = { cmd: ETHTOOL_GDRVINFO }; + struct ethtool_drvinfo info = { .cmd = ETHTOOL_GDRVINFO }; strncpy(info.driver, DRV_MODULE_NAME, ETHTOOL_BUSINFO_LEN); @@ -4738,7 +4738,7 @@ static int cas_ethtool_ioctl(struct net_device *dev, void *ep_user) /* get link status */ case ETHTOOL_GLINK: { - struct ethtool_value edata = { cmd: ETHTOOL_GLINK }; + struct ethtool_value edata = { .cmd = ETHTOOL_GLINK }; edata.data = (cp->lstate == link_up); if (copy_to_user(ep_user, &edata, sizeof(edata))) @@ -4748,7 +4748,7 @@ static int cas_ethtool_ioctl(struct net_device *dev, void *ep_user) /* get message-level */ case ETHTOOL_GMSGLVL: { - struct ethtool_value edata = { cmd: ETHTOOL_GMSGLVL }; + struct ethtool_value edata = { .cmd = ETHTOOL_GMSGLVL }; edata.data = cp->msg_enable; if (copy_to_user(ep_user, &edata, sizeof(edata))) @@ -4874,7 +4874,7 @@ static int cas_ethtool_ioctl(struct net_device *dev, void *ep_user) static int cas_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd) { struct cas *cp = netdev_priv(dev); - struct mii_ioctl_data *data = (struct mii_ioctl_data *)&ifr->ifr_data; + struct mii_ioctl_data *data = if_mii(ifr); unsigned long flags; int rc = -EOPNOTSUPP; @@ -5168,7 +5168,7 @@ err_out_iounmap: cas_shutdown(cp); up(&cp->pm_sem); - iounmap((void *) cp->regs); + iounmap(cp->regs); err_out_free_res: @@ -5216,7 +5216,7 @@ static void __devexit cas_remove_one(struct pci_dev *pdev) #endif pci_free_consistent(pdev, sizeof(struct cas_init_block), cp->init_block, cp->block_dvma); - iounmap((void *) cp->regs); + iounmap(cp->regs); free_netdev(dev); pci_release_regions(pdev); pci_disable_device(pdev); @@ -5224,7 +5224,7 @@ static void __devexit cas_remove_one(struct pci_dev *pdev) } #ifdef CONFIG_PM -static int cas_suspend(struct pci_dev *pdev, u32 state) +static int cas_suspend(struct pci_dev *pdev, pm_message_t state) { struct net_device *dev = pci_get_drvdata(pdev); struct cas *cp = netdev_priv(dev); -- cgit v1.2.3 From 481467d6fa4489aa42321a067e78bad26349488f Mon Sep 17 00:00:00 2001 From: Catalin Marinas Date: Fri, 30 Sep 2005 16:07:04 +0100 Subject: [ARM] 2939/1: Fix compilation error in arch/arm/mm/flush.c Patch from Catalin Marinas When CONFIG_CPU_CACHE_VIPT is defined, the flush_pfn_alias() function is implicitely declared and it later conflicts with its actual definition. This patch moves the function definition to the beginning of the file. Signed-off-by: Catalin Marinas Signed-off-by: Russell King --- arch/arm/mm/flush.c | 36 ++++++++++++++++++------------------ 1 file changed, 18 insertions(+), 18 deletions(-) diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c index b0208c99257..c9a03981b78 100644 --- a/arch/arm/mm/flush.c +++ b/arch/arm/mm/flush.c @@ -17,6 +17,24 @@ #ifdef CONFIG_CPU_CACHE_VIPT +#define ALIAS_FLUSH_START 0xffff4000 + +#define TOP_PTE(x) pte_offset_kernel(top_pmd, x) + +static void flush_pfn_alias(unsigned long pfn, unsigned long vaddr) +{ + unsigned long to = ALIAS_FLUSH_START + (CACHE_COLOUR(vaddr) << PAGE_SHIFT); + + set_pte(TOP_PTE(to), pfn_pte(pfn, PAGE_KERNEL)); + flush_tlb_kernel_page(to); + + asm( "mcrr p15, 0, %1, %0, c14\n" + " mcrr p15, 0, %1, %0, c5\n" + : + : "r" (to), "r" (to + PAGE_SIZE - L1_CACHE_BYTES) + : "cc"); +} + void flush_cache_mm(struct mm_struct *mm) { if (cache_is_vivt()) { @@ -67,24 +85,6 @@ void flush_cache_page(struct vm_area_struct *vma, unsigned long user_addr, unsig if (cache_is_vipt_aliasing()) flush_pfn_alias(pfn, user_addr); } - -#define ALIAS_FLUSH_START 0xffff4000 - -#define TOP_PTE(x) pte_offset_kernel(top_pmd, x) - -static void flush_pfn_alias(unsigned long pfn, unsigned long vaddr) -{ - unsigned long to = ALIAS_FLUSH_START + (CACHE_COLOUR(vaddr) << PAGE_SHIFT); - - set_pte(TOP_PTE(to), pfn_pte(pfn, PAGE_KERNEL)); - flush_tlb_kernel_page(to); - - asm( "mcrr p15, 0, %1, %0, c14\n" - " mcrr p15, 0, %1, %0, c5\n" - : - : "r" (to), "r" (to + PAGE_SIZE - L1_CACHE_BYTES) - : "cc"); -} #else #define flush_pfn_alias(pfn,vaddr) do { } while (0) #endif -- cgit v1.2.3 From a06f5466c4576dcbf838a50a87903b0082774da7 Mon Sep 17 00:00:00 2001 From: Catalin Marinas Date: Fri, 30 Sep 2005 16:07:05 +0100 Subject: [ARM] 2942/1: Fix the warning in arch/arm/common/gic.c Patch from Catalin Marinas The warning is caused by the gic_set_cpu() function being defined but not used if CONFIG_SMP is not defined. Signed-off-by: Catalin Marinas Signed-off-by: Russell King --- arch/arm/common/gic.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/arch/arm/common/gic.c b/arch/arm/common/gic.c index d7499071755..c02dc8116a1 100644 --- a/arch/arm/common/gic.c +++ b/arch/arm/common/gic.c @@ -68,6 +68,7 @@ static void gic_unmask_irq(unsigned int irq) writel(mask, gic_dist_base + GIC_DIST_ENABLE_SET + (irq / 32) * 4); } +#ifdef CONFIG_SMP static void gic_set_cpu(struct irqdesc *desc, unsigned int irq, unsigned int cpu) { void __iomem *reg = gic_dist_base + GIC_DIST_TARGET + (irq & ~3); @@ -78,6 +79,7 @@ static void gic_set_cpu(struct irqdesc *desc, unsigned int irq, unsigned int cpu val |= 1 << (cpu + shift); writel(val, reg); } +#endif static struct irqchip gic_chip = { .ack = gic_ack_irq, -- cgit v1.2.3 From 217874feed0d3a6543a6b7127782f4a08bffd731 Mon Sep 17 00:00:00 2001 From: Gen FUKATSU Date: Fri, 30 Sep 2005 16:09:17 +0100 Subject: [ARM] 2940/1: Fix BTB entry flush in arch/arm/mm/cache-v6.S Patch from Gen FUKATSU Invalidate BTB entry instruction flushes two instruction at a time. Therefore this instruction should be done four times after invalidate instruction cache line. Signed-off-by: Gen Fukatsu Signed-off-by: Catalin Marinas Signed-off-by: Russell King --- arch/arm/mm/cache-v6.S | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/arch/arm/mm/cache-v6.S b/arch/arm/mm/cache-v6.S index 85c10a71e7c..72966d90e95 100644 --- a/arch/arm/mm/cache-v6.S +++ b/arch/arm/mm/cache-v6.S @@ -18,6 +18,7 @@ #define HARVARD_CACHE #define CACHE_LINE_SIZE 32 #define D_CACHE_LINE_SIZE 32 +#define BTB_FLUSH_SIZE 8 /* * v6_flush_cache_all() @@ -98,7 +99,13 @@ ENTRY(v6_coherent_user_range) mcr p15, 0, r0, c7, c5, 1 @ invalidate I line #endif mcr p15, 0, r0, c7, c5, 7 @ invalidate BTB entry - add r0, r0, #CACHE_LINE_SIZE + add r0, r0, #BTB_FLUSH_SIZE + mcr p15, 0, r0, c7, c5, 7 @ invalidate BTB entry + add r0, r0, #BTB_FLUSH_SIZE + mcr p15, 0, r0, c7, c5, 7 @ invalidate BTB entry + add r0, r0, #BTB_FLUSH_SIZE + mcr p15, 0, r0, c7, c5, 7 @ invalidate BTB entry + add r0, r0, #BTB_FLUSH_SIZE cmp r0, r1 blo 1b #ifdef HARVARD_CACHE -- cgit v1.2.3 From 192eaa28ba7b44485e521df7ba7a2ccbc4cc4d13 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Fri, 30 Sep 2005 03:15:08 +0100 Subject: [PATCH] missing ERR_PTR in 9fs Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- fs/9p/vfs_super.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/fs/9p/vfs_super.c b/fs/9p/vfs_super.c index 0957f4da91d..82c5b008407 100644 --- a/fs/9p/vfs_super.c +++ b/fs/9p/vfs_super.c @@ -129,7 +129,7 @@ static struct super_block *v9fs_get_sb(struct file_system_type if ((newfid = v9fs_session_init(v9ses, dev_name, data)) < 0) { dprintk(DEBUG_ERROR, "problem initiating session\n"); - return newfid; + return ERR_PTR(newfid); } sb = sget(fs_type, NULL, v9fs_set_super, v9ses); -- cgit v1.2.3 From 74ba1fd96666170338dc732480b35b7a83cd164b Mon Sep 17 00:00:00 2001 From: Al Viro Date: Fri, 30 Sep 2005 03:16:43 +0100 Subject: [PATCH] useless linux/irq.h includes (arch/um) Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- arch/um/drivers/port_kern.c | 1 - arch/um/kernel/irq.c | 1 - 2 files changed, 2 deletions(-) diff --git a/arch/um/drivers/port_kern.c b/arch/um/drivers/port_kern.c index c41efd207fc..189839e4f1d 100644 --- a/arch/um/drivers/port_kern.c +++ b/arch/um/drivers/port_kern.c @@ -7,7 +7,6 @@ #include "linux/sched.h" #include "linux/slab.h" #include "linux/interrupt.h" -#include "linux/irq.h" #include "linux/spinlock.h" #include "linux/errno.h" #include "asm/atomic.h" diff --git a/arch/um/kernel/irq.c b/arch/um/kernel/irq.c index dcd81497199..bbf94bf2921 100644 --- a/arch/um/kernel/irq.c +++ b/arch/um/kernel/irq.c @@ -9,7 +9,6 @@ #include "linux/kernel.h" #include "linux/module.h" #include "linux/smp.h" -#include "linux/irq.h" #include "linux/kernel_stat.h" #include "linux/interrupt.h" #include "linux/random.h" -- cgit v1.2.3 From 46d7031ecb8a8360b0022abd8014f38cc1197166 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Fri, 30 Sep 2005 03:21:45 +0100 Subject: [PATCH] cassini annotations and fixes - __user annotations - NULL noise removal - C99 initializers - s/u32/pm_message_t/ in ->suspend() - removal of bogus casts in iounmap() arguments - if_mii() instead of open-coded variant Remains to be done: ethtool conversion. Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- drivers/net/cassini.c | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/drivers/net/cassini.c b/drivers/net/cassini.c index 69cb368247e..45831fb377a 100644 --- a/drivers/net/cassini.c +++ b/drivers/net/cassini.c @@ -3244,7 +3244,7 @@ static int cas_get_vpd_info(struct cas *cp, unsigned char *dev_addr, goto use_random_mac_addr; /* search for beginning of vpd */ - base = 0; + base = NULL; for (i = 2; i < EXPANSION_ROM_SIZE; i++) { /* check for PCIR */ if ((readb(p + i + 0) == 0x50) && @@ -4564,7 +4564,7 @@ static void cas_set_multicast(struct net_device *dev) /* Eventually add support for changing the advertisement * on autoneg. */ -static int cas_ethtool_ioctl(struct net_device *dev, void *ep_user) +static int cas_ethtool_ioctl(struct net_device *dev, void __user *ep_user) { struct cas *cp = netdev_priv(dev); u16 bmcr; @@ -4578,7 +4578,7 @@ static int cas_ethtool_ioctl(struct net_device *dev, void *ep_user) switch(ecmd.cmd) { case ETHTOOL_GDRVINFO: { - struct ethtool_drvinfo info = { cmd: ETHTOOL_GDRVINFO }; + struct ethtool_drvinfo info = { .cmd = ETHTOOL_GDRVINFO }; strncpy(info.driver, DRV_MODULE_NAME, ETHTOOL_BUSINFO_LEN); @@ -4738,7 +4738,7 @@ static int cas_ethtool_ioctl(struct net_device *dev, void *ep_user) /* get link status */ case ETHTOOL_GLINK: { - struct ethtool_value edata = { cmd: ETHTOOL_GLINK }; + struct ethtool_value edata = { .cmd = ETHTOOL_GLINK }; edata.data = (cp->lstate == link_up); if (copy_to_user(ep_user, &edata, sizeof(edata))) @@ -4748,7 +4748,7 @@ static int cas_ethtool_ioctl(struct net_device *dev, void *ep_user) /* get message-level */ case ETHTOOL_GMSGLVL: { - struct ethtool_value edata = { cmd: ETHTOOL_GMSGLVL }; + struct ethtool_value edata = { .cmd = ETHTOOL_GMSGLVL }; edata.data = cp->msg_enable; if (copy_to_user(ep_user, &edata, sizeof(edata))) @@ -4874,7 +4874,7 @@ static int cas_ethtool_ioctl(struct net_device *dev, void *ep_user) static int cas_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd) { struct cas *cp = netdev_priv(dev); - struct mii_ioctl_data *data = (struct mii_ioctl_data *)&ifr->ifr_data; + struct mii_ioctl_data *data = if_mii(ifr); unsigned long flags; int rc = -EOPNOTSUPP; @@ -5168,7 +5168,7 @@ err_out_iounmap: cas_shutdown(cp); up(&cp->pm_sem); - iounmap((void *) cp->regs); + iounmap(cp->regs); err_out_free_res: @@ -5216,7 +5216,7 @@ static void __devexit cas_remove_one(struct pci_dev *pdev) #endif pci_free_consistent(pdev, sizeof(struct cas_init_block), cp->init_block, cp->block_dvma); - iounmap((void *) cp->regs); + iounmap(cp->regs); free_netdev(dev); pci_release_regions(pdev); pci_disable_device(pdev); @@ -5224,7 +5224,7 @@ static void __devexit cas_remove_one(struct pci_dev *pdev) } #ifdef CONFIG_PM -static int cas_suspend(struct pci_dev *pdev, u32 state) +static int cas_suspend(struct pci_dev *pdev, pm_message_t state) { struct net_device *dev = pci_get_drvdata(pdev); struct cas *cp = netdev_priv(dev); -- cgit v1.2.3 From eacaa1f5aa4a41a48349f55abcd9258506943e76 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Fri, 30 Sep 2005 03:26:43 +0100 Subject: [PATCH] cpuset crapectomy Switched cpuset_common_file_read() to simple_read_from_buffer(), killed a bunch of useless (and not quite correct - e.g. min(size_t,ssize_t)) code. Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- kernel/cpuset.c | 12 +----------- 1 file changed, 1 insertion(+), 11 deletions(-) diff --git a/kernel/cpuset.c b/kernel/cpuset.c index 6a6e87b2f2f..45a5719a010 100644 --- a/kernel/cpuset.c +++ b/kernel/cpuset.c @@ -968,8 +968,6 @@ static ssize_t cpuset_common_file_read(struct file *file, char __user *buf, char *page; ssize_t retval = 0; char *s; - char *start; - ssize_t n; if (!(page = (char *)__get_free_page(GFP_KERNEL))) return -ENOMEM; @@ -999,15 +997,7 @@ static ssize_t cpuset_common_file_read(struct file *file, char __user *buf, *s++ = '\n'; *s = '\0'; - start = page + *ppos; - n = s - start; - - /* Do nothing if *ppos is at the eof or beyond the eof. */ - if (n <= 0) - goto out; - - retval = n - copy_to_user(buf, start, min(n, nbytes)); - *ppos += retval; + retval = simple_read_from_buffer(buf, nbytes, ppos, page, s - page); out: free_page((unsigned long)page); return retval; -- cgit v1.2.3 From 4735885701d7c24ed54f35f5102d32b3aabee55e Mon Sep 17 00:00:00 2001 From: Al Viro Date: Fri, 30 Sep 2005 03:29:05 +0100 Subject: [PATCH] uml get_user() NULL noise removal Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- include/asm-um/uaccess.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/asm-um/uaccess.h b/include/asm-um/uaccess.h index 801710d00a4..2ee028b8de9 100644 --- a/include/asm-um/uaccess.h +++ b/include/asm-um/uaccess.h @@ -44,7 +44,7 @@ const __typeof__(ptr) __private_ptr = ptr; \ __typeof__(*(__private_ptr)) __private_val; \ int __private_ret = -EFAULT; \ - (x) = 0; \ + (x) = (__typeof__(*(__private_ptr)))0; \ if (__copy_from_user(&__private_val, (__private_ptr), \ sizeof(*(__private_ptr))) == 0) {\ (x) = (__typeof__(*(__private_ptr))) __private_val; \ -- cgit v1.2.3 From c215a16a4ad620b612b51495cbb99dbbb59bb585 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Fri, 30 Sep 2005 03:36:50 +0100 Subject: [PATCH] bogus BUILD_BUG_ON() in bpa_iommu BUILD_BUG_ON(1) is asking for trouble (and getting it) when used in that manner - dead code elimination happens after we parse it and invalid type is invalid type, dead code or not. It might be version-dependent, but at least 4.0.1 refuses to accept that. Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- arch/ppc64/kernel/bpa_iommu.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/arch/ppc64/kernel/bpa_iommu.c b/arch/ppc64/kernel/bpa_iommu.c index f33a7bccb0d..507eb9d0223 100644 --- a/arch/ppc64/kernel/bpa_iommu.c +++ b/arch/ppc64/kernel/bpa_iommu.c @@ -99,7 +99,11 @@ get_iost_entry(unsigned long iopt_base, unsigned long io_address, unsigned page_ break; default: /* not a known compile time constant */ - BUILD_BUG_ON(1); + { + /* BUILD_BUG_ON() is not usable here */ + extern void __get_iost_entry_bad_page_size(void); + __get_iost_entry_bad_page_size(); + } break; } -- cgit v1.2.3 From 66df3bbf0701b7408a1067c4b819aceee2686bba Mon Sep 17 00:00:00 2001 From: Al Viro Date: Fri, 30 Sep 2005 04:19:43 +0100 Subject: [PATCH] volatile unsigned short f(...) doesn't make sense Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- drivers/net/bmac.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/bmac.c b/drivers/net/bmac.c index 8dc657fc8af..60dba4a1ca5 100644 --- a/drivers/net/bmac.c +++ b/drivers/net/bmac.c @@ -218,7 +218,7 @@ void bmwrite(struct net_device *dev, unsigned long reg_offset, unsigned data ) static inline -volatile unsigned short bmread(struct net_device *dev, unsigned long reg_offset ) +unsigned short bmread(struct net_device *dev, unsigned long reg_offset ) { return in_le16((void __iomem *)dev->base_addr + reg_offset); } -- cgit v1.2.3 From a3ca066efb18524bf3f07137a8f8ff434022c4f2 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Fri, 30 Sep 2005 04:20:57 +0100 Subject: [PATCH] missing qualifiers in readb() et.al. on ppc Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- include/asm-ppc/io.h | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/include/asm-ppc/io.h b/include/asm-ppc/io.h index 7eb7cf6360b..94d83998a75 100644 --- a/include/asm-ppc/io.h +++ b/include/asm-ppc/io.h @@ -56,7 +56,7 @@ extern unsigned long pci_dram_offset; * is actually performed (i.e. the data has come back) before we start * executing any following instructions. */ -extern inline int in_8(volatile unsigned char __iomem *addr) +extern inline int in_8(const volatile unsigned char __iomem *addr) { int ret; @@ -72,7 +72,7 @@ extern inline void out_8(volatile unsigned char __iomem *addr, int val) __asm__ __volatile__("stb%U0%X0 %1,%0; eieio" : "=m" (*addr) : "r" (val)); } -extern inline int in_le16(volatile unsigned short __iomem *addr) +extern inline int in_le16(const volatile unsigned short __iomem *addr) { int ret; @@ -83,7 +83,7 @@ extern inline int in_le16(volatile unsigned short __iomem *addr) return ret; } -extern inline int in_be16(volatile unsigned short __iomem *addr) +extern inline int in_be16(const volatile unsigned short __iomem *addr) { int ret; @@ -104,7 +104,7 @@ extern inline void out_be16(volatile unsigned short __iomem *addr, int val) __asm__ __volatile__("sth%U0%X0 %1,%0; eieio" : "=m" (*addr) : "r" (val)); } -extern inline unsigned in_le32(volatile unsigned __iomem *addr) +extern inline unsigned in_le32(const volatile unsigned __iomem *addr) { unsigned ret; @@ -115,7 +115,7 @@ extern inline unsigned in_le32(volatile unsigned __iomem *addr) return ret; } -extern inline unsigned in_be32(volatile unsigned __iomem *addr) +extern inline unsigned in_be32(const volatile unsigned __iomem *addr) { unsigned ret; @@ -139,7 +139,7 @@ extern inline void out_be32(volatile unsigned __iomem *addr, int val) #define readb(addr) in_8((volatile u8 *)(addr)) #define writeb(b,addr) out_8((volatile u8 *)(addr), (b)) #else -static inline __u8 readb(volatile void __iomem *addr) +static inline __u8 readb(const volatile void __iomem *addr) { return in_8(addr); } @@ -150,11 +150,11 @@ static inline void writeb(__u8 b, volatile void __iomem *addr) #endif #if defined(CONFIG_APUS) -static inline __u16 readw(volatile void __iomem *addr) +static inline __u16 readw(const volatile void __iomem *addr) { return *(__force volatile __u16 *)(addr); } -static inline __u32 readl(volatile void __iomem *addr) +static inline __u32 readl(const volatile void __iomem *addr) { return *(__force volatile __u32 *)(addr); } @@ -173,11 +173,11 @@ static inline void writel(__u32 b, volatile void __iomem *addr) #define writew(b,addr) out_le16((volatile u16 *)(addr),(b)) #define writel(b,addr) out_le32((volatile u32 *)(addr),(b)) #else -static inline __u16 readw(volatile void __iomem *addr) +static inline __u16 readw(const volatile void __iomem *addr) { return in_le16(addr); } -static inline __u32 readl(volatile void __iomem *addr) +static inline __u32 readl(const volatile void __iomem *addr) { return in_le32(addr); } -- cgit v1.2.3 From 794fb8370db3d5f26592b9b45d69aeca2f583efb Mon Sep 17 00:00:00 2001 From: Al Viro Date: Fri, 30 Sep 2005 05:09:34 +0100 Subject: [PATCH] useless includes of linux/irq.h (arch/ppc) Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- arch/ppc/platforms/4xx/bamboo.c | 1 - arch/ppc/platforms/4xx/ebony.c | 1 - arch/ppc/platforms/4xx/luan.c | 1 - arch/ppc/platforms/4xx/ocotea.c | 1 - arch/ppc/platforms/83xx/mpc834x_sys.c | 1 - arch/ppc/platforms/85xx/mpc8540_ads.c | 1 - arch/ppc/platforms/85xx/mpc8560_ads.c | 1 - arch/ppc/platforms/85xx/mpc85xx_ads_common.c | 1 - arch/ppc/platforms/85xx/mpc85xx_cds_common.c | 1 - arch/ppc/platforms/85xx/sbc8560.c | 1 - arch/ppc/platforms/85xx/sbc85xx.c | 1 - arch/ppc/platforms/85xx/stx_gp3.c | 1 - arch/ppc/platforms/chestnut.c | 1 - arch/ppc/platforms/chrp_setup.c | 1 - arch/ppc/platforms/gemini_setup.c | 1 - arch/ppc/platforms/mvme5100.c | 1 - arch/ppc/platforms/pmac_setup.c | 1 - arch/ppc/platforms/powerpmc250.c | 1 - arch/ppc/platforms/pplus.c | 1 - arch/ppc/platforms/prpmc750.c | 1 - arch/ppc/platforms/prpmc800.c | 1 - arch/ppc/platforms/radstone_ppc7d.c | 2 -- arch/ppc/platforms/sandpoint.c | 1 - arch/ppc/syslib/open_pic.c | 1 - arch/ppc/syslib/open_pic2.c | 1 - arch/ppc/syslib/ppc4xx_setup.c | 1 - 26 files changed, 27 deletions(-) diff --git a/arch/ppc/platforms/4xx/bamboo.c b/arch/ppc/platforms/4xx/bamboo.c index ac391d463d7..78a403b48db 100644 --- a/arch/ppc/platforms/4xx/bamboo.c +++ b/arch/ppc/platforms/4xx/bamboo.c @@ -27,7 +27,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/4xx/ebony.c b/arch/ppc/platforms/4xx/ebony.c index d6b2b1965dc..27b778ab903 100644 --- a/arch/ppc/platforms/4xx/ebony.c +++ b/arch/ppc/platforms/4xx/ebony.c @@ -30,7 +30,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/4xx/luan.c b/arch/ppc/platforms/4xx/luan.c index a38e6f9ef85..16d953bda22 100644 --- a/arch/ppc/platforms/4xx/luan.c +++ b/arch/ppc/platforms/4xx/luan.c @@ -28,7 +28,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/4xx/ocotea.c b/arch/ppc/platforms/4xx/ocotea.c index 80028df1b44..506949c5dd2 100644 --- a/arch/ppc/platforms/4xx/ocotea.c +++ b/arch/ppc/platforms/4xx/ocotea.c @@ -28,7 +28,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/83xx/mpc834x_sys.c b/arch/ppc/platforms/83xx/mpc834x_sys.c index b38a851a64e..79b3f533d0a 100644 --- a/arch/ppc/platforms/83xx/mpc834x_sys.c +++ b/arch/ppc/platforms/83xx/mpc834x_sys.c @@ -24,7 +24,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/85xx/mpc8540_ads.c b/arch/ppc/platforms/85xx/mpc8540_ads.c index f761fdf160d..7dc8a68acfd 100644 --- a/arch/ppc/platforms/85xx/mpc8540_ads.c +++ b/arch/ppc/platforms/85xx/mpc8540_ads.c @@ -24,7 +24,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/85xx/mpc8560_ads.c b/arch/ppc/platforms/85xx/mpc8560_ads.c index f2748c88665..8841fd7da6e 100644 --- a/arch/ppc/platforms/85xx/mpc8560_ads.c +++ b/arch/ppc/platforms/85xx/mpc8560_ads.c @@ -24,7 +24,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/85xx/mpc85xx_ads_common.c b/arch/ppc/platforms/85xx/mpc85xx_ads_common.c index 18e952d1767..bd3ac013675 100644 --- a/arch/ppc/platforms/85xx/mpc85xx_ads_common.c +++ b/arch/ppc/platforms/85xx/mpc85xx_ads_common.c @@ -24,7 +24,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/85xx/mpc85xx_cds_common.c b/arch/ppc/platforms/85xx/mpc85xx_cds_common.c index 6267b294f70..9f9039498ae 100644 --- a/arch/ppc/platforms/85xx/mpc85xx_cds_common.c +++ b/arch/ppc/platforms/85xx/mpc85xx_cds_common.c @@ -24,7 +24,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/85xx/sbc8560.c b/arch/ppc/platforms/85xx/sbc8560.c index 165df94d4aa..c76760a781c 100644 --- a/arch/ppc/platforms/85xx/sbc8560.c +++ b/arch/ppc/platforms/85xx/sbc8560.c @@ -24,7 +24,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/85xx/sbc85xx.c b/arch/ppc/platforms/85xx/sbc85xx.c index 4f6d1ddd6fb..c02f110219f 100644 --- a/arch/ppc/platforms/85xx/sbc85xx.c +++ b/arch/ppc/platforms/85xx/sbc85xx.c @@ -23,7 +23,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/85xx/stx_gp3.c b/arch/ppc/platforms/85xx/stx_gp3.c index c99b365d611..20940f4044f 100644 --- a/arch/ppc/platforms/85xx/stx_gp3.c +++ b/arch/ppc/platforms/85xx/stx_gp3.c @@ -30,7 +30,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/chestnut.c b/arch/ppc/platforms/chestnut.c index 7786818bd9d..df6ff98c023 100644 --- a/arch/ppc/platforms/chestnut.c +++ b/arch/ppc/platforms/chestnut.c @@ -35,7 +35,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/chrp_setup.c b/arch/ppc/platforms/chrp_setup.c index 57f29ab29bd..66346f0de7e 100644 --- a/arch/ppc/platforms/chrp_setup.c +++ b/arch/ppc/platforms/chrp_setup.c @@ -32,7 +32,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/gemini_setup.c b/arch/ppc/platforms/gemini_setup.c index e391e52383c..3a5ff9fb71d 100644 --- a/arch/ppc/platforms/gemini_setup.c +++ b/arch/ppc/platforms/gemini_setup.c @@ -21,7 +21,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/mvme5100.c b/arch/ppc/platforms/mvme5100.c index b292b44b760..ce2ce88c803 100644 --- a/arch/ppc/platforms/mvme5100.c +++ b/arch/ppc/platforms/mvme5100.c @@ -20,7 +20,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/pmac_setup.c b/arch/ppc/platforms/pmac_setup.c index 4c56a4734ae..d6356f480d9 100644 --- a/arch/ppc/platforms/pmac_setup.c +++ b/arch/ppc/platforms/pmac_setup.c @@ -48,7 +48,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/powerpmc250.c b/arch/ppc/platforms/powerpmc250.c index 0abe15159e6..e6b520e6e13 100644 --- a/arch/ppc/platforms/powerpmc250.c +++ b/arch/ppc/platforms/powerpmc250.c @@ -26,7 +26,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/pplus.c b/arch/ppc/platforms/pplus.c index 65705c91179..e70aae20d6f 100644 --- a/arch/ppc/platforms/pplus.c +++ b/arch/ppc/platforms/pplus.c @@ -22,7 +22,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/prpmc750.c b/arch/ppc/platforms/prpmc750.c index 24ae1caafc6..0bb14a5e824 100644 --- a/arch/ppc/platforms/prpmc750.c +++ b/arch/ppc/platforms/prpmc750.c @@ -24,7 +24,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/prpmc800.c b/arch/ppc/platforms/prpmc800.c index 8b09fa69b35..de7baefacd3 100644 --- a/arch/ppc/platforms/prpmc800.c +++ b/arch/ppc/platforms/prpmc800.c @@ -22,7 +22,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/platforms/radstone_ppc7d.c b/arch/ppc/platforms/radstone_ppc7d.c index c30607a972d..0376c8cff5d 100644 --- a/arch/ppc/platforms/radstone_ppc7d.c +++ b/arch/ppc/platforms/radstone_ppc7d.c @@ -32,7 +32,6 @@ #include #include #include -#include #include #include #include @@ -59,7 +58,6 @@ #include #include #include -#include #include "radstone_ppc7d.h" diff --git a/arch/ppc/platforms/sandpoint.c b/arch/ppc/platforms/sandpoint.c index 21e31346b12..5232283c197 100644 --- a/arch/ppc/platforms/sandpoint.c +++ b/arch/ppc/platforms/sandpoint.c @@ -74,7 +74,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/syslib/open_pic.c b/arch/ppc/syslib/open_pic.c index 53da58523e3..1cf5de21a3f 100644 --- a/arch/ppc/syslib/open_pic.c +++ b/arch/ppc/syslib/open_pic.c @@ -13,7 +13,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/syslib/open_pic2.c b/arch/ppc/syslib/open_pic2.c index 9a7e8748e2b..16cff91d9f4 100644 --- a/arch/ppc/syslib/open_pic2.c +++ b/arch/ppc/syslib/open_pic2.c @@ -17,7 +17,6 @@ #include #include #include -#include #include #include #include diff --git a/arch/ppc/syslib/ppc4xx_setup.c b/arch/ppc/syslib/ppc4xx_setup.c index b843c4fef25..bf83240689d 100644 --- a/arch/ppc/syslib/ppc4xx_setup.c +++ b/arch/ppc/syslib/ppc4xx_setup.c @@ -18,7 +18,6 @@ #include #include #include -#include #include #include #include -- cgit v1.2.3 From 1294b118cb53fb14515666e2b218ad5ab40318c1 Mon Sep 17 00:00:00 2001 From: Kirill Korotaev Date: Fri, 30 Sep 2005 10:32:19 +0400 Subject: [PATCH] x86_64: Add missing () around arguments of pte_index macro x86-64: Add missing () around arguments of pte_index macro Signed-Off-By: Alexey Kuznetsov Signed-Off-By: Kirill Korotaev Signed-off-by: Linus Torvalds --- include/asm-x86_64/pgtable.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/asm-x86_64/pgtable.h b/include/asm-x86_64/pgtable.h index 2cb48351645..dd8711ecaf2 100644 --- a/include/asm-x86_64/pgtable.h +++ b/include/asm-x86_64/pgtable.h @@ -384,7 +384,7 @@ static inline pte_t pte_modify(pte_t pte, pgprot_t newprot) } #define pte_index(address) \ - ((address >> PAGE_SHIFT) & (PTRS_PER_PTE - 1)) + (((address) >> PAGE_SHIFT) & (PTRS_PER_PTE - 1)) #define pte_offset_kernel(dir, address) ((pte_t *) pmd_page_kernel(*(dir)) + \ pte_index(address)) -- cgit v1.2.3 From 03cdc0c304e1c068d49adc32264f07af76253e4c Mon Sep 17 00:00:00 2001 From: Daniel Ritz Date: Thu, 29 Sep 2005 21:39:32 +0200 Subject: [PATCH] usb/core/hcd-pci.c: don't free_irq() on suspend the free_irq() in USB suspend breaks resume on some setups where USB (ohci/ehci) shares the interrupt with an other device. Signed-off-by: Daniel Ritz Signed-off-by: Linus Torvalds --- drivers/usb/core/hcd-pci.c | 9 --------- 1 file changed, 9 deletions(-) diff --git a/drivers/usb/core/hcd-pci.c b/drivers/usb/core/hcd-pci.c index cbb451d227d..6385d1a99b6 100644 --- a/drivers/usb/core/hcd-pci.c +++ b/drivers/usb/core/hcd-pci.c @@ -242,7 +242,6 @@ int usb_hcd_pci_suspend (struct pci_dev *dev, pm_message_t message) case HC_STATE_SUSPENDED: /* no DMA or IRQs except when HC is active */ if (dev->current_state == PCI_D0) { - free_irq (hcd->irq, hcd); pci_save_state (dev); pci_disable_device (dev); } @@ -374,14 +373,6 @@ int usb_hcd_pci_resume (struct pci_dev *dev) hcd->state = HC_STATE_RESUMING; hcd->saw_irq = 0; - retval = request_irq (dev->irq, usb_hcd_irq, SA_SHIRQ, - hcd->irq_descr, hcd); - if (retval < 0) { - dev_err (hcd->self.controller, - "can't restore IRQ after resume!\n"); - usb_hc_died (hcd); - return retval; - } retval = hcd->driver->resume (hcd); if (!HC_IS_RUNNING (hcd->state)) { -- cgit v1.2.3 From b33fa1f3c3ec05e54e73f06c4578948c55d89ef6 Mon Sep 17 00:00:00 2001 From: Nick Piggin Date: Sat, 1 Oct 2005 02:34:42 +1000 Subject: [PATCH] i386: include linux/irq.h rather than asm/hw_irq.h I need the following patch to compile -git8 here, otherwise these files fail to compile (asm/hw_irq.h needs definitions from linux/irq.h and that file provides the required include ordering). I did not do a full audit, though there looks to be many other places that should get the same treatment, if this is the right way to do it. Signed-off-by: Linus Torvalds --- arch/i386/kernel/acpi/boot.c | 2 +- arch/i386/pci/acpi.c | 2 +- arch/i386/pci/irq.c | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/arch/i386/kernel/acpi/boot.c b/arch/i386/kernel/acpi/boot.c index 838437b2d24..b66c13c0cc0 100644 --- a/arch/i386/kernel/acpi/boot.c +++ b/arch/i386/kernel/acpi/boot.c @@ -29,12 +29,12 @@ #include #include #include +#include #include #include #include #include -#include #include #ifdef CONFIG_X86_64 diff --git a/arch/i386/pci/acpi.c b/arch/i386/pci/acpi.c index 7e7a202df3c..4c4522b43be 100644 --- a/arch/i386/pci/acpi.c +++ b/arch/i386/pci/acpi.c @@ -1,7 +1,7 @@ #include #include #include -#include +#include #include #include "pci.h" diff --git a/arch/i386/pci/irq.c b/arch/i386/pci/irq.c index 281ed8ab347..cddafe33ff7 100644 --- a/arch/i386/pci/irq.c +++ b/arch/i386/pci/irq.c @@ -15,7 +15,7 @@ #include #include #include -#include +#include #include #include "pci.h" -- cgit v1.2.3 From 13402580021a52e49c6d1068ff28ade4d5a175f1 Mon Sep 17 00:00:00 2001 From: James Morris Date: Fri, 30 Sep 2005 14:24:34 -0400 Subject: [PATCH] SELinux - fix SCTP socket bug and general IP protocol handling The following patch updates the way SELinux classifies and handles IP based protocols. Currently, IP sockets are classified by SELinux as being either TCP, UDP or 'Raw', the latter being a default for IP socket that is not TCP or UDP. The classification code is out of date and uses only the socket type parameter to socket(2) to determine the class of IP socket. So, any socket created with SOCK_STREAM will be classified by SELinux as TCP, and SOCK_DGRAM as UDP. Also, other socket types such as SOCK_SEQPACKET and SOCK_DCCP are currently ignored by SELinux, which classifies them as generic sockets, which means they don't even get basic IP level checking. This patch changes the SELinux IP socket classification logic, so that only an IPPROTO_IP protocol value passed to socket(2) classify the socket as TCP or UDP. The patch also drops the check for SOCK_RAW and converts it into a default, so that socket types like SOCK_DCCP and SOCK_SEQPACKET are classified as SECCLASS_RAWIP_SOCKET (instead of generic sockets). Note that protocol-specific support for SCTP, DCCP etc. is not addressed here, we're just getting these protocols checked at the IP layer. This fixes a reported problem where SCTP sockets were being recognized as generic SELinux sockets yet still being passed in one case to an IP level check, which then fails for generic sockets. It will also fix bugs where any SOCK_STREAM socket is classified as TCP or any SOCK_DGRAM socket is classified as UDP. This patch also unifies the way IP sockets classes are determined in selinux_socket_bind(), so we use the already calculated value instead of trying to recalculate it. Signed-off-by: James Morris Signed-off-by: Stephen Smalley Signed-off-by: Linus Torvalds --- security/selinux/hooks.c | 30 ++++++++++++++++++++++++------ 1 file changed, 24 insertions(+), 6 deletions(-) diff --git a/security/selinux/hooks.c b/security/selinux/hooks.c index 6e4937fe062..b13be15165f 100644 --- a/security/selinux/hooks.c +++ b/security/selinux/hooks.c @@ -630,6 +630,16 @@ static inline u16 inode_mode_to_security_class(umode_t mode) return SECCLASS_FILE; } +static inline int default_protocol_stream(int protocol) +{ + return (protocol == IPPROTO_IP || protocol == IPPROTO_TCP); +} + +static inline int default_protocol_dgram(int protocol) +{ + return (protocol == IPPROTO_IP || protocol == IPPROTO_UDP); +} + static inline u16 socket_type_to_security_class(int family, int type, int protocol) { switch (family) { @@ -646,10 +656,16 @@ static inline u16 socket_type_to_security_class(int family, int type, int protoc case PF_INET6: switch (type) { case SOCK_STREAM: - return SECCLASS_TCP_SOCKET; + if (default_protocol_stream(protocol)) + return SECCLASS_TCP_SOCKET; + else + return SECCLASS_RAWIP_SOCKET; case SOCK_DGRAM: - return SECCLASS_UDP_SOCKET; - case SOCK_RAW: + if (default_protocol_dgram(protocol)) + return SECCLASS_UDP_SOCKET; + else + return SECCLASS_RAWIP_SOCKET; + default: return SECCLASS_RAWIP_SOCKET; } break; @@ -2970,6 +2986,8 @@ static int selinux_socket_bind(struct socket *sock, struct sockaddr *address, in /* * If PF_INET or PF_INET6, check name_bind permission for the port. + * Multiple address binding for SCTP is not supported yet: we just + * check the first address now. */ family = sock->sk->sk_family; if (family == PF_INET || family == PF_INET6) { @@ -3014,12 +3032,12 @@ static int selinux_socket_bind(struct socket *sock, struct sockaddr *address, in goto out; } - switch(sk->sk_protocol) { - case IPPROTO_TCP: + switch(isec->sclass) { + case SECCLASS_TCP_SOCKET: node_perm = TCP_SOCKET__NODE_BIND; break; - case IPPROTO_UDP: + case SECCLASS_UDP_SOCKET: node_perm = UDP_SOCKET__NODE_BIND; break; -- cgit v1.2.3 From 6e3254c4e2927c117044a02acf5f5b56e1373053 Mon Sep 17 00:00:00 2001 From: Linus Torvalds Date: Fri, 30 Sep 2005 12:38:27 -0700 Subject: Revert "x86-64: Reverse order of bootmem lists" As requested by Thomas Gleixner : "5d3d0f7704ed0bc7eaca0501eeae3e5da1ea6c87 breaks a couple of ARM boards, which depend on the historical bootmem allocation order. There is a cleaner solution around to remove the pgdat list completely, but this is a topic for post 2.6.14 Andi signalled ACK already." Signed-off-by: Linus Torvalds --- mm/bootmem.c | 14 +++----------- 1 file changed, 3 insertions(+), 11 deletions(-) diff --git a/mm/bootmem.c b/mm/bootmem.c index 8ec4e4c2a17..c1330cc1978 100644 --- a/mm/bootmem.c +++ b/mm/bootmem.c @@ -61,17 +61,9 @@ static unsigned long __init init_bootmem_core (pg_data_t *pgdat, { bootmem_data_t *bdata = pgdat->bdata; unsigned long mapsize = ((end - start)+7)/8; - static struct pglist_data *pgdat_last; - - pgdat->pgdat_next = NULL; - /* Add new nodes last so that bootmem always starts - searching in the first nodes, not the last ones */ - if (pgdat_last) - pgdat_last->pgdat_next = pgdat; - else { - pgdat_list = pgdat; - pgdat_last = pgdat; - } + + pgdat->pgdat_next = pgdat_list; + pgdat_list = pgdat; mapsize = ALIGN(mapsize, sizeof(long)); bdata->node_bootmem_map = phys_to_virt(mapstart << PAGE_SHIFT); -- cgit v1.2.3 From 998765e5588b197737d457e16f72832d8036190f Mon Sep 17 00:00:00 2001 From: Zach Brown Date: Fri, 30 Sep 2005 11:58:54 -0700 Subject: [PATCH] aio: lock around kiocbTryKick() Only one of the run or kick path is supposed to put an iocb on the run list. If both of them do it than one of them can end up referencing a freed iocb. The kick patch could set the Kicked bit before acquiring the ctx_lock and putting the iocb on the run list. The run path, while holding the ctx_lock, could see this partial kick and mistake it for a kick that was deferred while it was doing work with the run_list NULLed out. It would then race with the kick thread to add the iocb to the run list. This patch moves the kick setting under the ctx_lock so that only one of the kick or run path queues the iocb on the run list, as intended. Signed-off-by: Zach Brown Signed-off-by: Benjamin LaHaise Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- fs/aio.c | 19 ++++++++++++------- 1 file changed, 12 insertions(+), 7 deletions(-) diff --git a/fs/aio.c b/fs/aio.c index 0e11e31dbb7..b8f296999c0 100644 --- a/fs/aio.c +++ b/fs/aio.c @@ -899,16 +899,24 @@ static void aio_kick_handler(void *data) * and if required activate the aio work queue to process * it */ -static void queue_kicked_iocb(struct kiocb *iocb) +static void try_queue_kicked_iocb(struct kiocb *iocb) { struct kioctx *ctx = iocb->ki_ctx; unsigned long flags; int run = 0; - WARN_ON((!list_empty(&iocb->ki_wait.task_list))); + /* We're supposed to be the only path putting the iocb back on the run + * list. If we find that the iocb is *back* on a wait queue already + * than retry has happened before we could queue the iocb. This also + * means that the retry could have completed and freed our iocb, no + * good. */ + BUG_ON((!list_empty(&iocb->ki_wait.task_list))); spin_lock_irqsave(&ctx->ctx_lock, flags); - run = __queue_kicked_iocb(iocb); + /* set this inside the lock so that we can't race with aio_run_iocb() + * testing it and putting the iocb on the run list under the lock */ + if (!kiocbTryKick(iocb)) + run = __queue_kicked_iocb(iocb); spin_unlock_irqrestore(&ctx->ctx_lock, flags); if (run) aio_queue_work(ctx); @@ -931,10 +939,7 @@ void fastcall kick_iocb(struct kiocb *iocb) return; } - /* If its already kicked we shouldn't queue it again */ - if (!kiocbTryKick(iocb)) { - queue_kicked_iocb(iocb); - } + try_queue_kicked_iocb(iocb); } EXPORT_SYMBOL(kick_iocb); -- cgit v1.2.3 From 897f15fb587fd2772b9e7ff6ec0265057f3c3975 Mon Sep 17 00:00:00 2001 From: Zach Brown Date: Fri, 30 Sep 2005 11:58:55 -0700 Subject: [PATCH] aio: remove unlocked task_list test and resulting race Only one of the run or kick path is supposed to put an iocb on the run list. If both of them do it than one of them can end up referencing a freed iocb. The kick path could delete the task_list item from the wait queue before getting the ctx_lock and putting the iocb on the run list. The run path was testing the task_list item outside the lock so that it could catch ki_retry methods that return -EIOCBRETRY *without* putting the iocb on a wait queue and promising to call kick_iocb. This unlocked check could then race with the kick path to cause both to try and put the iocb on the run list. The patch stops the run path from testing task_list by requring that any ki_retry that returns -EIOCBRETRY *must* guarantee that kick_iocb() will be called in the future. aio_p{read,write}, the only in-tree -EIOCBRETRY users, are updated. Signed-off-by: Zach Brown Signed-off-by: Benjamin LaHaise Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- fs/aio.c | 79 ++++++++++++++++++++++------------------------------- include/linux/aio.h | 34 +++++++++++++++++++++++ 2 files changed, 67 insertions(+), 46 deletions(-) diff --git a/fs/aio.c b/fs/aio.c index b8f296999c0..9edc0e4a121 100644 --- a/fs/aio.c +++ b/fs/aio.c @@ -741,19 +741,9 @@ static ssize_t aio_run_iocb(struct kiocb *iocb) ret = retry(iocb); current->io_wait = NULL; - if (-EIOCBRETRY != ret) { - if (-EIOCBQUEUED != ret) { - BUG_ON(!list_empty(&iocb->ki_wait.task_list)); - aio_complete(iocb, ret, 0); - /* must not access the iocb after this */ - } - } else { - /* - * Issue an additional retry to avoid waiting forever if - * no waits were queued (e.g. in case of a short read). - */ - if (list_empty(&iocb->ki_wait.task_list)) - kiocbSetKicked(iocb); + if (ret != -EIOCBRETRY && ret != -EIOCBQUEUED) { + BUG_ON(!list_empty(&iocb->ki_wait.task_list)); + aio_complete(iocb, ret, 0); } out: spin_lock_irq(&ctx->ctx_lock); @@ -1327,8 +1317,11 @@ asmlinkage long sys_io_destroy(aio_context_t ctx) } /* - * Default retry method for aio_read (also used for first time submit) - * Responsible for updating iocb state as retries progress + * aio_p{read,write} are the default ki_retry methods for + * IO_CMD_P{READ,WRITE}. They maintains kiocb retry state around potentially + * multiple calls to f_op->aio_read(). They loop around partial progress + * instead of returning -EIOCBRETRY because they don't have the means to call + * kick_iocb(). */ static ssize_t aio_pread(struct kiocb *iocb) { @@ -1337,25 +1330,25 @@ static ssize_t aio_pread(struct kiocb *iocb) struct inode *inode = mapping->host; ssize_t ret = 0; - ret = file->f_op->aio_read(iocb, iocb->ki_buf, - iocb->ki_left, iocb->ki_pos); + do { + ret = file->f_op->aio_read(iocb, iocb->ki_buf, + iocb->ki_left, iocb->ki_pos); + /* + * Can't just depend on iocb->ki_left to determine + * whether we are done. This may have been a short read. + */ + if (ret > 0) { + iocb->ki_buf += ret; + iocb->ki_left -= ret; + } - /* - * Can't just depend on iocb->ki_left to determine - * whether we are done. This may have been a short read. - */ - if (ret > 0) { - iocb->ki_buf += ret; - iocb->ki_left -= ret; /* - * For pipes and sockets we return once we have - * some data; for regular files we retry till we - * complete the entire read or find that we can't - * read any more data (e.g short reads). + * For pipes and sockets we return once we have some data; for + * regular files we retry till we complete the entire read or + * find that we can't read any more data (e.g short reads). */ - if (!S_ISFIFO(inode->i_mode) && !S_ISSOCK(inode->i_mode)) - ret = -EIOCBRETRY; - } + } while (ret > 0 && + !S_ISFIFO(inode->i_mode) && !S_ISSOCK(inode->i_mode)); /* This means we must have transferred all that we could */ /* No need to retry anymore */ @@ -1365,27 +1358,21 @@ static ssize_t aio_pread(struct kiocb *iocb) return ret; } -/* - * Default retry method for aio_write (also used for first time submit) - * Responsible for updating iocb state as retries progress - */ +/* see aio_pread() */ static ssize_t aio_pwrite(struct kiocb *iocb) { struct file *file = iocb->ki_filp; ssize_t ret = 0; - ret = file->f_op->aio_write(iocb, iocb->ki_buf, - iocb->ki_left, iocb->ki_pos); - - if (ret > 0) { - iocb->ki_buf += ret; - iocb->ki_left -= ret; - - ret = -EIOCBRETRY; - } + do { + ret = file->f_op->aio_write(iocb, iocb->ki_buf, + iocb->ki_left, iocb->ki_pos); + if (ret > 0) { + iocb->ki_buf += ret; + iocb->ki_left -= ret; + } + } while (ret > 0); - /* This means we must have transferred all that we could */ - /* No need to retry anymore */ if ((ret == 0) || (iocb->ki_left == 0)) ret = iocb->ki_nbytes - iocb->ki_left; diff --git a/include/linux/aio.h b/include/linux/aio.h index a4d5af907f9..60def658b24 100644 --- a/include/linux/aio.h +++ b/include/linux/aio.h @@ -43,6 +43,40 @@ struct kioctx; #define kiocbIsKicked(iocb) test_bit(KIF_KICKED, &(iocb)->ki_flags) #define kiocbIsCancelled(iocb) test_bit(KIF_CANCELLED, &(iocb)->ki_flags) +/* is there a better place to document function pointer methods? */ +/** + * ki_retry - iocb forward progress callback + * @kiocb: The kiocb struct to advance by performing an operation. + * + * This callback is called when the AIO core wants a given AIO operation + * to make forward progress. The kiocb argument describes the operation + * that is to be performed. As the operation proceeds, perhaps partially, + * ki_retry is expected to update the kiocb with progress made. Typically + * ki_retry is set in the AIO core and it itself calls file_operations + * helpers. + * + * ki_retry's return value determines when the AIO operation is completed + * and an event is generated in the AIO event ring. Except the special + * return values described below, the value that is returned from ki_retry + * is transferred directly into the completion ring as the operation's + * resulting status. Once this has happened ki_retry *MUST NOT* reference + * the kiocb pointer again. + * + * If ki_retry returns -EIOCBQUEUED it has made a promise that aio_complete() + * will be called on the kiocb pointer in the future. The AIO core will + * not ask the method again -- ki_retry must ensure forward progress. + * aio_complete() must be called once and only once in the future, multiple + * calls may result in undefined behaviour. + * + * If ki_retry returns -EIOCBRETRY it has made a promise that kick_iocb() + * will be called on the kiocb pointer in the future. This may happen + * through generic helpers that associate kiocb->ki_wait with a wait + * queue head that ki_retry uses via current->io_wait. It can also happen + * with custom tracking and manual calls to kick_iocb(), though that is + * discouraged. In either case, kick_iocb() must be called once and only + * once. ki_retry must ensure forward progress, the AIO core will wait + * indefinitely for kick_iocb() to be called. + */ struct kiocb { struct list_head ki_run_list; long ki_flags; -- cgit v1.2.3 From 353fb07e2043d2df12dddf4e2c39552d0ab9b026 Mon Sep 17 00:00:00 2001 From: Zach Brown Date: Fri, 30 Sep 2005 11:58:56 -0700 Subject: [PATCH] aio: avoid extra aio_{read,write} call when ki_left == 0 Recently aio_p{read,write} changed to perform retries internally rather than returning -EIOCBRETRY. This inadvertantly resulted in always calling aio_{read,write} with ki_left at 0 which would in turn immediately return 0. Harmless, but we can avoid this call by checking in the caller. Signed-off-by: Zach Brown Signed-off-by: Benjamin LaHaise Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- fs/aio.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/fs/aio.c b/fs/aio.c index 9edc0e4a121..d6b1551342b 100644 --- a/fs/aio.c +++ b/fs/aio.c @@ -1347,7 +1347,7 @@ static ssize_t aio_pread(struct kiocb *iocb) * regular files we retry till we complete the entire read or * find that we can't read any more data (e.g short reads). */ - } while (ret > 0 && + } while (ret > 0 && iocb->ki_left > 0 && !S_ISFIFO(inode->i_mode) && !S_ISSOCK(inode->i_mode)); /* This means we must have transferred all that we could */ @@ -1371,7 +1371,7 @@ static ssize_t aio_pwrite(struct kiocb *iocb) iocb->ki_buf += ret; iocb->ki_left -= ret; } - } while (ret > 0); + } while (ret > 0 && iocb->ki_left > 0); if ((ret == 0) || (iocb->ki_left == 0)) ret = iocb->ki_nbytes - iocb->ki_left; -- cgit v1.2.3 From d96c4e7bb039ae16c9b7e6809feb4fcfc45fcc87 Mon Sep 17 00:00:00 2001 From: Andrew Morton Date: Fri, 30 Sep 2005 11:58:57 -0700 Subject: [PATCH] x86: hw_irq.h warning fix include/asm/hw_irq.h:70: warning: `struct hw_interrupt_type' declared inside parameter list include/asm/hw_irq.h:70: warning: its scope is only this definition or declaration, which is probably not what you want Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- include/asm-i386/hw_irq.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/include/asm-i386/hw_irq.h b/include/asm-i386/hw_irq.h index 4ac84cc6f01..622815bf324 100644 --- a/include/asm-i386/hw_irq.h +++ b/include/asm-i386/hw_irq.h @@ -18,6 +18,8 @@ #include #include +struct hw_interrupt_type; + /* * Various low-level irq details needed by irq.c, process.c, * time.c, io_apic.c and smp.c -- cgit v1.2.3 From 79dfa4a5a2eea5035de793b1633031750fe8d3ff Mon Sep 17 00:00:00 2001 From: Michael Krufky Date: Fri, 30 Sep 2005 11:58:58 -0700 Subject: [PATCH] v4l: DViCO FusionHDTV5 Lite GPIO Fix GPIO fix for the composite and tv mute states of bt8xx card #135: DViCO FusionHDTV5 Lite. Without this patch, selecting one of these states could produce unexpected behavior. Signed-off-by: Michael Krufky Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/media/video/bttv-cards.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/media/video/bttv-cards.c b/drivers/media/video/bttv-cards.c index 190977a1e54..6c332800d6a 100644 --- a/drivers/media/video/bttv-cards.c +++ b/drivers/media/video/bttv-cards.c @@ -2398,7 +2398,7 @@ struct tvcard bttv_tvcards[] = { .svhs = 2, .muxsel = { 2, 3 }, .gpiomask = 0x00e00007, - .audiomux = { 0x00400005, 0, 0, 0, 0, 0 }, + .audiomux = { 0x00400005, 0, 0x00000001, 0, 0x00c00007, 0 }, .no_msp34xx = 1, .no_tda9875 = 1, .no_tda7432 = 1, -- cgit v1.2.3 From be662a18b7763496a052d489206af9ca2c2e1ac2 Mon Sep 17 00:00:00 2001 From: Paolo 'Blaisorblade' Giarrusso Date: Fri, 30 Sep 2005 11:58:59 -0700 Subject: [PATCH] uml: fix page faults in SKAS3 mode. I hadn't been running a SKAS3 host when testing the "uml: fix hang in TT mode on fault" patch (commit 546fe1cbf91d4d62e3849517c31a2327c992e5c5), and I didn't think enough to the missing trap_no in SKAS3 mode. In fact, the resulting kernel doesn't work at all in SKAS3 mode. Signed-off-by: Paolo 'Blaisorblade' Giarrusso Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/um/include/sysdep-i386/sigcontext.h | 10 +++++++++- arch/um/include/sysdep-x86_64/sigcontext.h | 5 ++++- arch/um/kernel/trap_kern.c | 5 ++++- 3 files changed, 17 insertions(+), 3 deletions(-) diff --git a/arch/um/include/sysdep-i386/sigcontext.h b/arch/um/include/sysdep-i386/sigcontext.h index 1fe72926516..23fd2644d7e 100644 --- a/arch/um/include/sysdep-i386/sigcontext.h +++ b/arch/um/include/sysdep-i386/sigcontext.h @@ -6,6 +6,7 @@ #ifndef __SYS_SIGCONTEXT_I386_H #define __SYS_SIGCONTEXT_I386_H +#include "uml-config.h" #include #define IP_RESTART_SYSCALL(ip) ((ip) -= 2) @@ -26,7 +27,14 @@ #define SC_START_SYSCALL(sc) do SC_EAX(sc) = -ENOSYS; while(0) /* This is Page Fault */ -#define SEGV_IS_FIXABLE(fi) ((fi)->trap_no == 14) +#define SEGV_IS_FIXABLE(fi) ((fi)->trap_no == 14) + +/* SKAS3 has no trap_no on i386, but get_skas_faultinfo() sets it to 0. */ +#ifdef UML_CONFIG_MODE_SKAS +#define SEGV_MAYBE_FIXABLE(fi) ((fi)->trap_no == 0 && ptrace_faultinfo) +#else +#define SEGV_MAYBE_FIXABLE(fi) 0 +#endif extern unsigned long *sc_sigmask(void *sc_ptr); extern int sc_get_fpregs(unsigned long buf, void *sc_ptr); diff --git a/arch/um/include/sysdep-x86_64/sigcontext.h b/arch/um/include/sysdep-x86_64/sigcontext.h index 2a78260d15a..41073235e7a 100644 --- a/arch/um/include/sysdep-x86_64/sigcontext.h +++ b/arch/um/include/sysdep-x86_64/sigcontext.h @@ -31,7 +31,10 @@ #define SC_START_SYSCALL(sc) do SC_RAX(sc) = -ENOSYS; while(0) /* This is Page Fault */ -#define SEGV_IS_FIXABLE(fi) ((fi)->trap_no == 14) +#define SEGV_IS_FIXABLE(fi) ((fi)->trap_no == 14) + +/* No broken SKAS API, which doesn't pass trap_no, here. */ +#define SEGV_MAYBE_FIXABLE(fi) 0 extern unsigned long *sc_sigmask(void *sc_ptr); diff --git a/arch/um/kernel/trap_kern.c b/arch/um/kernel/trap_kern.c index d297429ac36..95c8f8733ba 100644 --- a/arch/um/kernel/trap_kern.c +++ b/arch/um/kernel/trap_kern.c @@ -26,6 +26,9 @@ #include "mconsole_kern.h" #include "mem.h" #include "mem_kern.h" +#ifdef CONFIG_MODE_SKAS +#include "skas.h" +#endif /* Note this is constrained to return 0, -EFAULT, -EACCESS, -ENOMEM by segv(). */ int handle_page_fault(unsigned long address, unsigned long ip, @@ -134,7 +137,7 @@ unsigned long segv(struct faultinfo fi, unsigned long ip, int is_user, void *sc) else if(current->mm == NULL) panic("Segfault with no mm"); - if (SEGV_IS_FIXABLE(&fi)) + if (SEGV_IS_FIXABLE(&fi) || SEGV_MAYBE_FIXABLE(&fi)) err = handle_page_fault(address, ip, is_write, is_user, &si.si_code); else { err = -EFAULT; -- cgit v1.2.3 From 8923648c125421b0fcb240cde607e2748d099ab8 Mon Sep 17 00:00:00 2001 From: Paolo 'Blaisorblade' Giarrusso Date: Fri, 30 Sep 2005 11:59:00 -0700 Subject: [PATCH] uml: clear SKAS0/3 flags when running in TT mode SEGV_MAYBE_FIXABLE tests ptrace_faultinfo, and depends on it being 1 only in SKAS3 mode, while currently when running with mode=tt it will be 1 anyway. Fix this, and do the same for proc_mm. Signed-off-by: Paolo 'Blaisorblade' Giarrusso Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/um/include/os.h | 4 ++++ arch/um/kernel/um_arch.c | 2 ++ 2 files changed, 6 insertions(+) diff --git a/arch/um/include/os.h b/arch/um/include/os.h index 583329d0a53..6f766e1faec 100644 --- a/arch/um/include/os.h +++ b/arch/um/include/os.h @@ -157,6 +157,10 @@ extern int os_lock_file(int fd, int excl); extern void os_early_checks(void); extern int can_do_skas(void); +/* Make sure they are clear when running in TT mode. Required by + * SEGV_MAYBE_FIXABLE */ +#define clear_can_do_skas() do { ptrace_faultinfo = proc_mm = 0; } while (0) + /* mem.c */ extern int create_mem_file(unsigned long len); diff --git a/arch/um/kernel/um_arch.c b/arch/um/kernel/um_arch.c index f0a275947d3..93dc782dc1c 100644 --- a/arch/um/kernel/um_arch.c +++ b/arch/um/kernel/um_arch.c @@ -334,6 +334,8 @@ int linux_main(int argc, char **argv) add_arg(DEFAULT_COMMAND_LINE); os_early_checks(); + if (force_tt) + clear_can_do_skas(); mode_tt = force_tt ? 1 : !can_do_skas(); #ifndef CONFIG_MODE_TT if (mode_tt) { -- cgit v1.2.3 From bd948057357db5febfe64cf7a9ef11d7e347ffec Mon Sep 17 00:00:00 2001 From: Paolo 'Blaisorblade' Giarrusso Date: Fri, 30 Sep 2005 11:59:00 -0700 Subject: [PATCH] uml: revert "run mconsole "sysrq" in process context" Revert commit 12ebcd73e40e09f0dfddf89e465cc0541e0ff8b1, i.e. [PATCH] uml: run mconsole "sysrq" in process context on request from Jeff Dike. a) sysrq may be run when the scheduler is non-functioning b) the warning I wanted to fix actually came from the fault handler run in atomic context. But I fixed that not to take the semaphore in a separate patch. c) the fault handler is run because of a fault, and that fault was unaffected by this patch. Signed-off-by: Paolo 'Blaisorblade' Giarrusso Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/um/drivers/mconsole_user.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/um/drivers/mconsole_user.c b/arch/um/drivers/mconsole_user.c index 04383f98f4d..310c1f823f2 100644 --- a/arch/um/drivers/mconsole_user.c +++ b/arch/um/drivers/mconsole_user.c @@ -23,7 +23,7 @@ static struct mconsole_command commands[] = { { "reboot", mconsole_reboot, MCONSOLE_PROC }, { "config", mconsole_config, MCONSOLE_PROC }, { "remove", mconsole_remove, MCONSOLE_PROC }, - { "sysrq", mconsole_sysrq, MCONSOLE_PROC }, + { "sysrq", mconsole_sysrq, MCONSOLE_INTR }, { "help", mconsole_help, MCONSOLE_INTR }, { "cad", mconsole_cad, MCONSOLE_INTR }, { "stop", mconsole_stop, MCONSOLE_PROC }, -- cgit v1.2.3 From daa35edc0a967d1f77c2e2c1346f57d04371487a Mon Sep 17 00:00:00 2001 From: Paolo 'Blaisorblade' Giarrusso Date: Fri, 30 Sep 2005 11:59:01 -0700 Subject: [PATCH] uml: remove empty hostfs_truncate method Calling truncate() on hostfs spits a kernel warning "Something isn't implemented here", but it still works fine. Indeed, hostfs i_op->truncate doesn't do anything. But hostfs_setattr() -> set_attr() correctly detects ATTR_SIZE and calls truncate() on the host. So we should be safe (using ftruncate() may be better, in case the file is unlinked on the host, but we aren't sure to have the file open for writing, and reopening it would cause the same races; plus nobody should expect UML to be so careful). So, the warning is wrong, because the current implementation is working. Al, am I correct, and can the warning be therefore dropped? CC: Al Viro Signed-off-by: Paolo 'Blaisorblade' Giarrusso Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- fs/hostfs/hostfs_kern.c | 7 ------- 1 file changed, 7 deletions(-) diff --git a/fs/hostfs/hostfs_kern.c b/fs/hostfs/hostfs_kern.c index 59c5062cd63..dd711310626 100644 --- a/fs/hostfs/hostfs_kern.c +++ b/fs/hostfs/hostfs_kern.c @@ -793,11 +793,6 @@ int hostfs_rename(struct inode *from_ino, struct dentry *from, return(err); } -void hostfs_truncate(struct inode *ino) -{ - not_implemented(); -} - int hostfs_permission(struct inode *ino, int desired, struct nameidata *nd) { char *name; @@ -894,7 +889,6 @@ static struct inode_operations hostfs_iops = { .rmdir = hostfs_rmdir, .mknod = hostfs_mknod, .rename = hostfs_rename, - .truncate = hostfs_truncate, .permission = hostfs_permission, .setattr = hostfs_setattr, .getattr = hostfs_getattr, @@ -910,7 +904,6 @@ static struct inode_operations hostfs_dir_iops = { .rmdir = hostfs_rmdir, .mknod = hostfs_mknod, .rename = hostfs_rename, - .truncate = hostfs_truncate, .permission = hostfs_permission, .setattr = hostfs_setattr, .getattr = hostfs_getattr, -- cgit v1.2.3 From dd190d066b7ded8c44b2b67dd0a14bed01525d3c Mon Sep 17 00:00:00 2001 From: Miklos Szeredi Date: Fri, 30 Sep 2005 11:59:02 -0700 Subject: [PATCH] fuse: check O_DIRECT Check O_DIRECT and return -EINVAL error in open. dentry_open() also checks this but only after the open method is called. This patch optimizes away the unnecessary upcalls in this case. It could be a correctness issue too: if filesystem has open() with side effect, then it should fail before doing the open, not after. Signed-off-by: Miklos Szeredi Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- fs/fuse/file.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/fs/fuse/file.c b/fs/fuse/file.c index 6454022b053..657ab11c173 100644 --- a/fs/fuse/file.c +++ b/fs/fuse/file.c @@ -23,6 +23,10 @@ int fuse_open_common(struct inode *inode, struct file *file, int isdir) struct fuse_file *ff; int err; + /* VFS checks this, but only _after_ ->open() */ + if (file->f_flags & O_DIRECT) + return -EINVAL; + err = generic_file_open(inode, file); if (err) return err; -- cgit v1.2.3 From d38e24e260daf11365efd4ed621235fe9c0ba7ee Mon Sep 17 00:00:00 2001 From: Brent Casavant Date: Fri, 30 Sep 2005 11:59:04 -0700 Subject: [PATCH] ioc4_serial: Remove bogus error message This change removes a bogus error message from the IOC4 serial driver interrupt handler. This error message is bogus for two reasons. First, it can never occur given that current code takes care to initialize IOC4 in such a way that these "unknown" interrupts could never occur. Second, this code fails to take into account that other drivers can share the IOC4 interrupt mechanism through SA_SHIRQ, and thus this driver is not in-fact "all-knowing". Finally, this error message triggers every time some "unknown" interrupt occurs -- it's not rate limited or repetition limited in any way, thereby effectively denying use of the console device. Given its bogosity in the first place, it's best to just get rid of it entirely. Acked-by: Pat Gefre Signed-off-by: Brent Casavant Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/serial/ioc4_serial.c | 12 ------------ 1 file changed, 12 deletions(-) diff --git a/drivers/serial/ioc4_serial.c b/drivers/serial/ioc4_serial.c index 0c5c96a582b..f88fdd48068 100644 --- a/drivers/serial/ioc4_serial.c +++ b/drivers/serial/ioc4_serial.c @@ -973,18 +973,6 @@ static irqreturn_t ioc4_intr(int irq, void *arg, struct pt_regs *regs) this_ir &= ~this_mir; } } - if (this_ir) { - printk(KERN_ERR - "unknown IOC4 %s interrupt 0x%x, sio_ir = 0x%x," - " sio_ies = 0x%x, other_ir = 0x%x :" - "other_ies = 0x%x\n", - (intr_type == IOC4_SIO_INTR_TYPE) ? "sio" : - "other", this_ir, - readl(&soft->is_ioc4_misc_addr->sio_ir.raw), - readl(&soft->is_ioc4_misc_addr->sio_ies.raw), - readl(&soft->is_ioc4_misc_addr->other_ir.raw), - readl(&soft->is_ioc4_misc_addr->other_ies.raw)); - } } #ifdef DEBUG_INTERRUPTS { -- cgit v1.2.3 From 105d7b38b08f85c9abc3fd31e5cfa7ee4cf0a402 Mon Sep 17 00:00:00 2001 From: Jody McIntyre Date: Fri, 30 Sep 2005 11:59:04 -0700 Subject: [PATCH] MAINTAINERS: sbp2 driver is not orphaned. Cc: Ben Collins Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- MAINTAINERS | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/MAINTAINERS b/MAINTAINERS index f3d9adec5aa..abf7f7a17ae 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -1168,11 +1168,6 @@ L: linux1394-devel@lists.sourceforge.net W: http://www.linux1394.org/ S: Orphan -IEEE 1394 SBP2 -L: linux1394-devel@lists.sourceforge.net -W: http://www.linux1394.org/ -S: Orphan - IEEE 1394 SUBSYSTEM P: Ben Collins M: bcollins@debian.org @@ -1207,6 +1202,15 @@ L: linux1394-devel@lists.sourceforge.net W: http://www.linux1394.org/ S: Maintained +IEEE 1394 SBP2 +P: Ben Collins +M: bcollins@debian.org +P: Stefan Richter +M: stefanr@s5r6.in-berlin.de +L: linux1394-devel@lists.sourceforge.net +W: http://www.linux1394.org/ +S: Maintained + IMS TWINTURBO FRAMEBUFFER DRIVER P: Paul Mundt M: lethal@chaoticdreams.org -- cgit v1.2.3 From abd559b1052e28d8b9c28aabde241f18fa89090b Mon Sep 17 00:00:00 2001 From: Jody McIntyre Date: Fri, 30 Sep 2005 11:59:06 -0700 Subject: [PATCH] sbp2: fix deadlocks and delays on device removal/rmmod Fixes for deadlocks of the ieee1394 and scsi subsystems and long delays in futile error recovery attempts when SBP-2 devices are removed or drivers are unloaded. - Complete commands quickly with DID_NO_CONNECT if the 1394 node is gone or if the 1394 low-level driver was unloaded. - Skip unnecessary work in the eh_abort_handler and eh_device_reset_handler if the node or 1394 low-level driver is gone. - Let scsi's high-level shut down gracefully when sbp2 is being unloaded or detached from the 1394 unit. A call to scsi_remove_device is added for this purpose, which requires us to store a scsi_device pointer. - scsi_device pointer is obtained from slave_alloc hook and cleared by slave_destroy. This avoids usage of the pointer after the scsi device was deleted e.g. by the user via scsi_mod's sysfs interface. Signed-off-by: Stefan Richter Signed-off-by: Jody McIntyre Cc: Ben Collins Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/ieee1394/sbp2.c | 96 +++++++++++++++++++++++++++++-------------------- 1 file changed, 58 insertions(+), 38 deletions(-) diff --git a/drivers/ieee1394/sbp2.c b/drivers/ieee1394/sbp2.c index de88218ef7c..5d86b03979e 100644 --- a/drivers/ieee1394/sbp2.c +++ b/drivers/ieee1394/sbp2.c @@ -596,6 +596,14 @@ static void sbp2util_mark_command_completed(struct scsi_id_instance_data *scsi_i spin_unlock_irqrestore(&scsi_id->sbp2_command_orb_lock, flags); } +/* + * Is scsi_id valid? Is the 1394 node still present? + */ +static inline int sbp2util_node_is_available(struct scsi_id_instance_data *scsi_id) +{ + return scsi_id && scsi_id->ne && !scsi_id->ne->in_limbo; +} + /********************************************* @@ -631,11 +639,23 @@ static int sbp2_remove(struct device *dev) { struct unit_directory *ud; struct scsi_id_instance_data *scsi_id; + struct scsi_device *sdev; SBP2_DEBUG("sbp2_remove"); ud = container_of(dev, struct unit_directory, device); scsi_id = ud->device.driver_data; + if (!scsi_id) + return 0; + + /* Trigger shutdown functions in scsi's highlevel. */ + if (scsi_id->scsi_host) + scsi_unblock_requests(scsi_id->scsi_host); + sdev = scsi_id->sdev; + if (sdev) { + scsi_id->sdev = NULL; + scsi_remove_device(sdev); + } sbp2_logout_device(scsi_id); sbp2_remove_device(scsi_id); @@ -2473,37 +2493,26 @@ static int sbp2scsi_queuecommand(struct scsi_cmnd *SCpnt, struct scsi_id_instance_data *scsi_id = (struct scsi_id_instance_data *)SCpnt->device->host->hostdata[0]; struct sbp2scsi_host_info *hi; + int result = DID_NO_CONNECT << 16; SBP2_DEBUG("sbp2scsi_queuecommand"); - /* - * If scsi_id is null, it means there is no device in this slot, - * so we should return selection timeout. - */ - if (!scsi_id) { - SCpnt->result = DID_NO_CONNECT << 16; - done (SCpnt); - return 0; - } + if (!sbp2util_node_is_available(scsi_id)) + goto done; hi = scsi_id->hi; if (!hi) { SBP2_ERR("sbp2scsi_host_info is NULL - this is bad!"); - SCpnt->result = DID_NO_CONNECT << 16; - done (SCpnt); - return(0); + goto done; } /* * Until we handle multiple luns, just return selection time-out * to any IO directed at non-zero LUNs */ - if (SCpnt->device->lun) { - SCpnt->result = DID_NO_CONNECT << 16; - done (SCpnt); - return(0); - } + if (SCpnt->device->lun) + goto done; /* * Check for request sense command, and handle it here @@ -2514,7 +2523,7 @@ static int sbp2scsi_queuecommand(struct scsi_cmnd *SCpnt, memcpy(SCpnt->request_buffer, SCpnt->sense_buffer, SCpnt->request_bufflen); memset(SCpnt->sense_buffer, 0, sizeof(SCpnt->sense_buffer)); sbp2scsi_complete_command(scsi_id, SBP2_SCSI_STATUS_GOOD, SCpnt, done); - return(0); + return 0; } /* @@ -2522,9 +2531,8 @@ static int sbp2scsi_queuecommand(struct scsi_cmnd *SCpnt, */ if (!hpsb_node_entry_valid(scsi_id->ne)) { SBP2_ERR("Bus reset in progress - rejecting command"); - SCpnt->result = DID_BUS_BUSY << 16; - done (SCpnt); - return(0); + result = DID_BUS_BUSY << 16; + goto done; } /* @@ -2535,8 +2543,12 @@ static int sbp2scsi_queuecommand(struct scsi_cmnd *SCpnt, sbp2scsi_complete_command(scsi_id, SBP2_SCSI_STATUS_SELECTION_TIMEOUT, SCpnt, done); } + return 0; - return(0); +done: + SCpnt->result = result; + done(SCpnt); + return 0; } /* @@ -2683,14 +2695,27 @@ static void sbp2scsi_complete_command(struct scsi_id_instance_data *scsi_id, } -static int sbp2scsi_slave_configure (struct scsi_device *sdev) +static int sbp2scsi_slave_alloc(struct scsi_device *sdev) { - blk_queue_dma_alignment(sdev->request_queue, (512 - 1)); + ((struct scsi_id_instance_data *)sdev->host->hostdata[0])->sdev = sdev; + return 0; +} + +static int sbp2scsi_slave_configure(struct scsi_device *sdev) +{ + blk_queue_dma_alignment(sdev->request_queue, (512 - 1)); return 0; } +static void sbp2scsi_slave_destroy(struct scsi_device *sdev) +{ + ((struct scsi_id_instance_data *)sdev->host->hostdata[0])->sdev = NULL; + return; +} + + /* * Called by scsi stack when something has really gone wrong. Usually * called when a command has timed-out for some reason. @@ -2705,7 +2730,7 @@ static int sbp2scsi_abort(struct scsi_cmnd *SCpnt) SBP2_ERR("aborting sbp2 command"); scsi_print_command(SCpnt); - if (scsi_id) { + if (sbp2util_node_is_available(scsi_id)) { /* * Right now, just return any matching command structures @@ -2742,31 +2767,24 @@ static int sbp2scsi_abort(struct scsi_cmnd *SCpnt) /* * Called by scsi stack when something has really gone wrong. */ -static int __sbp2scsi_reset(struct scsi_cmnd *SCpnt) +static int sbp2scsi_reset(struct scsi_cmnd *SCpnt) { struct scsi_id_instance_data *scsi_id = (struct scsi_id_instance_data *)SCpnt->device->host->hostdata[0]; + unsigned long flags; SBP2_ERR("reset requested"); - if (scsi_id) { + spin_lock_irqsave(SCpnt->device->host->host_lock, flags); + + if (sbp2util_node_is_available(scsi_id)) { SBP2_ERR("Generating sbp2 fetch agent reset"); sbp2_agent_reset(scsi_id, 0); } - return(SUCCESS); -} - -static int sbp2scsi_reset(struct scsi_cmnd *SCpnt) -{ - unsigned long flags; - int rc; - - spin_lock_irqsave(SCpnt->device->host->host_lock, flags); - rc = __sbp2scsi_reset(SCpnt); spin_unlock_irqrestore(SCpnt->device->host->host_lock, flags); - return rc; + return SUCCESS; } static const char *sbp2scsi_info (struct Scsi_Host *host) @@ -2817,7 +2835,9 @@ static struct scsi_host_template scsi_driver_template = { .eh_device_reset_handler = sbp2scsi_reset, .eh_bus_reset_handler = sbp2scsi_reset, .eh_host_reset_handler = sbp2scsi_reset, + .slave_alloc = sbp2scsi_slave_alloc, .slave_configure = sbp2scsi_slave_configure, + .slave_destroy = sbp2scsi_slave_destroy, .this_id = -1, .sg_tablesize = SG_ALL, .use_clustering = ENABLE_CLUSTERING, -- cgit v1.2.3 From 2bab359a5009f330b12a4ed09a57d3d2ac6b3483 Mon Sep 17 00:00:00 2001 From: Jody McIntyre Date: Fri, 30 Sep 2005 11:59:07 -0700 Subject: [PATCH] sbp2: default to serialize_io=1 Set serialize_io=1 by default. This is safer and required by seemingly more and more hardware. It causes little or no performance loss for S400 devices. Performance of S800 1394b devices may drop by 25...30%. Therefore make the parameter's description and dmesg message clearer about performance impact. Update description of the max_speed parameter too. IEEE1394_SPEED_MAX is currently S800. Signed-off-by: Stefan Richter Signed-off-by: Jody McIntyre Cc: Ben Collins Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/ieee1394/sbp2.c | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/drivers/ieee1394/sbp2.c b/drivers/ieee1394/sbp2.c index 5d86b03979e..12cec7c4a34 100644 --- a/drivers/ieee1394/sbp2.c +++ b/drivers/ieee1394/sbp2.c @@ -97,16 +97,18 @@ static char version[] __devinitdata = */ static int max_speed = IEEE1394_SPEED_MAX; module_param(max_speed, int, 0644); -MODULE_PARM_DESC(max_speed, "Force max speed (3 = 800mb, 2 = 400mb default, 1 = 200mb, 0 = 100mb)"); +MODULE_PARM_DESC(max_speed, "Force max speed (3 = 800mb, 2 = 400mb, 1 = 200mb, 0 = 100mb)"); /* * Set serialize_io to 1 if you'd like only one scsi command sent * down to us at a time (debugging). This might be necessary for very * badly behaved sbp2 devices. + * + * TODO: Make this configurable per device. */ -static int serialize_io; +static int serialize_io = 1; module_param(serialize_io, int, 0444); -MODULE_PARM_DESC(serialize_io, "Serialize all I/O coming down from the scsi drivers (default = 0)"); +MODULE_PARM_DESC(serialize_io, "Serialize I/O coming from scsi drivers (default = 1, faster = 0)"); /* * Bump up max_sectors if you'd like to support very large sized @@ -2857,7 +2859,8 @@ static int sbp2_module_init(void) /* Module load debug option to force one command at a time (serializing I/O) */ if (serialize_io) { - SBP2_ERR("Driver forced to serialize I/O (serialize_io = 1)"); + SBP2_INFO("Driver forced to serialize I/O (serialize_io=1)"); + SBP2_INFO("Try serialize_io=0 for better performance"); scsi_driver_template.can_queue = 1; scsi_driver_template.cmd_per_lun = 1; } -- cgit v1.2.3 From 328699bf0ff4d35a9932ce279441f955e78a890e Mon Sep 17 00:00:00 2001 From: Jody McIntyre Date: Fri, 30 Sep 2005 11:59:08 -0700 Subject: [PATCH] ieee1394: reorder activities after bus reset (fixes device detection) Units were not detected if the local IRM performed a bus reset. ("The root node is not cycle master capable; selecting a new root node and resetting...", often seen with iPods and other SBP-2 devices). Rearrange the order of IRM duties and node scanning. TODO: Audit the ROM caching and parsing code for underlying issues. Signed-off-by: Stefan Richter Signed-off-by: Jody McIntyre Cc: Ben Collins Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/ieee1394/nodemgr.c | 19 +++++++++---------- 1 file changed, 9 insertions(+), 10 deletions(-) diff --git a/drivers/ieee1394/nodemgr.c b/drivers/ieee1394/nodemgr.c index b23322523ef..743f13c81ad 100644 --- a/drivers/ieee1394/nodemgr.c +++ b/drivers/ieee1394/nodemgr.c @@ -1438,9 +1438,13 @@ static int nodemgr_do_irm_duties(struct hpsb_host *host, int cycles) if (host->busmgr_id == 0xffff && host->node_count > 1) { u16 root_node = host->node_count - 1; - struct node_entry *ne = find_entry_by_nodeid(host, root_node | LOCAL_BUS); - if (ne && ne->busopt.cmc) + /* get cycle master capability flag from root node */ + if (host->is_cycmst || + (!hpsb_read(host, LOCAL_BUS | root_node, get_hpsb_generation(host), + (CSR_REGISTER_BASE + CSR_CONFIG_ROM + 2 * sizeof(quadlet_t)), + &bc, sizeof(quadlet_t)) && + be32_to_cpu(bc) & 1 << CSR_CMC_SHIFT)) hpsb_send_phy_config(host, root_node, -1); else { HPSB_DEBUG("The root node is not cycle master capable; " @@ -1557,24 +1561,19 @@ static int nodemgr_host_thread(void *__hi) } } - if (!nodemgr_check_irm_capability(host, reset_cycles)) { + if (!nodemgr_check_irm_capability(host, reset_cycles) || + !nodemgr_do_irm_duties(host, reset_cycles)) { reset_cycles++; up(&nodemgr_serialize); continue; } + reset_cycles = 0; /* Scan our nodes to get the bus options and create node * entries. This does not do the sysfs stuff, since that * would trigger hotplug callbacks and such, which is a * bad idea at this point. */ nodemgr_node_scan(hi, generation); - if (!nodemgr_do_irm_duties(host, reset_cycles)) { - reset_cycles++; - up(&nodemgr_serialize); - continue; - } - - reset_cycles = 0; /* This actually does the full probe, with sysfs * registration. */ -- cgit v1.2.3 From e31a127c2f99b9cb9abc99a1ec22b75194890800 Mon Sep 17 00:00:00 2001 From: Jody McIntyre Date: Fri, 30 Sep 2005 11:59:09 -0700 Subject: [PATCH] ieee1394: skip unnecessary pause when scanning config ROMs Skip a superfluous pause that occured when the config ROM of a node was scanned unsuccessfully. This also occurs if a node without link wrongly enables its "link active" self ID flag. A GWCTech 6-port hub does this. Signed-off-by: Stefan Richter Signed-off-by: Jody McIntyre Cc: Ben Collins Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/ieee1394/nodemgr.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/ieee1394/nodemgr.c b/drivers/ieee1394/nodemgr.c index 743f13c81ad..347ece6b583 100644 --- a/drivers/ieee1394/nodemgr.c +++ b/drivers/ieee1394/nodemgr.c @@ -64,10 +64,10 @@ static int nodemgr_bus_read(struct csr1212_csr *csr, u64 addr, u16 length, struct nodemgr_csr_info *ci = (struct nodemgr_csr_info*)__ci; int i, ret = 0; - for (i = 0; i < 3; i++) { + for (i = 1; ; i++) { ret = hpsb_read(ci->host, ci->nodeid, ci->generation, addr, buffer, length); - if (!ret) + if (!ret || i == 3) break; if (msleep_interruptible(334)) -- cgit v1.2.3 From db2fd664f8ac3664dfd94d624c0a871bee937bd5 Mon Sep 17 00:00:00 2001 From: Jody McIntyre Date: Fri, 30 Sep 2005 11:59:09 -0700 Subject: [PATCH] ieee1394: fix for debug output Fix debug code so it prints the correct speed (was defaulting to 100, so anything > 400 showed only 100). Signed-off-by: Stefan Richter Signed-off-by: Ben Collins Signed-off-by: Jody McIntyre Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/ieee1394/ieee1394_core.c | 32 ++++++++++---------------------- 1 file changed, 10 insertions(+), 22 deletions(-) diff --git a/drivers/ieee1394/ieee1394_core.c b/drivers/ieee1394/ieee1394_core.c index d633770fac8..32a1e016c85 100644 --- a/drivers/ieee1394/ieee1394_core.c +++ b/drivers/ieee1394/ieee1394_core.c @@ -70,7 +70,7 @@ const char *hpsb_speedto_str[] = { "S100", "S200", "S400", "S800", "S1600", "S32 struct class *hpsb_protocol_class; #ifdef CONFIG_IEEE1394_VERBOSEDEBUG -static void dump_packet(const char *text, quadlet_t *data, int size) +static void dump_packet(const char *text, quadlet_t *data, int size, int speed) { int i; @@ -78,12 +78,15 @@ static void dump_packet(const char *text, quadlet_t *data, int size) size = (size > 4 ? 4 : size); printk(KERN_DEBUG "ieee1394: %s", text); + if (speed > -1 && speed < 6) + printk(" at %s", hpsb_speedto_str[speed]); + printk(":"); for (i = 0; i < size; i++) printk(" %08x", data[i]); printk("\n"); } #else -#define dump_packet(x,y,z) +#define dump_packet(a,b,c,d) #endif static void abort_requests(struct hpsb_host *host); @@ -544,8 +547,7 @@ int hpsb_send_packet(struct hpsb_packet *packet) if (packet->data_size) memcpy(((u8*)data) + packet->header_size, packet->data, packet->data_size); - dump_packet("send packet local:", packet->header, - packet->header_size); + dump_packet("send packet local", packet->header, packet->header_size, -1); hpsb_packet_sent(host, packet, packet->expect_response ? ACK_PENDING : ACK_COMPLETE); hpsb_packet_received(host, data, size, 0); @@ -561,21 +563,7 @@ int hpsb_send_packet(struct hpsb_packet *packet) + NODEID_TO_NODE(packet->node_id)]; } -#ifdef CONFIG_IEEE1394_VERBOSEDEBUG - switch (packet->speed_code) { - case 2: - dump_packet("send packet 400:", packet->header, - packet->header_size); - break; - case 1: - dump_packet("send packet 200:", packet->header, - packet->header_size); - break; - default: - dump_packet("send packet 100:", packet->header, - packet->header_size); - } -#endif + dump_packet("send packet", packet->header, packet->header_size, packet->speed_code); return host->driver->transmit_packet(host, packet); } @@ -636,7 +624,7 @@ static void handle_packet_response(struct hpsb_host *host, int tcode, if (packet == NULL) { HPSB_DEBUG("unsolicited response packet received - no tlabel match"); - dump_packet("contents:", data, 16); + dump_packet("contents", data, 16, -1); spin_unlock_irqrestore(&host->pending_packet_queue.lock, flags); return; } @@ -677,7 +665,7 @@ static void handle_packet_response(struct hpsb_host *host, int tcode, if (!tcode_match) { spin_unlock_irqrestore(&host->pending_packet_queue.lock, flags); HPSB_INFO("unsolicited response packet received - tcode mismatch"); - dump_packet("contents:", data, 16); + dump_packet("contents", data, 16, -1); return; } @@ -914,7 +902,7 @@ void hpsb_packet_received(struct hpsb_host *host, quadlet_t *data, size_t size, return; } - dump_packet("received packet:", data, size); + dump_packet("received packet", data, size, -1); tcode = (data[0] >> 4) & 0xf; -- cgit v1.2.3 From 63bea35036540c0e8a309aef9bc37a9acfb520ae Mon Sep 17 00:00:00 2001 From: Jody McIntyre Date: Fri, 30 Sep 2005 11:59:10 -0700 Subject: [PATCH] ieee1394: use time_before() Use of time_before() macro, defined at linux/jiffies.h, which deal with wrapping correctly and are nicer to read. Signed-off-by: Marcelo Feitoza Parisi Signed-off-by: Domen Puncer Signed-off-by: Ben Collins Signed-off-by: Stefan Richter Signed-off-by: Jody McIntyre Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/ieee1394/hosts.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/ieee1394/hosts.c b/drivers/ieee1394/hosts.c index c502c6e9c44..aeeaeb670d0 100644 --- a/drivers/ieee1394/hosts.c +++ b/drivers/ieee1394/hosts.c @@ -18,6 +18,7 @@ #include #include #include +#include #include "csr1212.h" #include "ieee1394.h" @@ -217,7 +218,7 @@ int hpsb_update_config_rom_image(struct hpsb_host *host) /* IEEE 1394a-2000 prohibits using the same generation number * twice in a 60 second period. */ - if (jiffies - host->csr.gen_timestamp[next_gen] < 60 * HZ) + if (time_before(jiffies, host->csr.gen_timestamp[next_gen] + 60 * HZ)) /* Wait 60 seconds from the last time this generation number was * used. */ reset_delay = (60 * HZ) + host->csr.gen_timestamp[next_gen] - jiffies; -- cgit v1.2.3 From 3256cc13983da2cfe45c17788e4f5b379695404e Mon Sep 17 00:00:00 2001 From: Jody McIntyre Date: Fri, 30 Sep 2005 11:59:16 -0700 Subject: [PATCH] ieee1394: trivial edits of a few comments trivial edits of a few comments Signed-off-by: Stefan Richter Signed-off-by: Ben Collins Signed-off-by: Jody McIntyre Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/ieee1394/hosts.h | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/drivers/ieee1394/hosts.h b/drivers/ieee1394/hosts.h index 739e76840d5..38f42112dff 100644 --- a/drivers/ieee1394/hosts.h +++ b/drivers/ieee1394/hosts.h @@ -135,17 +135,17 @@ enum isoctl_cmd { enum reset_types { /* 166 microsecond reset -- only type of reset available on - non-1394a capable IEEE 1394 controllers */ + non-1394a capable controllers */ LONG_RESET, /* Short (arbitrated) reset -- only available on 1394a capable - IEEE 1394 capable controllers */ + controllers */ SHORT_RESET, - /* Variants, that set force_root before issueing the bus reset */ + /* Variants that set force_root before issueing the bus reset */ LONG_RESET_FORCE_ROOT, SHORT_RESET_FORCE_ROOT, - /* Variants, that clear force_root before issueing the bus reset */ + /* Variants that clear force_root before issueing the bus reset */ LONG_RESET_NO_FORCE_ROOT, SHORT_RESET_NO_FORCE_ROOT }; -- cgit v1.2.3 From 998150c3d3cf049da7596875f6fdc253db089a9a Mon Sep 17 00:00:00 2001 From: Jody McIntyre Date: Fri, 30 Sep 2005 11:59:17 -0700 Subject: [PATCH] ieee1394: remove superfluous include in csr1212 Remove superfluous include. Signed-off-by: Jody McIntyre Signed-off-by: Stefan Richter Signed-off-by: Jody McIntyre Cc: Ben Collins Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/ieee1394/csr1212.h | 1 - 1 file changed, 1 deletion(-) diff --git a/drivers/ieee1394/csr1212.h b/drivers/ieee1394/csr1212.h index e6734263a1d..28c5f4b726e 100644 --- a/drivers/ieee1394/csr1212.h +++ b/drivers/ieee1394/csr1212.h @@ -37,7 +37,6 @@ #include #include #include -#include #include #include -- cgit v1.2.3 From 3ae3d0d4ae4131563d9eb55859f4fa5bd39059bd Mon Sep 17 00:00:00 2001 From: Jody McIntyre Date: Fri, 30 Sep 2005 11:59:18 -0700 Subject: [PATCH] eth1394: workaround limitation in rawiso routines Work around limitation in rawiso routines. Required with 1394b cards on architectures where PAGE_SIZE is 4096. Based on a previous patch by Ben Collins. Signed-off-by: Jody McIntyre Cc: Ben Collins Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/ieee1394/eth1394.c | 12 +++++------- drivers/ieee1394/eth1394.h | 6 ++++++ 2 files changed, 11 insertions(+), 7 deletions(-) diff --git a/drivers/ieee1394/eth1394.c b/drivers/ieee1394/eth1394.c index cd53c174ced..4802bbbb6dc 100644 --- a/drivers/ieee1394/eth1394.c +++ b/drivers/ieee1394/eth1394.c @@ -89,7 +89,7 @@ #define TRACE() printk(KERN_ERR "%s:%s[%d] ---- TRACE\n", driver_name, __FUNCTION__, __LINE__) static char version[] __devinitdata = - "$Rev: 1264 $ Ben Collins "; + "$Rev: 1312 $ Ben Collins "; struct fragment_info { struct list_head list; @@ -221,9 +221,7 @@ static int ether1394_open (struct net_device *dev) if (priv->bc_state == ETHER1394_BC_ERROR) { /* we'll try again */ priv->iso = hpsb_iso_recv_init(priv->host, - ETHER1394_GASP_BUFFERS * 2 * - (1 << (priv->host->csr.max_rec + - 1)), + ETHER1394_ISO_BUF_SIZE, ETHER1394_GASP_BUFFERS, priv->broadcast_channel, HPSB_ISO_DMA_PACKET_PER_BUFFER, @@ -635,8 +633,8 @@ static void ether1394_add_host (struct hpsb_host *host) * be checked when the eth device is opened. */ priv->broadcast_channel = host->csr.broadcast_channel & 0x3f; - priv->iso = hpsb_iso_recv_init(host, (ETHER1394_GASP_BUFFERS * 2 * - (1 << (host->csr.max_rec + 1))), + priv->iso = hpsb_iso_recv_init(host, + ETHER1394_ISO_BUF_SIZE, ETHER1394_GASP_BUFFERS, priv->broadcast_channel, HPSB_ISO_DMA_PACKET_PER_BUFFER, @@ -1770,7 +1768,7 @@ fail: static void ether1394_get_drvinfo(struct net_device *dev, struct ethtool_drvinfo *info) { strcpy (info->driver, driver_name); - strcpy (info->version, "$Rev: 1264 $"); + strcpy (info->version, "$Rev: 1312 $"); /* FIXME XXX provide sane businfo */ strcpy (info->bus_info, "ieee1394"); } diff --git a/drivers/ieee1394/eth1394.h b/drivers/ieee1394/eth1394.h index ed8f1c4b7fd..a77213cfc48 100644 --- a/drivers/ieee1394/eth1394.h +++ b/drivers/ieee1394/eth1394.h @@ -44,6 +44,12 @@ #define ETHER1394_GASP_BUFFERS 16 +/* rawiso buffer size - due to a limitation in rawiso, we must limit each + * GASP buffer to be less than PAGE_SIZE. */ +#define ETHER1394_ISO_BUF_SIZE ETHER1394_GASP_BUFFERS * \ + min((unsigned int)PAGE_SIZE, \ + 2 * (1U << (priv->host->csr.max_rec + 1))) + /* Node set == 64 */ #define NODE_SET (ALL_NODES + 1) -- cgit v1.2.3 From f31c9cf3bd6bc1f3e29807ba59d0c7d711385a06 Mon Sep 17 00:00:00 2001 From: Jody McIntyre Date: Fri, 30 Sep 2005 11:59:18 -0700 Subject: [PATCH] ieee1394: delete legacy module aliases amdtp, dv1394, raw1394, video1394: Delete legacy module aliases. The macros did not work and the aliases are not needed nowadays. Signed-off-by: Stefan Richter Signed-off-by: Ben Collins Signed-off-by: Jody McIntyre Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/ieee1394/amdtp.c | 1 - drivers/ieee1394/dv1394.c | 1 - drivers/ieee1394/raw1394.c | 1 - drivers/ieee1394/video1394.c | 1 - 4 files changed, 4 deletions(-) diff --git a/drivers/ieee1394/amdtp.c b/drivers/ieee1394/amdtp.c index 84ae027b021..e8e28569a66 100644 --- a/drivers/ieee1394/amdtp.c +++ b/drivers/ieee1394/amdtp.c @@ -1297,4 +1297,3 @@ static void __exit amdtp_exit_module (void) module_init(amdtp_init_module); module_exit(amdtp_exit_module); -MODULE_ALIAS_CHARDEV(IEEE1394_MAJOR, IEEE1394_MINOR_BLOCK_AMDTP * 16); diff --git a/drivers/ieee1394/dv1394.c b/drivers/ieee1394/dv1394.c index 4538b0235ca..e34730c7a87 100644 --- a/drivers/ieee1394/dv1394.c +++ b/drivers/ieee1394/dv1394.c @@ -2660,4 +2660,3 @@ static int __init dv1394_init_module(void) module_init(dv1394_init_module); module_exit(dv1394_exit_module); -MODULE_ALIAS_CHARDEV(IEEE1394_MAJOR, IEEE1394_MINOR_BLOCK_DV1394 * 16); diff --git a/drivers/ieee1394/raw1394.c b/drivers/ieee1394/raw1394.c index b4fa14793fe..5fe4f2ba097 100644 --- a/drivers/ieee1394/raw1394.c +++ b/drivers/ieee1394/raw1394.c @@ -2958,4 +2958,3 @@ static void __exit cleanup_raw1394(void) module_init(init_raw1394); module_exit(cleanup_raw1394); MODULE_LICENSE("GPL"); -MODULE_ALIAS_CHARDEV(IEEE1394_MAJOR, IEEE1394_MINOR_BLOCK_RAW1394 * 16); diff --git a/drivers/ieee1394/video1394.c b/drivers/ieee1394/video1394.c index 9d6facf2f78..11be9c9c82a 100644 --- a/drivers/ieee1394/video1394.c +++ b/drivers/ieee1394/video1394.c @@ -1571,4 +1571,3 @@ static int __init video1394_init_module (void) module_init(video1394_init_module); module_exit(video1394_exit_module); -MODULE_ALIAS_CHARDEV(IEEE1394_MAJOR, IEEE1394_MINOR_BLOCK_VIDEO1394 * 16); -- cgit v1.2.3 From 32e7a04faa29f50f65e06d43a9029bb607743e76 Mon Sep 17 00:00:00 2001 From: Jody McIntyre Date: Fri, 30 Sep 2005 11:59:19 -0700 Subject: [PATCH] ohci1394: less noise in dmesg less noise in dmesg Signed-off-by: Ben Collins Signed-off-by: Stefan Richter Signed-off-by: Jody McIntyre Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/ieee1394/ohci1394.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/ieee1394/ohci1394.c b/drivers/ieee1394/ohci1394.c index 27018c8efc2..6a6acbd80af 100644 --- a/drivers/ieee1394/ohci1394.c +++ b/drivers/ieee1394/ohci1394.c @@ -162,7 +162,7 @@ printk(level "%s: " fmt "\n" , OHCI1394_DRIVER_NAME , ## args) printk(level "%s: fw-host%d: " fmt "\n" , OHCI1394_DRIVER_NAME, ohci->host->id , ## args) static char version[] __devinitdata = - "$Rev: 1299 $ Ben Collins "; + "$Rev: 1313 $ Ben Collins "; /* Module Parameters */ static int phys_dma = 1; @@ -1084,7 +1084,7 @@ static int ohci_devctl(struct hpsb_host *host, enum devctl_cmd cmd, int arg) initialize_dma_rcv_ctx(&ohci->ir_legacy_context, 1); if (printk_ratelimit()) - PRINT(KERN_ERR, "IR legacy activated"); + DBGMSG("IR legacy activated"); } spin_lock_irqsave(&ohci->IR_channel_lock, flags); -- cgit v1.2.3 From 2dd960d66bc12b6b206e63104636514e5da0ddb7 Mon Sep 17 00:00:00 2001 From: "Zhang, Yanmin" Date: Fri, 30 Sep 2005 11:59:20 -0700 Subject: [PATCH] utilization of kprobe_mutex is incorrect on x86_64 The up()/down() orders are incorrect in arch/x86_64/kprobes.c file. kprobe_mutext is used to protect the free kprobe instruction slot list. arch_prepare_kprobe applies for a slot from the free list, and arch_remove_kprobe returns a slot to the free list. The incorrect up()/down() orders to operate on kprobe_mutex fail to protect the free list. If 2 threads try to get/return kprobe instruction slot at the same time, the free slot list might be broken, or a free slot might be applied by 2 threads. Signed-off-by: Zhang Yanmin Cc: Andi Kleen Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/x86_64/kernel/kprobes.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/arch/x86_64/kernel/kprobes.c b/arch/x86_64/kernel/kprobes.c index df08c43276a..76a28b007be 100644 --- a/arch/x86_64/kernel/kprobes.c +++ b/arch/x86_64/kernel/kprobes.c @@ -77,9 +77,9 @@ static inline int is_IF_modifier(kprobe_opcode_t *insn) int __kprobes arch_prepare_kprobe(struct kprobe *p) { /* insn: must be on special executable page on x86_64. */ - up(&kprobe_mutex); - p->ainsn.insn = get_insn_slot(); down(&kprobe_mutex); + p->ainsn.insn = get_insn_slot(); + up(&kprobe_mutex); if (!p->ainsn.insn) { return -ENOMEM; } @@ -231,9 +231,9 @@ void __kprobes arch_disarm_kprobe(struct kprobe *p) void __kprobes arch_remove_kprobe(struct kprobe *p) { - up(&kprobe_mutex); - free_insn_slot(p->ainsn.insn); down(&kprobe_mutex); + free_insn_slot(p->ainsn.insn); + up(&kprobe_mutex); } static inline void save_previous_kprobe(void) -- cgit v1.2.3 From e6a045a5b89037ae87c8c1bc84403f1d498e52a1 Mon Sep 17 00:00:00 2001 From: Ravikiran G Thirumalai Date: Fri, 30 Sep 2005 11:59:21 -0700 Subject: [PATCH] x86_64: fix the BP node_to_cpumask Fix the BP node_to_cpumask. 2.6.14-rc* broke the boot cpu bit as the cpu_to_node(0) is now not setup early enough for numa_init_array. cpu_to_node[] is setup much later at srat_detect_node on acpi srat based em64t machines. This seems like a problem on amd machines too, Tested on em64t though. /sys/devices/system/node/node0/cpumap shows up sanely after this patch. Signed off by: Ravikiran Thirumalai Signed-off-by: Shai Fultheim Cc: Andi Kleen Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/x86_64/mm/numa.c | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/arch/x86_64/mm/numa.c b/arch/x86_64/mm/numa.c index 80a49d9bd8a..68ad7585351 100644 --- a/arch/x86_64/mm/numa.c +++ b/arch/x86_64/mm/numa.c @@ -178,7 +178,6 @@ void __init numa_init_array(void) rr++; } - set_bit(0, &node_to_cpumask[cpu_to_node(0)]); } #ifdef CONFIG_NUMA_EMU @@ -266,9 +265,7 @@ void __init numa_initmem_init(unsigned long start_pfn, unsigned long end_pfn) __cpuinit void numa_add_cpu(int cpu) { - /* BP is initialized elsewhere */ - if (cpu) - set_bit(cpu, &node_to_cpumask[cpu_to_node(cpu)]); + set_bit(cpu, &node_to_cpumask[cpu_to_node(cpu)]); } unsigned long __init numa_free_all_bootmem(void) -- cgit v1.2.3 From 85cc5135ace4c8b75d7b4e1ea9fe15a7fcbd1516 Mon Sep 17 00:00:00 2001 From: Ravikiran G Thirumalai Date: Fri, 30 Sep 2005 11:59:22 -0700 Subject: [PATCH] x86_64 early numa init fix The tests Alok carried out on Petr's box confirmed that cpu_to_node[BP] is not setup early enough by numa_init_array due to the x86_64 changes in 2.6.14-rc*, and unfortunately set wrongly by the work around code in numa_init_array(). cpu_to_node[0] gets set with 1 early and later gets set properly to 0 during identify_cpu() when all cpus are brought up, but confusing the numa slab in the process. Here is a quick fix for this. The right fix obviously is to have cpu_to_node[bsp] setup early for numa_init_array(). The following patch will fix the problem now, and the code can stay on even when cpu_to_node{BP] gets fixed early correctly. Thanks to Petr for access to his box. Signed off by: Ravikiran Thirumalai Signed-off-by: Alok N Kataria Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/x86_64/mm/numa.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/arch/x86_64/mm/numa.c b/arch/x86_64/mm/numa.c index 68ad7585351..21480382100 100644 --- a/arch/x86_64/mm/numa.c +++ b/arch/x86_64/mm/numa.c @@ -167,15 +167,14 @@ void __init numa_init_array(void) mapping. To avoid this fill in the mapping for all possible CPUs, as the number of CPUs is not known yet. We round robin the existing nodes. */ - rr = 0; + rr = first_node(node_online_map); for (i = 0; i < NR_CPUS; i++) { if (cpu_to_node[i] != NUMA_NO_NODE) continue; + cpu_to_node[i] = rr; rr = next_node(rr, node_online_map); if (rr == MAX_NUMNODES) rr = first_node(node_online_map); - cpu_to_node[i] = rr; - rr++; } } -- cgit v1.2.3 From aba7a22f291c13448177b28e0e3d01260ed04fbe Mon Sep 17 00:00:00 2001 From: "Michael S. Tsirkin" Date: Fri, 30 Sep 2005 13:55:50 -0700 Subject: [IB] mthca: Fix memory leak on device close Remember to free the multicast group context memory table. Signed-off-by: Michael S. Tsirkin Signed-off-by: Roland Dreier --- drivers/infiniband/hw/mthca/mthca_main.c | 45 +++++++++++++++----------------- 1 file changed, 21 insertions(+), 24 deletions(-) diff --git a/drivers/infiniband/hw/mthca/mthca_main.c b/drivers/infiniband/hw/mthca/mthca_main.c index ffbcd40418d..23a3f56c789 100644 --- a/drivers/infiniband/hw/mthca/mthca_main.c +++ b/drivers/infiniband/hw/mthca/mthca_main.c @@ -503,6 +503,25 @@ err_free_aux: return err; } +static void mthca_free_icms(struct mthca_dev *mdev) +{ + u8 status; + + mthca_free_icm_table(mdev, mdev->mcg_table.table); + if (mdev->mthca_flags & MTHCA_FLAG_SRQ) + mthca_free_icm_table(mdev, mdev->srq_table.table); + mthca_free_icm_table(mdev, mdev->cq_table.table); + mthca_free_icm_table(mdev, mdev->qp_table.rdb_table); + mthca_free_icm_table(mdev, mdev->qp_table.eqp_table); + mthca_free_icm_table(mdev, mdev->qp_table.qp_table); + mthca_free_icm_table(mdev, mdev->mr_table.mpt_table); + mthca_free_icm_table(mdev, mdev->mr_table.mtt_table); + mthca_unmap_eq_icm(mdev); + + mthca_UNMAP_ICM_AUX(mdev, &status); + mthca_free_icm(mdev, mdev->fw.arbel.aux_icm); +} + static int __devinit mthca_init_arbel(struct mthca_dev *mdev) { struct mthca_dev_lim dev_lim; @@ -580,18 +599,7 @@ static int __devinit mthca_init_arbel(struct mthca_dev *mdev) return 0; err_free_icm: - if (mdev->mthca_flags & MTHCA_FLAG_SRQ) - mthca_free_icm_table(mdev, mdev->srq_table.table); - mthca_free_icm_table(mdev, mdev->cq_table.table); - mthca_free_icm_table(mdev, mdev->qp_table.rdb_table); - mthca_free_icm_table(mdev, mdev->qp_table.eqp_table); - mthca_free_icm_table(mdev, mdev->qp_table.qp_table); - mthca_free_icm_table(mdev, mdev->mr_table.mpt_table); - mthca_free_icm_table(mdev, mdev->mr_table.mtt_table); - mthca_unmap_eq_icm(mdev); - - mthca_UNMAP_ICM_AUX(mdev, &status); - mthca_free_icm(mdev, mdev->fw.arbel.aux_icm); + mthca_free_icms(mdev); err_stop_fw: mthca_UNMAP_FA(mdev, &status); @@ -611,18 +619,7 @@ static void mthca_close_hca(struct mthca_dev *mdev) mthca_CLOSE_HCA(mdev, 0, &status); if (mthca_is_memfree(mdev)) { - if (mdev->mthca_flags & MTHCA_FLAG_SRQ) - mthca_free_icm_table(mdev, mdev->srq_table.table); - mthca_free_icm_table(mdev, mdev->cq_table.table); - mthca_free_icm_table(mdev, mdev->qp_table.rdb_table); - mthca_free_icm_table(mdev, mdev->qp_table.eqp_table); - mthca_free_icm_table(mdev, mdev->qp_table.qp_table); - mthca_free_icm_table(mdev, mdev->mr_table.mpt_table); - mthca_free_icm_table(mdev, mdev->mr_table.mtt_table); - mthca_unmap_eq_icm(mdev); - - mthca_UNMAP_ICM_AUX(mdev, &status); - mthca_free_icm(mdev, mdev->fw.arbel.aux_icm); + mthca_free_icms(mdev); mthca_UNMAP_FA(mdev, &status); mthca_free_icm(mdev, mdev->fw.arbel.fw_icm); -- cgit v1.2.3 From 1c9426e8a59461688bb451e006456987b198e4c0 Mon Sep 17 00:00:00 2001 From: Linus Torvalds Date: Fri, 30 Sep 2005 14:17:35 -0700 Subject: Linux v2.6.14-rc3 --- Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile b/Makefile index 8cf6becf68d..fdb96bc8508 100644 --- a/Makefile +++ b/Makefile @@ -1,7 +1,7 @@ VERSION = 2 PATCHLEVEL = 6 SUBLEVEL = 14 -EXTRAVERSION =-rc2 +EXTRAVERSION =-rc3 NAME=Affluent Albatross # *DOCUMENTATION* -- cgit v1.2.3 -- cgit v1.2.3 From a9487e48a34d7ad606f40a76080475a522a27cff Mon Sep 17 00:00:00 2001 From: Benjamin Herrenschmidt Date: Sat, 1 Oct 2005 09:21:25 +1000 Subject: [PATCH] pmac: fix cpufreq for old tipb 550Mhz The old 550Mhz titanium powerbook can switch to a lower frequency (500Mhz). A user has been repeately reporting overtemp conditions on his machine at high speed so this simple patch adds support to PowerMac cpufreq for this machine. The difference in frequency isn't big but seem enough to fix that user's problems. The patch has been around for some time now and doesn't seem to cause any problem, so I suppose it could go in now. Signed-off-by: Benjamin Herrenschmidt Signed-off-by: Alain RICHARD Signed-off-by: Linus Torvalds --- arch/ppc/platforms/pmac_cpufreq.c | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/arch/ppc/platforms/pmac_cpufreq.c b/arch/ppc/platforms/pmac_cpufreq.c index c0605244edd..d4bc5f67ec5 100644 --- a/arch/ppc/platforms/pmac_cpufreq.c +++ b/arch/ppc/platforms/pmac_cpufreq.c @@ -695,6 +695,13 @@ static int __init pmac_cpufreq_setup(void) set_speed_proc = pmu_set_cpu_speed; is_pmu_based = 1; } + /* Else check for TiPb 550 */ + else if (machine_is_compatible("PowerBook3,3") && cur_freq == 550000) { + hi_freq = cur_freq; + low_freq = 500000; + set_speed_proc = pmu_set_cpu_speed; + is_pmu_based = 1; + } /* Else check for TiPb 400 & 500 */ else if (machine_is_compatible("PowerBook3,2")) { /* We only know about the 400 MHz and the 500Mhz model -- cgit v1.2.3 From f0e837d9182d7903bde3ebafbd1d0d68c6d32d43 Mon Sep 17 00:00:00 2001 From: Francois Romieu Date: Fri, 30 Sep 2005 16:54:02 -0700 Subject: [PATCH] r8169: tone down the r8169 driver Tone down the r8169 driver As an alternative, people can use the boot time 'debug' option and/or use 'ethtool -s ethX msglvl xyz'. The different messages are listed at: http://www.zoreil.com/~romieu/r8169/doc/msglvl.txt Signed-off-by: Francois Romieu Cc: Jeff Garzik Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/net/r8169.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/net/r8169.c b/drivers/net/r8169.c index f9223c1c5aa..afb3f186b88 100644 --- a/drivers/net/r8169.c +++ b/drivers/net/r8169.c @@ -92,8 +92,7 @@ VERSION 2.2LK <2005/01/25> #endif /* RTL8169_DEBUG */ #define R8169_MSG_DEFAULT \ - (NETIF_MSG_DRV | NETIF_MSG_PROBE | NETIF_MSG_LINK | NETIF_MSG_IFUP | \ - NETIF_MSG_IFDOWN) + (NETIF_MSG_DRV | NETIF_MSG_PROBE | NETIF_MSG_IFUP | NETIF_MSG_IFDOWN) #define TX_BUFFS_AVAIL(tp) \ (tp->dirty_tx + NUM_TX_DESC - tp->cur_tx - 1) -- cgit v1.2.3 From 702c96d55059b4a8e5b1eb112ee3b1804708a1bd Mon Sep 17 00:00:00 2001 From: Deepak Saxena Date: Fri, 30 Sep 2005 16:20:22 -0700 Subject: [PATCH] ARM: Fix IXP2000 serial port resource range. For real this time. Serial port only needs 32 bytes of resource space but we are currently asking for 64K. Signed-off-by: Deepak Saxena [ diff went missing first time due to corrupted patch ] Signed-off-by: Linus Torvalds --- arch/arm/mach-ixp2000/core.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/arm/mach-ixp2000/core.c b/arch/arm/mach-ixp2000/core.c index f34797a46a2..f4d7f1f6ef8 100644 --- a/arch/arm/mach-ixp2000/core.c +++ b/arch/arm/mach-ixp2000/core.c @@ -167,7 +167,7 @@ static struct plat_serial8250_port ixp2000_serial_port[] = { static struct resource ixp2000_uart_resource = { .start = IXP2000_UART_PHYS_BASE, - .end = IXP2000_UART_PHYS_BASE + 0xffff, + .end = IXP2000_UART_PHYS_BASE + 0x1f, .flags = IORESOURCE_MEM, }; -- cgit v1.2.3 From 2d8ab6ad6edf0e8709da9ad24e3f023503f76cee Mon Sep 17 00:00:00 2001 From: Ananth N Mavinakayanahalli Date: Sat, 1 Oct 2005 13:14:17 -0400 Subject: [PATCH] ppc64: fix up()/down() usage for kprobe_mutex The incorrect kprobe_mutex usage on x86_64 had percolated to ppc64 too. First noticed by Yanmin Zhang. Signed-off-by: Ananth N Mavinakayanahalli Signed-off-by: Linus Torvalds --- arch/ppc64/kernel/kprobes.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/arch/ppc64/kernel/kprobes.c b/arch/ppc64/kernel/kprobes.c index 7e80d49c589..9c6facc24f7 100644 --- a/arch/ppc64/kernel/kprobes.c +++ b/arch/ppc64/kernel/kprobes.c @@ -59,9 +59,9 @@ int __kprobes arch_prepare_kprobe(struct kprobe *p) /* insn must be on a special executable page on ppc64 */ if (!ret) { - up(&kprobe_mutex); - p->ainsn.insn = get_insn_slot(); down(&kprobe_mutex); + p->ainsn.insn = get_insn_slot(); + up(&kprobe_mutex); if (!p->ainsn.insn) ret = -ENOMEM; } @@ -90,9 +90,9 @@ void __kprobes arch_disarm_kprobe(struct kprobe *p) void __kprobes arch_remove_kprobe(struct kprobe *p) { - up(&kprobe_mutex); - free_insn_slot(p->ainsn.insn); down(&kprobe_mutex); + free_insn_slot(p->ainsn.insn); + up(&kprobe_mutex); } static inline void prepare_singlestep(struct kprobe *p, struct pt_regs *regs) -- cgit v1.2.3 From fd2e54b35bd70d11c160ded4834e2378e915356e Mon Sep 17 00:00:00 2001 From: Diego Calleja Date: Sat, 1 Oct 2005 17:00:48 +0200 Subject: [PATCH] trivial #if -> #ifdef Use '#ifdef' consistently on __KERNEL__. This was reported as bug #5340 (isn't easier to send a fix than report the bug?!) Signed-off-by: Diego Calleja Signed-off-by: Linus Torvalds --- include/linux/mod_devicetable.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/linux/mod_devicetable.h b/include/linux/mod_devicetable.h index 4ed2107bc02..2f0299a448f 100644 --- a/include/linux/mod_devicetable.h +++ b/include/linux/mod_devicetable.h @@ -183,7 +183,7 @@ struct of_device_id char name[32]; char type[32]; char compatible[128]; -#if __KERNEL__ +#ifdef __KERNEL__ void *data; #else kernel_ulong_t data; -- cgit v1.2.3 From 14bf01bb0599c89fc7f426d20353b76e12555308 Mon Sep 17 00:00:00 2001 From: Linus Torvalds Date: Sat, 1 Oct 2005 11:04:18 -0700 Subject: Fix inequality comparison against "task->state" We should always use bitmask ops, rather than depend on some ordering of the different states. With the TASK_NONINTERACTIVE flag, the inequality doesn't really work. Oleg Nesterov argues (likely correctly) that this test is unnecessary in the first place. However, the minimal fix for now is to at least make it work in the presense of TASK_NONINTERACTIVE. Waiting for consensus from Roland & co on potential bigger cleanups. Signed-off-by: Linus Torvalds --- kernel/exit.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/kernel/exit.c b/kernel/exit.c index ee6d8b8abef..43077732619 100644 --- a/kernel/exit.c +++ b/kernel/exit.c @@ -1203,7 +1203,7 @@ static int wait_task_stopped(task_t *p, int delayed_group_leader, int noreap, exit_code = p->exit_code; if (unlikely(!exit_code) || - unlikely(p->state > TASK_STOPPED)) + unlikely(p->state & TASK_TRACED)) goto bail_ref; return wait_noreap_copyout(p, pid, uid, why, (exit_code << 8) | 0x7f, -- cgit v1.2.3 From 9f4426dde2be352aabc326539eccc726cea2d98c Mon Sep 17 00:00:00 2001 From: Vincent Sanders Date: Sat, 1 Oct 2005 22:56:34 +0100 Subject: [ARM] 2944/1: GCC 4 mx1ads serial driver compile fix Patch from Vincent Sanders When building the mx1ads ARM platforms the serial driver fails to compile with GCC 4.01 due to extern/static ambiguity. Signed-off-by: Vincent Sanders Signed-off-by: Russell King --- drivers/serial/imx.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/serial/imx.c b/drivers/serial/imx.c index 4c985e6b378..4e1e80adaf1 100644 --- a/drivers/serial/imx.c +++ b/drivers/serial/imx.c @@ -860,7 +860,7 @@ imx_console_setup(struct console *co, char *options) return uart_set_options(&sport->port, co, baud, parity, bits, flow); } -extern struct uart_driver imx_reg; +static struct uart_driver imx_reg; static struct console imx_console = { .name = "ttySMX", .write = imx_console_write, -- cgit v1.2.3 From 31f919c3296a30427b18458b13c308513a62c3b9 Mon Sep 17 00:00:00 2001 From: Vincent Sanders Date: Sat, 1 Oct 2005 22:56:34 +0100 Subject: [ARM] 2945/1: ARM fortunet fails to build because of missing include Patch from Vincent Sanders When building the fortunet ARM platform it fails to compile because of missing include. Signed-off-by: Vincent Sanders Signed-off-by: Russell King --- arch/arm/mach-clps711x/fortunet.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/arch/arm/mach-clps711x/fortunet.c b/arch/arm/mach-clps711x/fortunet.c index f83a59761e0..3d88da0c287 100644 --- a/arch/arm/mach-clps711x/fortunet.c +++ b/arch/arm/mach-clps711x/fortunet.c @@ -31,6 +31,8 @@ #include +#include + #include "common.h" struct meminfo memmap = { -- cgit v1.2.3 From 14bfd1ff94f519a59b1e88e682819332d7e98171 Mon Sep 17 00:00:00 2001 From: Sven Henkel Date: Sun, 2 Oct 2005 08:29:18 +1000 Subject: [PATCH] pmac/radeonfb: Add suspend support for M11 chip in new iBook 12" This adds suspend support for the Radeon M11 chip in 12" iBooks manufactured after July 2005. I don't know if the new 14" iBooks also have that chip, so they might also be supported. The chip identifies itself as "RV350 NV" (pci id 0x4e56), revision 0x80. Apple calls it "Snowy", xfree86 names it "ATI FireGL Mobility T2 (M11) NV (AGP)". So, we seem to be lucky here: The suspend-code for the M10 (which also is a "RV350 NV") works flawless for that chip. Signed-off-by: Sven Henkel Signed-off-by: Benjamin Herrenschmidt Signed-off-by: Linus Torvalds --- drivers/video/aty/radeon_pm.c | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/drivers/video/aty/radeon_pm.c b/drivers/video/aty/radeon_pm.c index 59a1b6f8506..097d668c4fe 100644 --- a/drivers/video/aty/radeon_pm.c +++ b/drivers/video/aty/radeon_pm.c @@ -62,9 +62,9 @@ static void radeon_pm_disable_dynamic_mode(struct radeonfb_info *rinfo) OUTPLL(pllSCLK_CNTL, tmp); return; } - /* RV350 (M10) */ + /* RV350 (M10/M11) */ if (rinfo->family == CHIP_FAMILY_RV350) { - /* for RV350/M10, no delays are required. */ + /* for RV350/M10/M11, no delays are required. */ tmp = INPLL(pllSCLK_CNTL2); tmp |= (SCLK_CNTL2__R300_FORCE_TCL | SCLK_CNTL2__R300_FORCE_GA | @@ -248,7 +248,7 @@ static void radeon_pm_enable_dynamic_mode(struct radeonfb_info *rinfo) return; } - /* M10 */ + /* M10/M11 */ if (rinfo->family == CHIP_FAMILY_RV350) { tmp = INPLL(pllSCLK_CNTL2); tmp &= ~(SCLK_CNTL2__R300_FORCE_TCL | @@ -1155,7 +1155,7 @@ static void radeon_pm_full_reset_sdram(struct radeonfb_info *rinfo) OUTREG( CRTC_GEN_CNTL, (crtcGenCntl | CRTC_GEN_CNTL__CRTC_DISP_REQ_EN_B) ); OUTREG( CRTC2_GEN_CNTL, (crtcGenCntl2 | CRTC2_GEN_CNTL__CRTC2_DISP_REQ_EN_B) ); - /* This is the code for the Aluminium PowerBooks M10 */ + /* This is the code for the Aluminium PowerBooks M10 / iBooks M11 */ if (rinfo->family == CHIP_FAMILY_RV350) { u32 sdram_mode_reg = rinfo->save_regs[35]; static u32 default_mrtable[] = @@ -2741,9 +2741,11 @@ void radeonfb_pm_init(struct radeonfb_info *rinfo, int dynclk) rinfo->pm_mode |= radeon_pm_d2; /* We can restart Jasper (M10 chip in albooks), BlueStone (7500 chip - * in some desktop G4s), and Via (M9+ chip on iBook G4) + * in some desktop G4s), Via (M9+ chip on iBook G4) and + * Snowy (M11 chip on iBook G4 manufactured after July 2005) */ - if (!strcmp(rinfo->of_node->name, "ATY,JasperParent")) { + if (!strcmp(rinfo->of_node->name, "ATY,JasperParent") || + !strcmp(rinfo->of_node->name, "ATY,SnowyParent")) { rinfo->reinit_func = radeon_reinitialize_M10; rinfo->pm_mode |= radeon_pm_off; } -- cgit v1.2.3 From 036bfdcb0dfa39fc1ff5ded196b5fd92f1bb9ea8 Mon Sep 17 00:00:00 2001 From: Sven Henkel Date: Sun, 2 Oct 2005 08:30:33 +1000 Subject: [PATCH] ppc32: Add new iBook 12" to PowerMac models table This adds the new iBook G4 (manufactured after July 2005) to the PowerMac models table. The model name (PowerBook6,7) is taken from a 12" iBook, I don't know if it also matches the 14" version. The patch applies to a vanilla 2.6.13.2 kernel. Signed-off-by: Sven Henkel Signed-off-by: Benjamin Herrenschmidt Signed-off-by: Linus Torvalds --- arch/ppc/platforms/pmac_feature.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/arch/ppc/platforms/pmac_feature.c b/arch/ppc/platforms/pmac_feature.c index 867336ad5d3..dd6d45ae050 100644 --- a/arch/ppc/platforms/pmac_feature.c +++ b/arch/ppc/platforms/pmac_feature.c @@ -2337,6 +2337,10 @@ static struct pmac_mb_def pmac_mb_defs[] __pmacdata = { PMAC_TYPE_UNKNOWN_INTREPID, intrepid_features, PMAC_MB_MAY_SLEEP | PMAC_MB_HAS_FW_POWER | PMAC_MB_MOBILE, }, + { "PowerBook6,7", "iBook G4", + PMAC_TYPE_UNKNOWN_INTREPID, intrepid_features, + PMAC_MB_MAY_SLEEP | PMAC_MB_HAS_FW_POWER | PMAC_MB_MOBILE, + }, { "PowerBook6,8", "PowerBook G4 12\"", PMAC_TYPE_UNKNOWN_INTREPID, intrepid_features, PMAC_MB_MAY_SLEEP | PMAC_MB_HAS_FW_POWER | PMAC_MB_MOBILE, -- cgit v1.2.3 From 0e3a64e2162f971180bf1fdd91c263dbdfcfd385 Mon Sep 17 00:00:00 2001 From: Russell King Date: Sun, 2 Oct 2005 18:02:25 +0100 Subject: [ARM] Fix EBSA110 network driver link detection EBSA110 link detection didn't read the register - it wrote it. Oops. Signed-off-by: Russell King --- drivers/net/arm/am79c961a.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/arm/am79c961a.c b/drivers/net/arm/am79c961a.c index 9b659e3c8d6..9f6eb39cf49 100644 --- a/drivers/net/arm/am79c961a.c +++ b/drivers/net/arm/am79c961a.c @@ -85,7 +85,7 @@ static inline unsigned short read_ireg(u_long base_addr, u_int reg) u_short v; __asm__( "str%?h %1, [%2] @ NAT_RAP\n\t" - "str%?h %0, [%2, #8] @ NET_IDP\n\t" + "ldr%?h %0, [%2, #8] @ NET_IDP\n\t" : "=r" (v) : "r" (reg), "r" (ISAIO_BASE + 0x0464)); return v; -- cgit v1.2.3 From 487fd4eb1445407c9760af08b0b34c3f4cdb4afc Mon Sep 17 00:00:00 2001 From: Russell King Date: Sun, 2 Oct 2005 18:12:03 +0100 Subject: [ARM] Fix init printk for EBSA110 network driver, and link timer Arrange for the initialisation printks to happen after we've registered the network interface, so we know what name the device is. Also, check the link every 500ms (and use msecs_to_jiffies.) Signed-off-by: Russell King --- drivers/net/arm/am79c961a.c | 20 +++++++++----------- 1 file changed, 9 insertions(+), 11 deletions(-) diff --git a/drivers/net/arm/am79c961a.c b/drivers/net/arm/am79c961a.c index 9f6eb39cf49..c56d86d371a 100644 --- a/drivers/net/arm/am79c961a.c +++ b/drivers/net/arm/am79c961a.c @@ -15,16 +15,13 @@ */ #include #include -#include #include #include -#include #include #include #include #include #include -#include #include #include #include @@ -33,7 +30,6 @@ #include #include #include -#include #define TX_BUFFERS 15 #define RX_BUFFERS 25 @@ -288,7 +284,7 @@ static void am79c961_timer(unsigned long data) else if (!lnkstat && carrier) netif_carrier_off(dev); - mod_timer(&priv->timer, jiffies + 5*HZ); + mod_timer(&priv->timer, jiffies + msecs_to_jiffies(500)); } /* @@ -709,13 +705,9 @@ static int __init am79c961_init(void) goto release; am79c961_banner(); - printk(KERN_INFO "%s: ether address ", dev->name); - /* Retrive and print the ethernet address. */ - for (i = 0; i < 6; i++) { + for (i = 0; i < 6; i++) dev->dev_addr[i] = inb(dev->base_addr + i * 2) & 0xff; - printk (i == 5 ? "%02x\n" : "%02x:", dev->dev_addr[i]); - } spin_lock_init(&priv->chip_lock); init_timer(&priv->timer); @@ -736,8 +728,14 @@ static int __init am79c961_init(void) #endif ret = register_netdev(dev); - if (ret == 0) + if (ret == 0) { + printk(KERN_INFO "%s: ether address ", dev->name); + + for (i = 0; i < 6; i++) + printk (i == 5 ? "%02x\n" : "%02x:", dev->dev_addr[i]); + return 0; + } release: release_region(dev->base_addr, 0x18); -- cgit v1.2.3 From 9e70592fcd87c90e9e98090d66cb79f39d740d4a Mon Sep 17 00:00:00 2001 From: James Bottomley Date: Sun, 2 Oct 2005 12:59:49 -0500 Subject: [SCSI] fix potential panic with proc on module removal There's a problem in our host release in that it calls scsi_proc_hostdir_rm(). However, if you hold a reference to the host as you remove the module, the host template (which proc uses) will be freed and the system will panic when the host device is finally released. Fix this by moving scsi_proc_hostdir_rm() to where it should be: in scsi_remove_host(). Signed-off-by: James Bottomley --- drivers/scsi/hosts.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/scsi/hosts.c b/drivers/scsi/hosts.c index f2a72d33132..02fe371b0ab 100644 --- a/drivers/scsi/hosts.c +++ b/drivers/scsi/hosts.c @@ -176,6 +176,7 @@ void scsi_remove_host(struct Scsi_Host *shost) transport_unregister_device(&shost->shost_gendev); class_device_unregister(&shost->shost_classdev); device_del(&shost->shost_gendev); + scsi_proc_hostdir_rm(shost->hostt); } EXPORT_SYMBOL(scsi_remove_host); @@ -262,7 +263,6 @@ static void scsi_host_dev_release(struct device *dev) if (shost->work_q) destroy_workqueue(shost->work_q); - scsi_proc_hostdir_rm(shost->hostt); scsi_destroy_command_freelist(shost); kfree(shost->shost_data); -- cgit v1.2.3 From 97af50f60ff1202b0dd9ce481d4cf98c6a578bec Mon Sep 17 00:00:00 2001 From: James Bottomley Date: Sun, 2 Oct 2005 15:22:35 -0500 Subject: [SCSI] aic7xxx/aic79xx: fix module removal path not to panic In these drivers, scsi_remove_host() is called too late, at the point it is called, the driver has already shut down too far to accept any I/O that the shutdown might generate. Any generated I/O actually triggers a panic. Fix this by calling scsi_remove_host() as early as possible and not calling scsi_host_put() until just before we kfree the ahc_softc. Signed-off-by: James Bottomley --- drivers/scsi/aic7xxx/aic7770_osm.c | 3 +++ drivers/scsi/aic7xxx/aic79xx_osm.c | 8 +++----- drivers/scsi/aic7xxx/aic79xx_osm_pci.c | 3 +++ drivers/scsi/aic7xxx/aic7xxx_osm.c | 8 +++----- drivers/scsi/aic7xxx/aic7xxx_osm_pci.c | 3 +++ 5 files changed, 15 insertions(+), 10 deletions(-) diff --git a/drivers/scsi/aic7xxx/aic7770_osm.c b/drivers/scsi/aic7xxx/aic7770_osm.c index 70c5fb59c9e..d754b326786 100644 --- a/drivers/scsi/aic7xxx/aic7770_osm.c +++ b/drivers/scsi/aic7xxx/aic7770_osm.c @@ -112,6 +112,9 @@ aic7770_remove(struct device *dev) struct ahc_softc *ahc = dev_get_drvdata(dev); u_long s; + if (ahc->platform_data && ahc->platform_data->host) + scsi_remove_host(ahc->platform_data->host); + ahc_lock(ahc, &s); ahc_intr_enable(ahc, FALSE); ahc_unlock(ahc, &s); diff --git a/drivers/scsi/aic7xxx/aic79xx_osm.c b/drivers/scsi/aic7xxx/aic79xx_osm.c index 6b6d4e28779..95c285cc83e 100644 --- a/drivers/scsi/aic7xxx/aic79xx_osm.c +++ b/drivers/scsi/aic7xxx/aic79xx_osm.c @@ -1192,11 +1192,6 @@ ahd_platform_free(struct ahd_softc *ahd) int i, j; if (ahd->platform_data != NULL) { - if (ahd->platform_data->host != NULL) { - scsi_remove_host(ahd->platform_data->host); - scsi_host_put(ahd->platform_data->host); - } - /* destroy all of the device and target objects */ for (i = 0; i < AHD_NUM_TARGETS; i++) { starget = ahd->platform_data->starget[i]; @@ -1226,6 +1221,9 @@ ahd_platform_free(struct ahd_softc *ahd) release_mem_region(ahd->platform_data->mem_busaddr, 0x1000); } + if (ahd->platform_data->host) + scsi_host_put(ahd->platform_data->host); + free(ahd->platform_data, M_DEVBUF); } } diff --git a/drivers/scsi/aic7xxx/aic79xx_osm_pci.c b/drivers/scsi/aic7xxx/aic79xx_osm_pci.c index 390b53852d4..bf360ae021a 100644 --- a/drivers/scsi/aic7xxx/aic79xx_osm_pci.c +++ b/drivers/scsi/aic7xxx/aic79xx_osm_pci.c @@ -95,6 +95,9 @@ ahd_linux_pci_dev_remove(struct pci_dev *pdev) struct ahd_softc *ahd = pci_get_drvdata(pdev); u_long s; + if (ahd->platform_data && ahd->platform_data->host) + scsi_remove_host(ahd->platform_data->host); + ahd_lock(ahd, &s); ahd_intr_enable(ahd, FALSE); ahd_unlock(ahd, &s); diff --git a/drivers/scsi/aic7xxx/aic7xxx_osm.c b/drivers/scsi/aic7xxx/aic7xxx_osm.c index 876d1de8480..6ee1435d37f 100644 --- a/drivers/scsi/aic7xxx/aic7xxx_osm.c +++ b/drivers/scsi/aic7xxx/aic7xxx_osm.c @@ -1209,11 +1209,6 @@ ahc_platform_free(struct ahc_softc *ahc) int i, j; if (ahc->platform_data != NULL) { - if (ahc->platform_data->host != NULL) { - scsi_remove_host(ahc->platform_data->host); - scsi_host_put(ahc->platform_data->host); - } - /* destroy all of the device and target objects */ for (i = 0; i < AHC_NUM_TARGETS; i++) { starget = ahc->platform_data->starget[i]; @@ -1242,6 +1237,9 @@ ahc_platform_free(struct ahc_softc *ahc) 0x1000); } + if (ahc->platform_data->host) + scsi_host_put(ahc->platform_data->host); + free(ahc->platform_data, M_DEVBUF); } } diff --git a/drivers/scsi/aic7xxx/aic7xxx_osm_pci.c b/drivers/scsi/aic7xxx/aic7xxx_osm_pci.c index 3ce77ddc889..cb30d9c1153 100644 --- a/drivers/scsi/aic7xxx/aic7xxx_osm_pci.c +++ b/drivers/scsi/aic7xxx/aic7xxx_osm_pci.c @@ -143,6 +143,9 @@ ahc_linux_pci_dev_remove(struct pci_dev *pdev) struct ahc_softc *ahc = pci_get_drvdata(pdev); u_long s; + if (ahc->platform_data && ahc->platform_data->host) + scsi_remove_host(ahc->platform_data->host); + ahc_lock(ahc, &s); ahc_intr_enable(ahc, FALSE); ahc_unlock(ahc, &s); -- cgit v1.2.3 From d70ddac1bf3a8b102996588010ca87018c3a4a04 Mon Sep 17 00:00:00 2001 From: Richard Henderson Date: Sun, 2 Oct 2005 12:49:52 -0700 Subject: [PATCH] alpha: fix kernel alignment traps Pass in the pointer to the on-stack registers rather than using them directly as the arguments. Ivan noticed that I missed a spot when purging the registers as first stack parameter idiom. Signed-off-by: Linus Torvalds --- arch/alpha/kernel/entry.S | 1 + arch/alpha/kernel/traps.c | 15 +++++++-------- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/arch/alpha/kernel/entry.S b/arch/alpha/kernel/entry.S index 76cc0cb5fc2..e38671c922b 100644 --- a/arch/alpha/kernel/entry.S +++ b/arch/alpha/kernel/entry.S @@ -196,6 +196,7 @@ entUna: stq $26, 208($sp) stq $27, 216($sp) stq $28, 224($sp) + mov $sp, $19 stq $gp, 232($sp) lda $8, 0x3fff stq $31, 248($sp) diff --git a/arch/alpha/kernel/traps.c b/arch/alpha/kernel/traps.c index 6f509a644bd..f9d12319e0f 100644 --- a/arch/alpha/kernel/traps.c +++ b/arch/alpha/kernel/traps.c @@ -446,16 +446,15 @@ struct unaligned_stat { /* Macro for exception fixup code to access integer registers. */ -#define una_reg(r) (regs.regs[(r) >= 16 && (r) <= 18 ? (r)+19 : (r)]) +#define una_reg(r) (regs->regs[(r) >= 16 && (r) <= 18 ? (r)+19 : (r)]) asmlinkage void do_entUna(void * va, unsigned long opcode, unsigned long reg, - unsigned long a3, unsigned long a4, unsigned long a5, - struct allregs regs) + struct allregs *regs) { long error, tmp1, tmp2, tmp3, tmp4; - unsigned long pc = regs.pc - 4; + unsigned long pc = regs->pc - 4; const struct exception_table_entry *fixup; unaligned[0].count++; @@ -636,7 +635,7 @@ got_exception: printk("Forwarding unaligned exception at %lx (%lx)\n", pc, newpc); - (®s)->pc = newpc; + regs->pc = newpc; return; } @@ -650,7 +649,7 @@ got_exception: current->comm, current->pid); printk("pc = [<%016lx>] ra = [<%016lx>] ps = %04lx\n", - pc, una_reg(26), regs.ps); + pc, una_reg(26), regs->ps); printk("r0 = %016lx r1 = %016lx r2 = %016lx\n", una_reg(0), una_reg(1), una_reg(2)); printk("r3 = %016lx r4 = %016lx r5 = %016lx\n", @@ -670,10 +669,10 @@ got_exception: una_reg(22), una_reg(23), una_reg(24)); printk("r25= %016lx r27= %016lx r28= %016lx\n", una_reg(25), una_reg(27), una_reg(28)); - printk("gp = %016lx sp = %p\n", regs.gp, ®s+1); + printk("gp = %016lx sp = %p\n", regs->gp, regs+1); dik_show_code((unsigned int *)pc); - dik_show_trace((unsigned long *)(®s+1)); + dik_show_trace((unsigned long *)(regs+1)); if (test_and_set_thread_flag (TIF_DIE_IF_KERNEL)) { printk("die_if_kernel recursion detected.\n"); -- cgit v1.2.3 From 2c3a0540999ac9bd7147fb98833224a58cdaf217 Mon Sep 17 00:00:00 2001 From: Catalin Marinas Date: Sun, 2 Oct 2005 22:34:35 +0100 Subject: [ARM] 2943/1: Clear the exclusive monitor in v6_early_abort Patch from Catalin Marinas Data abort caused by ldrex/strex can leave the exclusive monitor in an unpredictable state. It is recommended that a clrex/strex is performed to clear this state. Signed-off-by: Catalin Marinas Signed-off-by: Russell King --- arch/arm/mm/abort-ev6.S | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/arch/arm/mm/abort-ev6.S b/arch/arm/mm/abort-ev6.S index 8f76f3df7b4..dbd34603312 100644 --- a/arch/arm/mm/abort-ev6.S +++ b/arch/arm/mm/abort-ev6.S @@ -20,6 +20,11 @@ */ .align 5 ENTRY(v6_early_abort) +#ifdef CONFIG_CPU_MPCORE + clrex +#else + strex r0, r1, [sp] @ Clear the exclusive monitor +#endif mrc p15, 0, r1, c5, c0, 0 @ get FSR mrc p15, 0, r0, c6, c0, 0 @ get FAR /* -- cgit v1.2.3 From 75f8426c17bc091260a6f7536ba10767596e15eb Mon Sep 17 00:00:00 2001 From: Paul Jackson Date: Sun, 2 Oct 2005 18:01:42 -0700 Subject: [PATCH] Document from line in patch format Document more details of patch format such as the "from" line and the "---" marker line, and provide more references for patch guidelines. Signed-off-by: Paul Jackson Signed-off-by: Linus Torvalds --- Documentation/SubmittingPatches | 70 ++++++++++++++++++++++++++++++++++++++++- 1 file changed, 69 insertions(+), 1 deletion(-) diff --git a/Documentation/SubmittingPatches b/Documentation/SubmittingPatches index 7f43b040311..1d96efec5e8 100644 --- a/Documentation/SubmittingPatches +++ b/Documentation/SubmittingPatches @@ -301,8 +301,68 @@ now, but you can do this to mark internal company procedures or just point out some special detail about the sign-off. +12) The canonical patch format -12) More references for submitting patches +The canonical patch subject line is: + + Subject: [PATCH 001/123] [:] + +The canonical patch message body contains the following: + + - A "from" line specifying the patch author. + + - An empty line. + + - The body of the explanation, which will be copied to the + permanent changelog to describe this patch. + + - The "Signed-off-by:" lines, described above, which will + also go in the changelog. + + - A marker line containing simply "---". + + - Any additional comments not suitable for the changelog. + + - The actual patch (diff output). + +The Subject line format makes it very easy to sort the emails +alphabetically by subject line - pretty much any email reader will +support that - since because the sequence number is zero-padded, +the numerical and alphabetic sort is the same. + +See further details on how to phrase the "" in the +"Subject:" line in Andrew Morton's "The perfect patch", referenced +below. + +The "from" line must be the very first line in the message body, +and has the form: + + From: Original Author + +The "from" line specifies who will be credited as the author of the +patch in the permanent changelog. If the "from" line is missing, +then the "From:" line from the email header will be used to determine +the patch author in the changelog. + +The explanation body will be committed to the permanent source +changelog, so should make sense to a competent reader who has long +since forgotten the immediate details of the discussion that might +have led to this patch. + +The "---" marker line serves the essential purpose of marking for patch +handling tools where the changelog message ends. + +One good use for the additional comments after the "---" marker is for +a diffstat, to show what files have changed, and the number of inserted +and deleted lines per file. A diffstat is especially useful on bigger +patches. Other comments relevant only to the moment or the maintainer, +not suitable for the permanent changelog, should also go here. + +See more details on the proper patch format in the following +references. + + +13) More references for submitting patches Andrew Morton, "The perfect patch" (tpp). @@ -310,6 +370,14 @@ Andrew Morton, "The perfect patch" (tpp). Jeff Garzik, "Linux kernel patch submission format." +Greg KH, "How to piss off a kernel subsystem maintainer" + + +Kernel Documentation/CodingStyle + + +Linus Torvald's mail on the canonical patch format: + ----------------------------------- -- cgit v1.2.3 From 51c928c34fa7cff38df584ad01de988805877dba Mon Sep 17 00:00:00 2001 From: James Bottomley Date: Sat, 1 Oct 2005 09:38:05 -0500 Subject: [SCSI] Legacy MegaRAID: Fix READ CAPACITY Some Legacy megaraid cards can't actually cope with the scatter/gather version of the READ CAPACITY command (which is what we now send them since altering all SCSI internal I/O to go via the block layer). Fix this (and a few other broken megaraid driver assumptions) by sending the non-sg version of the command if the sg list only has a single element. Signed-off-by: James Bottomley --- drivers/scsi/megaraid.c | 70 +++++++++++++++++++++++++++++++++++-------------- 1 file changed, 50 insertions(+), 20 deletions(-) diff --git a/drivers/scsi/megaraid.c b/drivers/scsi/megaraid.c index 6f308ebe3e7..61a6fd810bb 100644 --- a/drivers/scsi/megaraid.c +++ b/drivers/scsi/megaraid.c @@ -621,8 +621,6 @@ mega_build_cmd(adapter_t *adapter, Scsi_Cmnd *cmd, int *busy) if(islogical) { switch (cmd->cmnd[0]) { case TEST_UNIT_READY: - memset(cmd->request_buffer, 0, cmd->request_bufflen); - #if MEGA_HAVE_CLUSTERING /* * Do we support clustering and is the support enabled @@ -652,11 +650,28 @@ mega_build_cmd(adapter_t *adapter, Scsi_Cmnd *cmd, int *busy) return NULL; #endif - case MODE_SENSE: + case MODE_SENSE: { + char *buf; + + if (cmd->use_sg) { + struct scatterlist *sg; + + sg = (struct scatterlist *)cmd->request_buffer; + buf = kmap_atomic(sg->page, KM_IRQ0) + + sg->offset; + } else + buf = cmd->request_buffer; memset(cmd->request_buffer, 0, cmd->cmnd[4]); + if (cmd->use_sg) { + struct scatterlist *sg; + + sg = (struct scatterlist *)cmd->request_buffer; + kunmap_atomic(buf - sg->offset, KM_IRQ0); + } cmd->result = (DID_OK << 16); cmd->scsi_done(cmd); return NULL; + } case READ_CAPACITY: case INQUIRY: @@ -1685,14 +1700,23 @@ mega_rundoneq (adapter_t *adapter) static void mega_free_scb(adapter_t *adapter, scb_t *scb) { + unsigned long length; + switch( scb->dma_type ) { case MEGA_DMA_TYPE_NONE: break; case MEGA_BULK_DATA: + if (scb->cmd->use_sg == 0) + length = scb->cmd->request_bufflen; + else { + struct scatterlist *sgl = + (struct scatterlist *)scb->cmd->request_buffer; + length = sgl->length; + } pci_unmap_page(adapter->dev, scb->dma_h_bulkdata, - scb->cmd->request_bufflen, scb->dma_direction); + length, scb->dma_direction); break; case MEGA_SGLIST: @@ -1741,6 +1765,7 @@ mega_build_sglist(adapter_t *adapter, scb_t *scb, u32 *buf, u32 *len) struct scatterlist *sgl; struct page *page; unsigned long offset; + unsigned int length; Scsi_Cmnd *cmd; int sgcnt; int idx; @@ -1748,14 +1773,23 @@ mega_build_sglist(adapter_t *adapter, scb_t *scb, u32 *buf, u32 *len) cmd = scb->cmd; /* Scatter-gather not used */ - if( !cmd->use_sg ) { - - page = virt_to_page(cmd->request_buffer); - offset = offset_in_page(cmd->request_buffer); + if( cmd->use_sg == 0 || (cmd->use_sg == 1 && + !adapter->has_64bit_addr)) { + + if (cmd->use_sg == 0) { + page = virt_to_page(cmd->request_buffer); + offset = offset_in_page(cmd->request_buffer); + length = cmd->request_bufflen; + } else { + sgl = (struct scatterlist *)cmd->request_buffer; + page = sgl->page; + offset = sgl->offset; + length = sgl->length; + } scb->dma_h_bulkdata = pci_map_page(adapter->dev, page, offset, - cmd->request_bufflen, + length, scb->dma_direction); scb->dma_type = MEGA_BULK_DATA; @@ -1765,14 +1799,14 @@ mega_build_sglist(adapter_t *adapter, scb_t *scb, u32 *buf, u32 *len) */ if( adapter->has_64bit_addr ) { scb->sgl64[0].address = scb->dma_h_bulkdata; - scb->sgl64[0].length = cmd->request_bufflen; + scb->sgl64[0].length = length; *buf = (u32)scb->sgl_dma_addr; - *len = (u32)cmd->request_bufflen; + *len = (u32)length; return 1; } else { *buf = (u32)scb->dma_h_bulkdata; - *len = (u32)cmd->request_bufflen; + *len = (u32)length; } return 0; } @@ -1791,27 +1825,23 @@ mega_build_sglist(adapter_t *adapter, scb_t *scb, u32 *buf, u32 *len) if( sgcnt > adapter->sglen ) BUG(); + *len = 0; + for( idx = 0; idx < sgcnt; idx++, sgl++ ) { if( adapter->has_64bit_addr ) { scb->sgl64[idx].address = sg_dma_address(sgl); - scb->sgl64[idx].length = sg_dma_len(sgl); + *len += scb->sgl64[idx].length = sg_dma_len(sgl); } else { scb->sgl[idx].address = sg_dma_address(sgl); - scb->sgl[idx].length = sg_dma_len(sgl); + *len += scb->sgl[idx].length = sg_dma_len(sgl); } } /* Reset pointer and length fields */ *buf = scb->sgl_dma_addr; - /* - * For passthru command, dataxferlen must be set, even for commands - * with a sg list - */ - *len = (u32)cmd->request_bufflen; - /* Return count of SG requests */ return sgcnt; } -- cgit v1.2.3 From d6b9acc0c6c4a7c5d484d15271a5274656d0864f Mon Sep 17 00:00:00 2001 From: Paul Jackson Date: Mon, 3 Oct 2005 00:29:10 -0700 Subject: [PATCH] Document patch subject line better Improve explanation of the Subject line fields in Documentation/SubmittingPatches Canonical Patch Format. Signed-off-by: Paul Jackson Signed-off-by: Linus Torvalds --- Documentation/SubmittingPatches | 24 ++++++++++++++++++++---- 1 file changed, 20 insertions(+), 4 deletions(-) diff --git a/Documentation/SubmittingPatches b/Documentation/SubmittingPatches index 1d96efec5e8..237d54c44bc 100644 --- a/Documentation/SubmittingPatches +++ b/Documentation/SubmittingPatches @@ -305,7 +305,7 @@ point out some special detail about the sign-off. The canonical patch subject line is: - Subject: [PATCH 001/123] [:] + Subject: [PATCH 001/123] subsystem: summary phrase The canonical patch message body contains the following: @@ -330,9 +330,25 @@ alphabetically by subject line - pretty much any email reader will support that - since because the sequence number is zero-padded, the numerical and alphabetic sort is the same. -See further details on how to phrase the "" in the -"Subject:" line in Andrew Morton's "The perfect patch", referenced -below. +The "subsystem" in the email's Subject should identify which +area or subsystem of the kernel is being patched. + +The "summary phrase" in the email's Subject should concisely +describe the patch which that email contains. The "summary +phrase" should not be a filename. Do not use the same "summary +phrase" for every patch in a whole patch series. + +Bear in mind that the "summary phrase" of your email becomes +a globally-unique identifier for that patch. It propagates +all the way into the git changelog. The "summary phrase" may +later be used in developer discussions which refer to the patch. +People will want to google for the "summary phrase" to read +discussion regarding that patch. + +A couple of example Subjects: + + Subject: [patch 2/5] ext2: improve scalability of bitmap searching + Subject: [PATCHv2 001/207] x86: fix eflags tracking The "from" line must be the very first line in the message body, and has the form: -- cgit v1.2.3 From ddea7be0ec8d1374f0b483a81566ed56ec9f3905 Mon Sep 17 00:00:00 2001 From: Ravikiran G Thirumalai Date: Mon, 3 Oct 2005 10:36:28 -0700 Subject: [PATCH] x86_64: Fix numa node topology detection for srat based x86_64 boxes 2.6.14-rc2 does not assign cpus to proper nodeids on our em64t numa boxen. Our boxes use acpi srat for parsing the numa information. srat_detect_node() used phys_proc_id[] to get to the cpu's local apic id, but phys_proc_id[] represents the cpu<->initial_apic_id mapping. The following patch fixes this problem. Now apicid_to_node[] is properly indexed with the local apic id. Signed-off-by: Ravikiran Thirumalai Acked-by: Suresh Siddha Cc: Andi Kleen Signed-off-by: Linus Torvalds --- arch/x86_64/kernel/setup.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/arch/x86_64/kernel/setup.c b/arch/x86_64/kernel/setup.c index 257f5ba1790..cb28df14ff6 100644 --- a/arch/x86_64/kernel/setup.c +++ b/arch/x86_64/kernel/setup.c @@ -967,13 +967,12 @@ static int __cpuinit intel_num_cpu_cores(struct cpuinfo_x86 *c) static void srat_detect_node(void) { #ifdef CONFIG_NUMA - unsigned apicid, node; + unsigned node; int cpu = smp_processor_id(); /* Don't do the funky fallback heuristics the AMD version employs for now. */ - apicid = phys_proc_id[cpu]; - node = apicid_to_node[apicid]; + node = apicid_to_node[hard_smp_processor_id()]; if (node == NUMA_NO_NODE) node = 0; cpu_to_node[cpu] = node; -- cgit v1.2.3 From 325ed8239309cb29f10ea58c5a668058ead11479 Mon Sep 17 00:00:00 2001 From: Herbert Xu Date: Mon, 3 Oct 2005 13:57:23 -0700 Subject: [NET]: Fix packet timestamping. I've found the problem in general. It affects any 64-bit architecture. The problem occurs when you change the system time. Suppose that when you boot your system clock is forward by a day. This gets recorded down in skb_tv_base. You then wind the clock back by a day. From that point onwards the offset will be negative which essentially overflows the 32-bit variables they're stored in. In fact, why don't we just store the real time stamp in those 32-bit variables? After all, we're not going to overflow for quite a while yet. When we do overflow, we'll need a better solution of course. Signed-off-by: Herbert Xu Signed-off-by: David S. Miller --- include/linux/skbuff.h | 12 +++--------- net/core/skbuff.c | 5 ----- net/ipv4/netfilter/ip_queue.c | 4 ++-- net/ipv4/netfilter/ipt_ULOG.c | 4 ++-- net/ipv6/netfilter/ip6_queue.c | 4 ++-- net/netfilter/nfnetlink_log.c | 4 ++-- net/netfilter/nfnetlink_queue.c | 4 ++-- net/packet/af_packet.c | 4 ++-- 8 files changed, 15 insertions(+), 26 deletions(-) diff --git a/include/linux/skbuff.h b/include/linux/skbuff.h index 2741c0c55e8..466c879f82b 100644 --- a/include/linux/skbuff.h +++ b/include/linux/skbuff.h @@ -155,8 +155,6 @@ struct skb_shared_info { #define SKB_DATAREF_SHIFT 16 #define SKB_DATAREF_MASK ((1 << SKB_DATAREF_SHIFT) - 1) -extern struct timeval skb_tv_base; - struct skb_timeval { u32 off_sec; u32 off_usec; @@ -175,7 +173,7 @@ enum { * @prev: Previous buffer in list * @list: List we are on * @sk: Socket we are owned by - * @tstamp: Time we arrived stored as offset to skb_tv_base + * @tstamp: Time we arrived * @dev: Device we arrived on/are leaving by * @input_dev: Device we arrived on * @h: Transport layer header @@ -1255,10 +1253,6 @@ static inline void skb_get_timestamp(const struct sk_buff *skb, struct timeval * { stamp->tv_sec = skb->tstamp.off_sec; stamp->tv_usec = skb->tstamp.off_usec; - if (skb->tstamp.off_sec) { - stamp->tv_sec += skb_tv_base.tv_sec; - stamp->tv_usec += skb_tv_base.tv_usec; - } } /** @@ -1272,8 +1266,8 @@ static inline void skb_get_timestamp(const struct sk_buff *skb, struct timeval * */ static inline void skb_set_timestamp(struct sk_buff *skb, const struct timeval *stamp) { - skb->tstamp.off_sec = stamp->tv_sec - skb_tv_base.tv_sec; - skb->tstamp.off_usec = stamp->tv_usec - skb_tv_base.tv_usec; + skb->tstamp.off_sec = stamp->tv_sec; + skb->tstamp.off_usec = stamp->tv_usec; } extern void __net_timestamp(struct sk_buff *skb); diff --git a/net/core/skbuff.c b/net/core/skbuff.c index f80a2878561..0e9431b59fb 100644 --- a/net/core/skbuff.c +++ b/net/core/skbuff.c @@ -71,8 +71,6 @@ static kmem_cache_t *skbuff_head_cache __read_mostly; static kmem_cache_t *skbuff_fclone_cache __read_mostly; -struct timeval __read_mostly skb_tv_base; - /* * Keep out-of-line to prevent kernel bloat. * __builtin_return_address is not used because it is not always @@ -1708,8 +1706,6 @@ void __init skb_init(void) NULL, NULL); if (!skbuff_fclone_cache) panic("cannot create skbuff cache"); - - do_gettimeofday(&skb_tv_base); } EXPORT_SYMBOL(___pskb_trim); @@ -1743,4 +1739,3 @@ EXPORT_SYMBOL(skb_prepare_seq_read); EXPORT_SYMBOL(skb_seq_read); EXPORT_SYMBOL(skb_abort_seq_read); EXPORT_SYMBOL(skb_find_text); -EXPORT_SYMBOL(skb_tv_base); diff --git a/net/ipv4/netfilter/ip_queue.c b/net/ipv4/netfilter/ip_queue.c index d54f14d926f..36339eb39e1 100644 --- a/net/ipv4/netfilter/ip_queue.c +++ b/net/ipv4/netfilter/ip_queue.c @@ -240,8 +240,8 @@ ipq_build_packet_message(struct ipq_queue_entry *entry, int *errp) pmsg->packet_id = (unsigned long )entry; pmsg->data_len = data_len; - pmsg->timestamp_sec = skb_tv_base.tv_sec + entry->skb->tstamp.off_sec; - pmsg->timestamp_usec = skb_tv_base.tv_usec + entry->skb->tstamp.off_usec; + pmsg->timestamp_sec = entry->skb->tstamp.off_sec; + pmsg->timestamp_usec = entry->skb->tstamp.off_usec; pmsg->mark = entry->skb->nfmark; pmsg->hook = entry->info->hook; pmsg->hw_protocol = entry->skb->protocol; diff --git a/net/ipv4/netfilter/ipt_ULOG.c b/net/ipv4/netfilter/ipt_ULOG.c index e2c14f3cb2f..2883ccd8a91 100644 --- a/net/ipv4/netfilter/ipt_ULOG.c +++ b/net/ipv4/netfilter/ipt_ULOG.c @@ -225,8 +225,8 @@ static void ipt_ulog_packet(unsigned int hooknum, /* copy hook, prefix, timestamp, payload, etc. */ pm->data_len = copy_len; - pm->timestamp_sec = skb_tv_base.tv_sec + skb->tstamp.off_sec; - pm->timestamp_usec = skb_tv_base.tv_usec + skb->tstamp.off_usec; + pm->timestamp_sec = skb->tstamp.off_sec; + pm->timestamp_usec = skb->tstamp.off_usec; pm->mark = skb->nfmark; pm->hook = hooknum; if (prefix != NULL) diff --git a/net/ipv6/netfilter/ip6_queue.c b/net/ipv6/netfilter/ip6_queue.c index aa11cf366ef..5027bbe6415 100644 --- a/net/ipv6/netfilter/ip6_queue.c +++ b/net/ipv6/netfilter/ip6_queue.c @@ -238,8 +238,8 @@ ipq_build_packet_message(struct ipq_queue_entry *entry, int *errp) pmsg->packet_id = (unsigned long )entry; pmsg->data_len = data_len; - pmsg->timestamp_sec = skb_tv_base.tv_sec + entry->skb->tstamp.off_sec; - pmsg->timestamp_usec = skb_tv_base.tv_usec + entry->skb->tstamp.off_usec; + pmsg->timestamp_sec = entry->skb->tstamp.off_sec; + pmsg->timestamp_usec = entry->skb->tstamp.off_usec; pmsg->mark = entry->skb->nfmark; pmsg->hook = entry->info->hook; pmsg->hw_protocol = entry->skb->protocol; diff --git a/net/netfilter/nfnetlink_log.c b/net/netfilter/nfnetlink_log.c index ff5601ceedc..efcd10f996b 100644 --- a/net/netfilter/nfnetlink_log.c +++ b/net/netfilter/nfnetlink_log.c @@ -494,8 +494,8 @@ __build_packet_message(struct nfulnl_instance *inst, if (skb->tstamp.off_sec) { struct nfulnl_msg_packet_timestamp ts; - ts.sec = cpu_to_be64(skb_tv_base.tv_sec + skb->tstamp.off_sec); - ts.usec = cpu_to_be64(skb_tv_base.tv_usec + skb->tstamp.off_usec); + ts.sec = cpu_to_be64(skb->tstamp.off_sec); + ts.usec = cpu_to_be64(skb->tstamp.off_usec); NFA_PUT(inst->skb, NFULA_TIMESTAMP, sizeof(ts), &ts); } diff --git a/net/netfilter/nfnetlink_queue.c b/net/netfilter/nfnetlink_queue.c index f81fe8c52e9..eaa44c49567 100644 --- a/net/netfilter/nfnetlink_queue.c +++ b/net/netfilter/nfnetlink_queue.c @@ -492,8 +492,8 @@ nfqnl_build_packet_message(struct nfqnl_instance *queue, if (entry->skb->tstamp.off_sec) { struct nfqnl_msg_packet_timestamp ts; - ts.sec = cpu_to_be64(skb_tv_base.tv_sec + entry->skb->tstamp.off_sec); - ts.usec = cpu_to_be64(skb_tv_base.tv_usec + entry->skb->tstamp.off_usec); + ts.sec = cpu_to_be64(entry->skb->tstamp.off_sec); + ts.usec = cpu_to_be64(entry->skb->tstamp.off_usec); NFA_PUT(skb, NFQA_TIMESTAMP, sizeof(ts), &ts); } diff --git a/net/packet/af_packet.c b/net/packet/af_packet.c index 6a67a87384c..499ae3df4a4 100644 --- a/net/packet/af_packet.c +++ b/net/packet/af_packet.c @@ -654,8 +654,8 @@ static int tpacket_rcv(struct sk_buff *skb, struct net_device *dev, struct packe __net_timestamp(skb); sock_enable_timestamp(sk); } - h->tp_sec = skb_tv_base.tv_sec + skb->tstamp.off_sec; - h->tp_usec = skb_tv_base.tv_usec + skb->tstamp.off_usec; + h->tp_sec = skb->tstamp.off_sec; + h->tp_usec = skb->tstamp.off_usec; sll = (struct sockaddr_ll*)((u8*)h + TPACKET_ALIGN(sizeof(*h))); sll->sll_halen = 0; -- cgit v1.2.3 From a232f76732e11c91c2215d3a43cf9ebc7f939939 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Mon, 3 Oct 2005 14:01:37 -0700 Subject: [CASSINI]: Convert to ethtool_ops Signed-off-by: Al Viro Signed-off-by: David S. Miller --- drivers/net/cassini.c | 502 +++++++++++++++++++++----------------------------- 1 file changed, 214 insertions(+), 288 deletions(-) diff --git a/drivers/net/cassini.c b/drivers/net/cassini.c index 45831fb377a..2e617424d3f 100644 --- a/drivers/net/cassini.c +++ b/drivers/net/cassini.c @@ -4423,18 +4423,14 @@ static struct { #define CAS_REG_LEN (sizeof(ethtool_register_table)/sizeof(int)) #define CAS_MAX_REGS (sizeof (u32)*CAS_REG_LEN) -static u8 *cas_get_regs(struct cas *cp) +static void cas_read_regs(struct cas *cp, u8 *ptr, int len) { - u8 *ptr = kmalloc(CAS_MAX_REGS, GFP_KERNEL); u8 *p; int i; unsigned long flags; - if (!ptr) - return NULL; - spin_lock_irqsave(&cp->lock, flags); - for (i = 0, p = ptr; i < CAS_REG_LEN ; i ++, p += sizeof(u32)) { + for (i = 0, p = ptr; i < len ; i ++, p += sizeof(u32)) { u16 hval; u32 val; if (ethtool_register_table[i].offsets < 0) { @@ -4447,8 +4443,6 @@ static u8 *cas_get_regs(struct cas *cp) memcpy(p, (u8 *)&val, sizeof(u32)); } spin_unlock_irqrestore(&cp->lock, flags); - - return ptr; } static struct net_device_stats *cas_get_stats(struct net_device *dev) @@ -4561,316 +4555,251 @@ static void cas_set_multicast(struct net_device *dev) spin_unlock_irqrestore(&cp->lock, flags); } -/* Eventually add support for changing the advertisement - * on autoneg. - */ -static int cas_ethtool_ioctl(struct net_device *dev, void __user *ep_user) +static void cas_get_drvinfo(struct net_device *dev, struct ethtool_drvinfo *info) +{ + struct cas *cp = netdev_priv(dev); + strncpy(info->driver, DRV_MODULE_NAME, ETHTOOL_BUSINFO_LEN); + strncpy(info->version, DRV_MODULE_VERSION, ETHTOOL_BUSINFO_LEN); + info->fw_version[0] = '\0'; + strncpy(info->bus_info, pci_name(cp->pdev), ETHTOOL_BUSINFO_LEN); + info->regdump_len = cp->casreg_len < CAS_MAX_REGS ? + cp->casreg_len : CAS_MAX_REGS; + info->n_stats = CAS_NUM_STAT_KEYS; +} + +static int cas_get_settings(struct net_device *dev, struct ethtool_cmd *cmd) { struct cas *cp = netdev_priv(dev); u16 bmcr; int full_duplex, speed, pause; - struct ethtool_cmd ecmd; unsigned long flags; enum link_state linkstate = link_up; - if (copy_from_user(&ecmd, ep_user, sizeof(ecmd))) - return -EFAULT; - - switch(ecmd.cmd) { - case ETHTOOL_GDRVINFO: { - struct ethtool_drvinfo info = { .cmd = ETHTOOL_GDRVINFO }; - - strncpy(info.driver, DRV_MODULE_NAME, - ETHTOOL_BUSINFO_LEN); - strncpy(info.version, DRV_MODULE_VERSION, - ETHTOOL_BUSINFO_LEN); - info.fw_version[0] = '\0'; - strncpy(info.bus_info, pci_name(cp->pdev), - ETHTOOL_BUSINFO_LEN); - info.regdump_len = cp->casreg_len < CAS_MAX_REGS ? - cp->casreg_len : CAS_MAX_REGS; - info.n_stats = CAS_NUM_STAT_KEYS; - if (copy_to_user(ep_user, &info, sizeof(info))) - return -EFAULT; - - return 0; + cmd->advertising = 0; + cmd->supported = SUPPORTED_Autoneg; + if (cp->cas_flags & CAS_FLAG_1000MB_CAP) { + cmd->supported |= SUPPORTED_1000baseT_Full; + cmd->advertising |= ADVERTISED_1000baseT_Full; } - case ETHTOOL_GSET: - ecmd.advertising = 0; - ecmd.supported = SUPPORTED_Autoneg; - if (cp->cas_flags & CAS_FLAG_1000MB_CAP) { - ecmd.supported |= SUPPORTED_1000baseT_Full; - ecmd.advertising |= ADVERTISED_1000baseT_Full; + /* Record PHY settings if HW is on. */ + spin_lock_irqsave(&cp->lock, flags); + bmcr = 0; + linkstate = cp->lstate; + if (CAS_PHY_MII(cp->phy_type)) { + cmd->port = PORT_MII; + cmd->transceiver = (cp->cas_flags & CAS_FLAG_SATURN) ? + XCVR_INTERNAL : XCVR_EXTERNAL; + cmd->phy_address = cp->phy_addr; + cmd->advertising |= ADVERTISED_TP | ADVERTISED_MII | + ADVERTISED_10baseT_Half | + ADVERTISED_10baseT_Full | + ADVERTISED_100baseT_Half | + ADVERTISED_100baseT_Full; + + cmd->supported |= + (SUPPORTED_10baseT_Half | + SUPPORTED_10baseT_Full | + SUPPORTED_100baseT_Half | + SUPPORTED_100baseT_Full | + SUPPORTED_TP | SUPPORTED_MII); + + if (cp->hw_running) { + cas_mif_poll(cp, 0); + bmcr = cas_phy_read(cp, MII_BMCR); + cas_read_mii_link_mode(cp, &full_duplex, + &speed, &pause); + cas_mif_poll(cp, 1); } - /* Record PHY settings if HW is on. */ - spin_lock_irqsave(&cp->lock, flags); - bmcr = 0; - linkstate = cp->lstate; - if (CAS_PHY_MII(cp->phy_type)) { - ecmd.port = PORT_MII; - ecmd.transceiver = (cp->cas_flags & CAS_FLAG_SATURN) ? - XCVR_INTERNAL : XCVR_EXTERNAL; - ecmd.phy_address = cp->phy_addr; - ecmd.advertising |= ADVERTISED_TP | ADVERTISED_MII | - ADVERTISED_10baseT_Half | - ADVERTISED_10baseT_Full | - ADVERTISED_100baseT_Half | - ADVERTISED_100baseT_Full; - - ecmd.supported |= - (SUPPORTED_10baseT_Half | - SUPPORTED_10baseT_Full | - SUPPORTED_100baseT_Half | - SUPPORTED_100baseT_Full | - SUPPORTED_TP | SUPPORTED_MII); - - if (cp->hw_running) { - cas_mif_poll(cp, 0); - bmcr = cas_phy_read(cp, MII_BMCR); - cas_read_mii_link_mode(cp, &full_duplex, - &speed, &pause); - cas_mif_poll(cp, 1); - } - - } else { - ecmd.port = PORT_FIBRE; - ecmd.transceiver = XCVR_INTERNAL; - ecmd.phy_address = 0; - ecmd.supported |= SUPPORTED_FIBRE; - ecmd.advertising |= ADVERTISED_FIBRE; - - if (cp->hw_running) { - /* pcs uses the same bits as mii */ - bmcr = readl(cp->regs + REG_PCS_MII_CTRL); - cas_read_pcs_link_mode(cp, &full_duplex, - &speed, &pause); - } + } else { + cmd->port = PORT_FIBRE; + cmd->transceiver = XCVR_INTERNAL; + cmd->phy_address = 0; + cmd->supported |= SUPPORTED_FIBRE; + cmd->advertising |= ADVERTISED_FIBRE; + + if (cp->hw_running) { + /* pcs uses the same bits as mii */ + bmcr = readl(cp->regs + REG_PCS_MII_CTRL); + cas_read_pcs_link_mode(cp, &full_duplex, + &speed, &pause); } - spin_unlock_irqrestore(&cp->lock, flags); + } + spin_unlock_irqrestore(&cp->lock, flags); - if (bmcr & BMCR_ANENABLE) { - ecmd.advertising |= ADVERTISED_Autoneg; - ecmd.autoneg = AUTONEG_ENABLE; - ecmd.speed = ((speed == 10) ? - SPEED_10 : - ((speed == 1000) ? - SPEED_1000 : SPEED_100)); - ecmd.duplex = full_duplex ? DUPLEX_FULL : DUPLEX_HALF; + if (bmcr & BMCR_ANENABLE) { + cmd->advertising |= ADVERTISED_Autoneg; + cmd->autoneg = AUTONEG_ENABLE; + cmd->speed = ((speed == 10) ? + SPEED_10 : + ((speed == 1000) ? + SPEED_1000 : SPEED_100)); + cmd->duplex = full_duplex ? DUPLEX_FULL : DUPLEX_HALF; + } else { + cmd->autoneg = AUTONEG_DISABLE; + cmd->speed = + (bmcr & CAS_BMCR_SPEED1000) ? + SPEED_1000 : + ((bmcr & BMCR_SPEED100) ? SPEED_100: + SPEED_10); + cmd->duplex = + (bmcr & BMCR_FULLDPLX) ? + DUPLEX_FULL : DUPLEX_HALF; + } + if (linkstate != link_up) { + /* Force these to "unknown" if the link is not up and + * autonogotiation in enabled. We can set the link + * speed to 0, but not cmd->duplex, + * because its legal values are 0 and 1. Ethtool will + * print the value reported in parentheses after the + * word "Unknown" for unrecognized values. + * + * If in forced mode, we report the speed and duplex + * settings that we configured. + */ + if (cp->link_cntl & BMCR_ANENABLE) { + cmd->speed = 0; + cmd->duplex = 0xff; } else { - ecmd.autoneg = AUTONEG_DISABLE; - ecmd.speed = - (bmcr & CAS_BMCR_SPEED1000) ? - SPEED_1000 : - ((bmcr & BMCR_SPEED100) ? SPEED_100: - SPEED_10); - ecmd.duplex = - (bmcr & BMCR_FULLDPLX) ? - DUPLEX_FULL : DUPLEX_HALF; - } - if (linkstate != link_up) { - /* Force these to "unknown" if the link is not up and - * autonogotiation in enabled. We can set the link - * speed to 0, but not ecmd.duplex, - * because its legal values are 0 and 1. Ethtool will - * print the value reported in parentheses after the - * word "Unknown" for unrecognized values. - * - * If in forced mode, we report the speed and duplex - * settings that we configured. - */ - if (cp->link_cntl & BMCR_ANENABLE) { - ecmd.speed = 0; - ecmd.duplex = 0xff; - } else { - ecmd.speed = SPEED_10; - if (cp->link_cntl & BMCR_SPEED100) { - ecmd.speed = SPEED_100; - } else if (cp->link_cntl & CAS_BMCR_SPEED1000) { - ecmd.speed = SPEED_1000; - } - ecmd.duplex = (cp->link_cntl & BMCR_FULLDPLX)? - DUPLEX_FULL : DUPLEX_HALF; + cmd->speed = SPEED_10; + if (cp->link_cntl & BMCR_SPEED100) { + cmd->speed = SPEED_100; + } else if (cp->link_cntl & CAS_BMCR_SPEED1000) { + cmd->speed = SPEED_1000; } + cmd->duplex = (cp->link_cntl & BMCR_FULLDPLX)? + DUPLEX_FULL : DUPLEX_HALF; } - if (copy_to_user(ep_user, &ecmd, sizeof(ecmd))) - return -EFAULT; - return 0; + } + return 0; +} - case ETHTOOL_SSET: - if (!capable(CAP_NET_ADMIN)) - return -EPERM; +static int cas_set_settings(struct net_device *dev, struct ethtool_cmd *cmd) +{ + struct cas *cp = netdev_priv(dev); + unsigned long flags; - /* Verify the settings we care about. */ - if (ecmd.autoneg != AUTONEG_ENABLE && - ecmd.autoneg != AUTONEG_DISABLE) - return -EINVAL; + /* Verify the settings we care about. */ + if (cmd->autoneg != AUTONEG_ENABLE && + cmd->autoneg != AUTONEG_DISABLE) + return -EINVAL; - if (ecmd.autoneg == AUTONEG_DISABLE && - ((ecmd.speed != SPEED_1000 && - ecmd.speed != SPEED_100 && - ecmd.speed != SPEED_10) || - (ecmd.duplex != DUPLEX_HALF && - ecmd.duplex != DUPLEX_FULL))) - return -EINVAL; + if (cmd->autoneg == AUTONEG_DISABLE && + ((cmd->speed != SPEED_1000 && + cmd->speed != SPEED_100 && + cmd->speed != SPEED_10) || + (cmd->duplex != DUPLEX_HALF && + cmd->duplex != DUPLEX_FULL))) + return -EINVAL; - /* Apply settings and restart link process. */ - spin_lock_irqsave(&cp->lock, flags); - cas_begin_auto_negotiation(cp, &ecmd); - spin_unlock_irqrestore(&cp->lock, flags); - return 0; + /* Apply settings and restart link process. */ + spin_lock_irqsave(&cp->lock, flags); + cas_begin_auto_negotiation(cp, cmd); + spin_unlock_irqrestore(&cp->lock, flags); + return 0; +} - case ETHTOOL_NWAY_RST: - if ((cp->link_cntl & BMCR_ANENABLE) == 0) - return -EINVAL; +static int cas_nway_reset(struct net_device *dev) +{ + struct cas *cp = netdev_priv(dev); + unsigned long flags; - /* Restart link process. */ - spin_lock_irqsave(&cp->lock, flags); - cas_begin_auto_negotiation(cp, NULL); - spin_unlock_irqrestore(&cp->lock, flags); + if ((cp->link_cntl & BMCR_ANENABLE) == 0) + return -EINVAL; - return 0; + /* Restart link process. */ + spin_lock_irqsave(&cp->lock, flags); + cas_begin_auto_negotiation(cp, NULL); + spin_unlock_irqrestore(&cp->lock, flags); - case ETHTOOL_GWOL: - case ETHTOOL_SWOL: - break; /* doesn't exist */ + return 0; +} - /* get link status */ - case ETHTOOL_GLINK: { - struct ethtool_value edata = { .cmd = ETHTOOL_GLINK }; +static u32 cas_get_link(struct net_device *dev) +{ + struct cas *cp = netdev_priv(dev); + return cp->lstate == link_up; +} - edata.data = (cp->lstate == link_up); - if (copy_to_user(ep_user, &edata, sizeof(edata))) - return -EFAULT; - return 0; - } +static u32 cas_get_msglevel(struct net_device *dev) +{ + struct cas *cp = netdev_priv(dev); + return cp->msg_enable; +} - /* get message-level */ - case ETHTOOL_GMSGLVL: { - struct ethtool_value edata = { .cmd = ETHTOOL_GMSGLVL }; +static void cas_set_msglevel(struct net_device *dev, u32 value) +{ + struct cas *cp = netdev_priv(dev); + cp->msg_enable = value; +} - edata.data = cp->msg_enable; - if (copy_to_user(ep_user, &edata, sizeof(edata))) - return -EFAULT; - return 0; - } +static int cas_get_regs_len(struct net_device *dev) +{ + struct cas *cp = netdev_priv(dev); + return cp->casreg_len < CAS_MAX_REGS ? cp->casreg_len: CAS_MAX_REGS; +} - /* set message-level */ - case ETHTOOL_SMSGLVL: { - struct ethtool_value edata; +static void cas_get_regs(struct net_device *dev, struct ethtool_regs *regs, + void *p) +{ + struct cas *cp = netdev_priv(dev); + regs->version = 0; + /* cas_read_regs handles locks (cp->lock). */ + cas_read_regs(cp, p, regs->len / sizeof(u32)); +} - if (!capable(CAP_NET_ADMIN)) { - return (-EPERM); - } - if (copy_from_user(&edata, ep_user, sizeof(edata))) - return -EFAULT; - cp->msg_enable = edata.data; - return 0; - } +static int cas_get_stats_count(struct net_device *dev) +{ + return CAS_NUM_STAT_KEYS; +} - case ETHTOOL_GREGS: { - struct ethtool_regs edata; - u8 *ptr; - int len = cp->casreg_len < CAS_MAX_REGS ? - cp->casreg_len: CAS_MAX_REGS; - - if (copy_from_user(&edata, ep_user, sizeof (edata))) - return -EFAULT; - - if (edata.len > len) - edata.len = len; - edata.version = 0; - if (copy_to_user (ep_user, &edata, sizeof(edata))) - return -EFAULT; - - /* cas_get_regs handles locks (cp->lock). */ - ptr = cas_get_regs(cp); - if (ptr == NULL) - return -ENOMEM; - if (copy_to_user(ep_user + sizeof (edata), ptr, edata.len)) - return -EFAULT; - - kfree(ptr); - return (0); - } - case ETHTOOL_GSTRINGS: { - struct ethtool_gstrings edata; - int len; - - if (copy_from_user(&edata, ep_user, sizeof(edata))) - return -EFAULT; - - len = edata.len; - switch(edata.string_set) { - case ETH_SS_STATS: - edata.len = (len < CAS_NUM_STAT_KEYS) ? - len : CAS_NUM_STAT_KEYS; - if (copy_to_user(ep_user, &edata, sizeof(edata))) - return -EFAULT; - - if (copy_to_user(ep_user + sizeof(edata), - ðtool_cassini_statnames, - (edata.len * ETH_GSTRING_LEN))) - return -EFAULT; - return 0; - default: - return -EINVAL; - } - } - case ETHTOOL_GSTATS: { - int i = 0; - u64 *tmp; - struct ethtool_stats edata; - struct net_device_stats *stats; - int len; - - if (copy_from_user(&edata, ep_user, sizeof(edata))) - return -EFAULT; - - len = edata.n_stats; - stats = cas_get_stats(cp->dev); - edata.cmd = ETHTOOL_GSTATS; - edata.n_stats = (len < CAS_NUM_STAT_KEYS) ? - len : CAS_NUM_STAT_KEYS; - if (copy_to_user(ep_user, &edata, sizeof (edata))) - return -EFAULT; - - tmp = kmalloc(sizeof(u64)*CAS_NUM_STAT_KEYS, GFP_KERNEL); - if (tmp) { - tmp[i++] = stats->collisions; - tmp[i++] = stats->rx_bytes; - tmp[i++] = stats->rx_crc_errors; - tmp[i++] = stats->rx_dropped; - tmp[i++] = stats->rx_errors; - tmp[i++] = stats->rx_fifo_errors; - tmp[i++] = stats->rx_frame_errors; - tmp[i++] = stats->rx_length_errors; - tmp[i++] = stats->rx_over_errors; - tmp[i++] = stats->rx_packets; - tmp[i++] = stats->tx_aborted_errors; - tmp[i++] = stats->tx_bytes; - tmp[i++] = stats->tx_dropped; - tmp[i++] = stats->tx_errors; - tmp[i++] = stats->tx_fifo_errors; - tmp[i++] = stats->tx_packets; - BUG_ON(i != CAS_NUM_STAT_KEYS); - - i = copy_to_user(ep_user + sizeof(edata), - tmp, sizeof(u64)*edata.n_stats); - kfree(tmp); - } else { - return -ENOMEM; - } - if (i) - return -EFAULT; - return 0; - } - } +static void cas_get_strings(struct net_device *dev, u32 stringset, u8 *data) +{ + memcpy(data, ðtool_cassini_statnames, + CAS_NUM_STAT_KEYS * ETH_GSTRING_LEN); +} - return -EOPNOTSUPP; +static void cas_get_ethtool_stats(struct net_device *dev, + struct ethtool_stats *estats, u64 *data) +{ + struct cas *cp = netdev_priv(dev); + struct net_device_stats *stats = cas_get_stats(cp->dev); + int i = 0; + data[i++] = stats->collisions; + data[i++] = stats->rx_bytes; + data[i++] = stats->rx_crc_errors; + data[i++] = stats->rx_dropped; + data[i++] = stats->rx_errors; + data[i++] = stats->rx_fifo_errors; + data[i++] = stats->rx_frame_errors; + data[i++] = stats->rx_length_errors; + data[i++] = stats->rx_over_errors; + data[i++] = stats->rx_packets; + data[i++] = stats->tx_aborted_errors; + data[i++] = stats->tx_bytes; + data[i++] = stats->tx_dropped; + data[i++] = stats->tx_errors; + data[i++] = stats->tx_fifo_errors; + data[i++] = stats->tx_packets; + BUG_ON(i != CAS_NUM_STAT_KEYS); } +static struct ethtool_ops cas_ethtool_ops = { + .get_drvinfo = cas_get_drvinfo, + .get_settings = cas_get_settings, + .set_settings = cas_set_settings, + .nway_reset = cas_nway_reset, + .get_link = cas_get_link, + .get_msglevel = cas_get_msglevel, + .set_msglevel = cas_set_msglevel, + .get_regs_len = cas_get_regs_len, + .get_regs = cas_get_regs, + .get_stats_count = cas_get_stats_count, + .get_strings = cas_get_strings, + .get_ethtool_stats = cas_get_ethtool_stats, +}; + static int cas_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd) { struct cas *cp = netdev_priv(dev); @@ -4883,10 +4812,6 @@ static int cas_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd) */ down(&cp->pm_sem); switch (cmd) { - case SIOCETHTOOL: - rc = cas_ethtool_ioctl(dev, ifr->ifr_data); - break; - case SIOCGMIIPHY: /* Get address of MII PHY in use. */ data->phy_id = cp->phy_addr; /* Fallthrough... */ @@ -5112,6 +5037,7 @@ static int __devinit cas_init_one(struct pci_dev *pdev, dev->get_stats = cas_get_stats; dev->set_multicast_list = cas_set_multicast; dev->do_ioctl = cas_ioctl; + dev->ethtool_ops = &cas_ethtool_ops; dev->tx_timeout = cas_tx_timeout; dev->watchdog_timeo = CAS_TX_TIMEOUT; dev->change_mtu = cas_change_mtu; -- cgit v1.2.3 From 399de50bbbb2501a6db43daaa8a2dafbc9bcfe0c Mon Sep 17 00:00:00 2001 From: Michael Chan Date: Mon, 3 Oct 2005 14:02:39 -0700 Subject: [TG3]: Refine AMD K8 write-reorder chipset test. Test for VIA K8T800 north bridge instead of AMD K8 HyperTransport bridge based on new information from Andi Kleen. The AMD HyperTransport interface is not responsible for PCI transactions and so the re-ordering is more likely done by the VIA north bridge. This code is subject to change if we get more information from AMD or VIA. PCI Express devices are excluded from doing the read flush since all chipsets in the write_reorder list are PCI chipsets. Signed-off-by: Michael Chan Signed-off-by: David S. Miller --- drivers/net/tg3.c | 23 ++++++++++++----------- 1 file changed, 12 insertions(+), 11 deletions(-) diff --git a/drivers/net/tg3.c b/drivers/net/tg3.c index 25f85fb9df4..fee0e6e5ff1 100644 --- a/drivers/net/tg3.c +++ b/drivers/net/tg3.c @@ -9284,8 +9284,8 @@ static int __devinit tg3_get_invariants(struct tg3 *tp) static struct pci_device_id write_reorder_chipsets[] = { { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_FE_GATE_700C) }, - { PCI_DEVICE(PCI_VENDOR_ID_AMD, - PCI_DEVICE_ID_AMD_K8_NB) }, + { PCI_DEVICE(PCI_VENDOR_ID_VIA, + PCI_DEVICE_ID_VIA_8385_0) }, { }, }; u32 misc_ctrl_reg; @@ -9300,15 +9300,6 @@ static int __devinit tg3_get_invariants(struct tg3 *tp) tp->tg3_flags2 |= TG3_FLG2_SUN_570X; #endif - /* If we have an AMD 762 or K8 chipset, write - * reordering to the mailbox registers done by the host - * controller can cause major troubles. We read back from - * every mailbox register write to force the writes to be - * posted to the chip in order. - */ - if (pci_dev_present(write_reorder_chipsets)) - tp->tg3_flags |= TG3_FLAG_MBOX_WRITE_REORDER; - /* Force memory write invalidate off. If we leave it on, * then on 5700_BX chips we have to enable a workaround. * The workaround is to set the TG3PCI_DMA_RW_CTRL boundary @@ -9439,6 +9430,16 @@ static int __devinit tg3_get_invariants(struct tg3 *tp) if (pci_find_capability(tp->pdev, PCI_CAP_ID_EXP) != 0) tp->tg3_flags2 |= TG3_FLG2_PCI_EXPRESS; + /* If we have an AMD 762 or VIA K8T800 chipset, write + * reordering to the mailbox registers done by the host + * controller can cause major troubles. We read back from + * every mailbox register write to force the writes to be + * posted to the chip in order. + */ + if (pci_dev_present(write_reorder_chipsets) && + !(tp->tg3_flags2 & TG3_FLG2_PCI_EXPRESS)) + tp->tg3_flags |= TG3_FLAG_MBOX_WRITE_REORDER; + if (GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5703 && tp->pci_lat_timer < 64) { tp->pci_lat_timer = 64; -- cgit v1.2.3 From 81c3d5470ecc70564eb9209946730fe2be93ad06 Mon Sep 17 00:00:00 2001 From: Eric Dumazet Date: Mon, 3 Oct 2005 14:13:38 -0700 Subject: [INET]: speedup inet (tcp/dccp) lookups Arnaldo and I agreed it could be applied now, because I have other pending patches depending on this one (Thank you Arnaldo) (The other important patch moves skc_refcnt in a separate cache line, so that the SMP/NUMA performance doesnt suffer from cache line ping pongs) 1) First some performance data : -------------------------------- tcp_v4_rcv() wastes a *lot* of time in __inet_lookup_established() The most time critical code is : sk_for_each(sk, node, &head->chain) { if (INET_MATCH(sk, acookie, saddr, daddr, ports, dif)) goto hit; /* You sunk my battleship! */ } The sk_for_each() does use prefetch() hints but only the begining of "struct sock" is prefetched. As INET_MATCH first comparison uses inet_sk(__sk)->daddr, wich is far away from the begining of "struct sock", it has to bring into CPU cache cold cache line. Each iteration has to use at least 2 cache lines. This can be problematic if some chains are very long. 2) The goal ----------- The idea I had is to change things so that INET_MATCH() may return FALSE in 99% of cases only using the data already in the CPU cache, using one cache line per iteration. 3) Description of the patch --------------------------- Adds a new 'unsigned int skc_hash' field in 'struct sock_common', filling a 32 bits hole on 64 bits platform. struct sock_common { unsigned short skc_family; volatile unsigned char skc_state; unsigned char skc_reuse; int skc_bound_dev_if; struct hlist_node skc_node; struct hlist_node skc_bind_node; atomic_t skc_refcnt; + unsigned int skc_hash; struct proto *skc_prot; }; Store in this 32 bits field the full hash, not masked by (ehash_size - 1) Using this full hash as the first comparison done in INET_MATCH permits us immediatly skip the element without touching a second cache line in case of a miss. Suppress the sk_hashent/tw_hashent fields since skc_hash (aliased to sk_hash and tw_hash) already contains the slot number if we mask with (ehash_size - 1) File include/net/inet_hashtables.h 64 bits platforms : #define INET_MATCH(__sk, __hash, __cookie, __saddr, __daddr, __ports, __dif)\ (((__sk)->sk_hash == (__hash)) ((*((__u64 *)&(inet_sk(__sk)->daddr)))== (__cookie)) && \ ((*((__u32 *)&(inet_sk(__sk)->dport))) == (__ports)) && \ (!((__sk)->sk_bound_dev_if) || ((__sk)->sk_bound_dev_if == (__dif)))) 32bits platforms: #define TCP_IPV4_MATCH(__sk, __hash, __cookie, __saddr, __daddr, __ports, __dif)\ (((__sk)->sk_hash == (__hash)) && \ (inet_sk(__sk)->daddr == (__saddr)) && \ (inet_sk(__sk)->rcv_saddr == (__daddr)) && \ (!((__sk)->sk_bound_dev_if) || ((__sk)->sk_bound_dev_if == (__dif)))) - Adds a prefetch(head->chain.first) in __inet_lookup_established()/__tcp_v4_check_established() and __inet6_lookup_established()/__tcp_v6_check_established() and __dccp_v4_check_established() to bring into cache the first element of the list, before the {read|write}_lock(&head->lock); Signed-off-by: Eric Dumazet Acked-by: Arnaldo Carvalho de Melo Signed-off-by: David S. Miller --- include/linux/ipv6.h | 5 +-- include/linux/tc_ematch/tc_em_meta.h | 2 +- include/net/inet6_hashtables.h | 21 ++++++------ include/net/inet_hashtables.h | 64 +++++++++++++++++++++--------------- include/net/inet_timewait_sock.h | 2 +- include/net/sock.h | 5 +-- net/atm/common.c | 2 +- net/dccp/ipv4.c | 12 +++---- net/ipv4/inet_timewait_sock.c | 6 ++-- net/ipv4/tcp_ipv4.c | 11 ++++--- net/ipv6/tcp_ipv6.c | 18 +++++----- net/sched/em_meta.c | 6 ++-- 12 files changed, 85 insertions(+), 69 deletions(-) diff --git a/include/linux/ipv6.h b/include/linux/ipv6.h index bb6f88e1406..e0b922785d9 100644 --- a/include/linux/ipv6.h +++ b/include/linux/ipv6.h @@ -372,8 +372,9 @@ static inline struct raw6_sock *raw6_sk(const struct sock *sk) #define inet_v6_ipv6only(__sk) 0 #endif /* defined(CONFIG_IPV6) || defined(CONFIG_IPV6_MODULE) */ -#define INET6_MATCH(__sk, __saddr, __daddr, __ports, __dif) \ - (((*((__u32 *)&(inet_sk(__sk)->dport))) == (__ports)) && \ +#define INET6_MATCH(__sk, __hash, __saddr, __daddr, __ports, __dif)\ + (((__sk)->sk_hash == (__hash)) && \ + ((*((__u32 *)&(inet_sk(__sk)->dport))) == (__ports)) && \ ((__sk)->sk_family == AF_INET6) && \ ipv6_addr_equal(&inet6_sk(__sk)->daddr, (__saddr)) && \ ipv6_addr_equal(&inet6_sk(__sk)->rcv_saddr, (__daddr)) && \ diff --git a/include/linux/tc_ematch/tc_em_meta.h b/include/linux/tc_ematch/tc_em_meta.h index 081b1ee8516..e21937cf91d 100644 --- a/include/linux/tc_ematch/tc_em_meta.h +++ b/include/linux/tc_ematch/tc_em_meta.h @@ -71,7 +71,7 @@ enum TCF_META_ID_SK_SNDBUF, TCF_META_ID_SK_ALLOCS, TCF_META_ID_SK_ROUTE_CAPS, - TCF_META_ID_SK_HASHENT, + TCF_META_ID_SK_HASH, TCF_META_ID_SK_LINGERTIME, TCF_META_ID_SK_ACK_BACKLOG, TCF_META_ID_SK_MAX_ACK_BACKLOG, diff --git a/include/net/inet6_hashtables.h b/include/net/inet6_hashtables.h index 03df3b15796..5a2beed5a77 100644 --- a/include/net/inet6_hashtables.h +++ b/include/net/inet6_hashtables.h @@ -26,19 +26,18 @@ struct inet_hashinfo; /* I have no idea if this is a good hash for v6 or not. -DaveM */ -static inline int inet6_ehashfn(const struct in6_addr *laddr, const u16 lport, - const struct in6_addr *faddr, const u16 fport, - const int ehash_size) +static inline unsigned int inet6_ehashfn(const struct in6_addr *laddr, const u16 lport, + const struct in6_addr *faddr, const u16 fport) { - int hashent = (lport ^ fport); + unsigned int hashent = (lport ^ fport); hashent ^= (laddr->s6_addr32[3] ^ faddr->s6_addr32[3]); hashent ^= hashent >> 16; hashent ^= hashent >> 8; - return (hashent & (ehash_size - 1)); + return hashent; } -static inline int inet6_sk_ehashfn(const struct sock *sk, const int ehash_size) +static inline int inet6_sk_ehashfn(const struct sock *sk) { const struct inet_sock *inet = inet_sk(sk); const struct ipv6_pinfo *np = inet6_sk(sk); @@ -46,7 +45,7 @@ static inline int inet6_sk_ehashfn(const struct sock *sk, const int ehash_size) const struct in6_addr *faddr = &np->daddr; const __u16 lport = inet->num; const __u16 fport = inet->dport; - return inet6_ehashfn(laddr, lport, faddr, fport, ehash_size); + return inet6_ehashfn(laddr, lport, faddr, fport); } /* @@ -69,14 +68,14 @@ static inline struct sock * /* Optimize here for direct hit, only listening connections can * have wildcards anyways. */ - const int hash = inet6_ehashfn(daddr, hnum, saddr, sport, - hashinfo->ehash_size); - struct inet_ehash_bucket *head = &hashinfo->ehash[hash]; + unsigned int hash = inet6_ehashfn(daddr, hnum, saddr, sport); + struct inet_ehash_bucket *head = inet_ehash_bucket(hashinfo, hash); + prefetch(head->chain.first); read_lock(&head->lock); sk_for_each(sk, node, &head->chain) { /* For IPV6 do the cheaper port and family tests first. */ - if (INET6_MATCH(sk, saddr, daddr, ports, dif)) + if (INET6_MATCH(sk, hash, saddr, daddr, ports, dif)) goto hit; /* You sunk my battleship! */ } /* Must check for a TIME_WAIT'er before going to listener hash. */ diff --git a/include/net/inet_hashtables.h b/include/net/inet_hashtables.h index 646b6ea7fe2..35f49e65e29 100644 --- a/include/net/inet_hashtables.h +++ b/include/net/inet_hashtables.h @@ -108,7 +108,7 @@ struct inet_hashinfo { struct inet_bind_hashbucket *bhash; int bhash_size; - int ehash_size; + unsigned int ehash_size; /* All sockets in TCP_LISTEN state will be in here. This is the only * table where wildcard'd TCP sockets can exist. Hash function here @@ -130,17 +130,16 @@ struct inet_hashinfo { int port_rover; }; -static inline int inet_ehashfn(const __u32 laddr, const __u16 lport, - const __u32 faddr, const __u16 fport, - const int ehash_size) +static inline unsigned int inet_ehashfn(const __u32 laddr, const __u16 lport, + const __u32 faddr, const __u16 fport) { - int h = (laddr ^ lport) ^ (faddr ^ fport); + unsigned int h = (laddr ^ lport) ^ (faddr ^ fport); h ^= h >> 16; h ^= h >> 8; - return h & (ehash_size - 1); + return h; } -static inline int inet_sk_ehashfn(const struct sock *sk, const int ehash_size) +static inline int inet_sk_ehashfn(const struct sock *sk) { const struct inet_sock *inet = inet_sk(sk); const __u32 laddr = inet->rcv_saddr; @@ -148,7 +147,14 @@ static inline int inet_sk_ehashfn(const struct sock *sk, const int ehash_size) const __u32 faddr = inet->daddr; const __u16 fport = inet->dport; - return inet_ehashfn(laddr, lport, faddr, fport, ehash_size); + return inet_ehashfn(laddr, lport, faddr, fport); +} + +static inline struct inet_ehash_bucket *inet_ehash_bucket( + struct inet_hashinfo *hashinfo, + unsigned int hash) +{ + return &hashinfo->ehash[hash & (hashinfo->ehash_size - 1)]; } extern struct inet_bind_bucket * @@ -235,9 +241,11 @@ static inline void __inet_hash(struct inet_hashinfo *hashinfo, lock = &hashinfo->lhash_lock; inet_listen_wlock(hashinfo); } else { - sk->sk_hashent = inet_sk_ehashfn(sk, hashinfo->ehash_size); - list = &hashinfo->ehash[sk->sk_hashent].chain; - lock = &hashinfo->ehash[sk->sk_hashent].lock; + struct inet_ehash_bucket *head; + sk->sk_hash = inet_sk_ehashfn(sk); + head = inet_ehash_bucket(hashinfo, sk->sk_hash); + list = &head->chain; + lock = &head->lock; write_lock(lock); } __sk_add_node(sk, list); @@ -268,9 +276,8 @@ static inline void inet_unhash(struct inet_hashinfo *hashinfo, struct sock *sk) inet_listen_wlock(hashinfo); lock = &hashinfo->lhash_lock; } else { - struct inet_ehash_bucket *head = &hashinfo->ehash[sk->sk_hashent]; - lock = &head->lock; - write_lock_bh(&head->lock); + lock = &inet_ehash_bucket(hashinfo, sk->sk_hash)->lock; + write_lock_bh(lock); } if (__sk_del_node_init(sk)) @@ -337,23 +344,27 @@ sherry_cache: #define INET_ADDR_COOKIE(__name, __saddr, __daddr) \ const __u64 __name = (((__u64)(__daddr)) << 32) | ((__u64)(__saddr)); #endif /* __BIG_ENDIAN */ -#define INET_MATCH(__sk, __cookie, __saddr, __daddr, __ports, __dif)\ - (((*((__u64 *)&(inet_sk(__sk)->daddr))) == (__cookie)) && \ +#define INET_MATCH(__sk, __hash, __cookie, __saddr, __daddr, __ports, __dif)\ + (((__sk)->sk_hash == (__hash)) && \ + ((*((__u64 *)&(inet_sk(__sk)->daddr))) == (__cookie)) && \ ((*((__u32 *)&(inet_sk(__sk)->dport))) == (__ports)) && \ (!((__sk)->sk_bound_dev_if) || ((__sk)->sk_bound_dev_if == (__dif)))) -#define INET_TW_MATCH(__sk, __cookie, __saddr, __daddr, __ports, __dif)\ - (((*((__u64 *)&(inet_twsk(__sk)->tw_daddr))) == (__cookie)) && \ +#define INET_TW_MATCH(__sk, __hash, __cookie, __saddr, __daddr, __ports, __dif)\ + (((__sk)->sk_hash == (__hash)) && \ + ((*((__u64 *)&(inet_twsk(__sk)->tw_daddr))) == (__cookie)) && \ ((*((__u32 *)&(inet_twsk(__sk)->tw_dport))) == (__ports)) && \ (!((__sk)->sk_bound_dev_if) || ((__sk)->sk_bound_dev_if == (__dif)))) #else /* 32-bit arch */ #define INET_ADDR_COOKIE(__name, __saddr, __daddr) -#define INET_MATCH(__sk, __cookie, __saddr, __daddr, __ports, __dif) \ - ((inet_sk(__sk)->daddr == (__saddr)) && \ +#define INET_MATCH(__sk, __hash, __cookie, __saddr, __daddr, __ports, __dif) \ + (((__sk)->sk_hash == (__hash)) && \ + (inet_sk(__sk)->daddr == (__saddr)) && \ (inet_sk(__sk)->rcv_saddr == (__daddr)) && \ ((*((__u32 *)&(inet_sk(__sk)->dport))) == (__ports)) && \ (!((__sk)->sk_bound_dev_if) || ((__sk)->sk_bound_dev_if == (__dif)))) -#define INET_TW_MATCH(__sk, __cookie, __saddr, __daddr, __ports, __dif) \ - ((inet_twsk(__sk)->tw_daddr == (__saddr)) && \ +#define INET_TW_MATCH(__sk, __hash,__cookie, __saddr, __daddr, __ports, __dif) \ + (((__sk)->sk_hash == (__hash)) && \ + (inet_twsk(__sk)->tw_daddr == (__saddr)) && \ (inet_twsk(__sk)->tw_rcv_saddr == (__daddr)) && \ ((*((__u32 *)&(inet_twsk(__sk)->tw_dport))) == (__ports)) && \ (!((__sk)->sk_bound_dev_if) || ((__sk)->sk_bound_dev_if == (__dif)))) @@ -378,18 +389,19 @@ static inline struct sock * /* Optimize here for direct hit, only listening connections can * have wildcards anyways. */ - const int hash = inet_ehashfn(daddr, hnum, saddr, sport, hashinfo->ehash_size); - struct inet_ehash_bucket *head = &hashinfo->ehash[hash]; + unsigned int hash = inet_ehashfn(daddr, hnum, saddr, sport); + struct inet_ehash_bucket *head = inet_ehash_bucket(hashinfo, hash); + prefetch(head->chain.first); read_lock(&head->lock); sk_for_each(sk, node, &head->chain) { - if (INET_MATCH(sk, acookie, saddr, daddr, ports, dif)) + if (INET_MATCH(sk, hash, acookie, saddr, daddr, ports, dif)) goto hit; /* You sunk my battleship! */ } /* Must check for a TIME_WAIT'er before going to listener hash. */ sk_for_each(sk, node, &(head + hashinfo->ehash_size)->chain) { - if (INET_TW_MATCH(sk, acookie, saddr, daddr, ports, dif)) + if (INET_TW_MATCH(sk, hash, acookie, saddr, daddr, ports, dif)) goto hit; } sk = NULL; diff --git a/include/net/inet_timewait_sock.h b/include/net/inet_timewait_sock.h index 3b070352e86..4ade56ef3a4 100644 --- a/include/net/inet_timewait_sock.h +++ b/include/net/inet_timewait_sock.h @@ -112,6 +112,7 @@ struct inet_timewait_sock { #define tw_node __tw_common.skc_node #define tw_bind_node __tw_common.skc_bind_node #define tw_refcnt __tw_common.skc_refcnt +#define tw_hash __tw_common.skc_hash #define tw_prot __tw_common.skc_prot volatile unsigned char tw_substate; /* 3 bits hole, try to pack */ @@ -126,7 +127,6 @@ struct inet_timewait_sock { /* And these are ours. */ __u8 tw_ipv6only:1; /* 31 bits hole, try to pack */ - int tw_hashent; int tw_timeout; unsigned long tw_ttd; struct inet_bind_bucket *tw_tb; diff --git a/include/net/sock.h b/include/net/sock.h index 8c48fbecb7c..b6440805c42 100644 --- a/include/net/sock.h +++ b/include/net/sock.h @@ -99,6 +99,7 @@ struct proto; * @skc_node: main hash linkage for various protocol lookup tables * @skc_bind_node: bind hash linkage for various protocol lookup tables * @skc_refcnt: reference count + * @skc_hash: hash value used with various protocol lookup tables * @skc_prot: protocol handlers inside a network family * * This is the minimal network layer representation of sockets, the header @@ -112,6 +113,7 @@ struct sock_common { struct hlist_node skc_node; struct hlist_node skc_bind_node; atomic_t skc_refcnt; + unsigned int skc_hash; struct proto *skc_prot; }; @@ -139,7 +141,6 @@ struct sock_common { * @sk_no_check: %SO_NO_CHECK setting, wether or not checkup packets * @sk_route_caps: route capabilities (e.g. %NETIF_F_TSO) * @sk_lingertime: %SO_LINGER l_linger setting - * @sk_hashent: hash entry in several tables (e.g. inet_hashinfo.ehash) * @sk_backlog: always used with the per-socket spinlock held * @sk_callback_lock: used with the callbacks in the end of this struct * @sk_error_queue: rarely used @@ -186,6 +187,7 @@ struct sock { #define sk_node __sk_common.skc_node #define sk_bind_node __sk_common.skc_bind_node #define sk_refcnt __sk_common.skc_refcnt +#define sk_hash __sk_common.skc_hash #define sk_prot __sk_common.skc_prot unsigned char sk_shutdown : 2, sk_no_check : 2, @@ -208,7 +210,6 @@ struct sock { unsigned int sk_allocation; int sk_sndbuf; int sk_route_caps; - int sk_hashent; unsigned long sk_flags; unsigned long sk_lingertime; /* diff --git a/net/atm/common.c b/net/atm/common.c index 801a5813ec6..63feea49fb1 100644 --- a/net/atm/common.c +++ b/net/atm/common.c @@ -46,7 +46,7 @@ static void __vcc_insert_socket(struct sock *sk) struct atm_vcc *vcc = atm_sk(sk); struct hlist_head *head = &vcc_hash[vcc->vci & (VCC_HTABLE_SIZE - 1)]; - sk->sk_hashent = vcc->vci & (VCC_HTABLE_SIZE - 1); + sk->sk_hash = vcc->vci & (VCC_HTABLE_SIZE - 1); sk_add_node(sk, head); } diff --git a/net/dccp/ipv4.c b/net/dccp/ipv4.c index 40fe6afacde..ae088d1347a 100644 --- a/net/dccp/ipv4.c +++ b/net/dccp/ipv4.c @@ -62,27 +62,27 @@ static int __dccp_v4_check_established(struct sock *sk, const __u16 lport, const int dif = sk->sk_bound_dev_if; INET_ADDR_COOKIE(acookie, saddr, daddr) const __u32 ports = INET_COMBINED_PORTS(inet->dport, lport); - const int hash = inet_ehashfn(daddr, lport, saddr, inet->dport, - dccp_hashinfo.ehash_size); - struct inet_ehash_bucket *head = &dccp_hashinfo.ehash[hash]; + unsigned int hash = inet_ehashfn(daddr, lport, saddr, inet->dport); + struct inet_ehash_bucket *head = inet_ehash_bucket(&dccp_hashinfo, hash); const struct sock *sk2; const struct hlist_node *node; struct inet_timewait_sock *tw; + prefetch(head->chain.first); write_lock(&head->lock); /* Check TIME-WAIT sockets first. */ sk_for_each(sk2, node, &(head + dccp_hashinfo.ehash_size)->chain) { tw = inet_twsk(sk2); - if (INET_TW_MATCH(sk2, acookie, saddr, daddr, ports, dif)) + if (INET_TW_MATCH(sk2, hash, acookie, saddr, daddr, ports, dif)) goto not_unique; } tw = NULL; /* And established part... */ sk_for_each(sk2, node, &head->chain) { - if (INET_MATCH(sk2, acookie, saddr, daddr, ports, dif)) + if (INET_MATCH(sk2, hash, acookie, saddr, daddr, ports, dif)) goto not_unique; } @@ -90,7 +90,7 @@ static int __dccp_v4_check_established(struct sock *sk, const __u16 lport, * in hash table socket with a funny identity. */ inet->num = lport; inet->sport = htons(lport); - sk->sk_hashent = hash; + sk->sk_hash = hash; BUG_TRAP(sk_unhashed(sk)); __sk_add_node(sk, &head->chain); sock_prot_inc_use(sk->sk_prot); diff --git a/net/ipv4/inet_timewait_sock.c b/net/ipv4/inet_timewait_sock.c index 4d1502a4985..f9076ef3a1a 100644 --- a/net/ipv4/inet_timewait_sock.c +++ b/net/ipv4/inet_timewait_sock.c @@ -20,7 +20,7 @@ void __inet_twsk_kill(struct inet_timewait_sock *tw, struct inet_hashinfo *hashi struct inet_bind_hashbucket *bhead; struct inet_bind_bucket *tb; /* Unlink from established hashes. */ - struct inet_ehash_bucket *ehead = &hashinfo->ehash[tw->tw_hashent]; + struct inet_ehash_bucket *ehead = inet_ehash_bucket(hashinfo, tw->tw_hash); write_lock(&ehead->lock); if (hlist_unhashed(&tw->tw_node)) { @@ -60,7 +60,7 @@ void __inet_twsk_hashdance(struct inet_timewait_sock *tw, struct sock *sk, { const struct inet_sock *inet = inet_sk(sk); const struct inet_connection_sock *icsk = inet_csk(sk); - struct inet_ehash_bucket *ehead = &hashinfo->ehash[sk->sk_hashent]; + struct inet_ehash_bucket *ehead = inet_ehash_bucket(hashinfo, sk->sk_hash); struct inet_bind_hashbucket *bhead; /* Step 1: Put TW into bind hash. Original socket stays there too. Note, that any socket with inet->num != 0 MUST be bound in @@ -106,7 +106,7 @@ struct inet_timewait_sock *inet_twsk_alloc(const struct sock *sk, const int stat tw->tw_dport = inet->dport; tw->tw_family = sk->sk_family; tw->tw_reuse = sk->sk_reuse; - tw->tw_hashent = sk->sk_hashent; + tw->tw_hash = sk->sk_hash; tw->tw_ipv6only = 0; tw->tw_prot = sk->sk_prot_creator; atomic_set(&tw->tw_refcnt, 1); diff --git a/net/ipv4/tcp_ipv4.c b/net/ipv4/tcp_ipv4.c index 13dfb391cdf..c85819d8474 100644 --- a/net/ipv4/tcp_ipv4.c +++ b/net/ipv4/tcp_ipv4.c @@ -130,19 +130,20 @@ static int __tcp_v4_check_established(struct sock *sk, __u16 lport, int dif = sk->sk_bound_dev_if; INET_ADDR_COOKIE(acookie, saddr, daddr) const __u32 ports = INET_COMBINED_PORTS(inet->dport, lport); - const int hash = inet_ehashfn(daddr, lport, saddr, inet->dport, tcp_hashinfo.ehash_size); - struct inet_ehash_bucket *head = &tcp_hashinfo.ehash[hash]; + unsigned int hash = inet_ehashfn(daddr, lport, saddr, inet->dport); + struct inet_ehash_bucket *head = inet_ehash_bucket(&tcp_hashinfo, hash); struct sock *sk2; const struct hlist_node *node; struct inet_timewait_sock *tw; + prefetch(head->chain.first); write_lock(&head->lock); /* Check TIME-WAIT sockets first. */ sk_for_each(sk2, node, &(head + tcp_hashinfo.ehash_size)->chain) { tw = inet_twsk(sk2); - if (INET_TW_MATCH(sk2, acookie, saddr, daddr, ports, dif)) { + if (INET_TW_MATCH(sk2, hash, acookie, saddr, daddr, ports, dif)) { const struct tcp_timewait_sock *tcptw = tcp_twsk(sk2); struct tcp_sock *tp = tcp_sk(sk); @@ -179,7 +180,7 @@ static int __tcp_v4_check_established(struct sock *sk, __u16 lport, /* And established part... */ sk_for_each(sk2, node, &head->chain) { - if (INET_MATCH(sk2, acookie, saddr, daddr, ports, dif)) + if (INET_MATCH(sk2, hash, acookie, saddr, daddr, ports, dif)) goto not_unique; } @@ -188,7 +189,7 @@ unique: * in hash table socket with a funny identity. */ inet->num = lport; inet->sport = htons(lport); - sk->sk_hashent = hash; + sk->sk_hash = hash; BUG_TRAP(sk_unhashed(sk)); __sk_add_node(sk, &head->chain); sock_prot_inc_use(sk->sk_prot); diff --git a/net/ipv6/tcp_ipv6.c b/net/ipv6/tcp_ipv6.c index 80643e6b346..d693cb988b7 100644 --- a/net/ipv6/tcp_ipv6.c +++ b/net/ipv6/tcp_ipv6.c @@ -209,9 +209,11 @@ static __inline__ void __tcp_v6_hash(struct sock *sk) lock = &tcp_hashinfo.lhash_lock; inet_listen_wlock(&tcp_hashinfo); } else { - sk->sk_hashent = inet6_sk_ehashfn(sk, tcp_hashinfo.ehash_size); - list = &tcp_hashinfo.ehash[sk->sk_hashent].chain; - lock = &tcp_hashinfo.ehash[sk->sk_hashent].lock; + unsigned int hash; + sk->sk_hash = hash = inet6_sk_ehashfn(sk); + hash &= (tcp_hashinfo.ehash_size - 1); + list = &tcp_hashinfo.ehash[hash].chain; + lock = &tcp_hashinfo.ehash[hash].lock; write_lock(lock); } @@ -322,13 +324,13 @@ static int __tcp_v6_check_established(struct sock *sk, const __u16 lport, const struct in6_addr *saddr = &np->daddr; const int dif = sk->sk_bound_dev_if; const u32 ports = INET_COMBINED_PORTS(inet->dport, lport); - const int hash = inet6_ehashfn(daddr, inet->num, saddr, inet->dport, - tcp_hashinfo.ehash_size); - struct inet_ehash_bucket *head = &tcp_hashinfo.ehash[hash]; + unsigned int hash = inet6_ehashfn(daddr, inet->num, saddr, inet->dport); + struct inet_ehash_bucket *head = inet_ehash_bucket(&tcp_hashinfo, hash); struct sock *sk2; const struct hlist_node *node; struct inet_timewait_sock *tw; + prefetch(head->chain.first); write_lock(&head->lock); /* Check TIME-WAIT sockets first. */ @@ -365,14 +367,14 @@ static int __tcp_v6_check_established(struct sock *sk, const __u16 lport, /* And established part... */ sk_for_each(sk2, node, &head->chain) { - if (INET6_MATCH(sk2, saddr, daddr, ports, dif)) + if (INET6_MATCH(sk2, hash, saddr, daddr, ports, dif)) goto not_unique; } unique: BUG_TRAP(sk_unhashed(sk)); __sk_add_node(sk, &head->chain); - sk->sk_hashent = hash; + sk->sk_hash = hash; sock_prot_inc_use(sk->sk_prot); write_unlock(&head->lock); diff --git a/net/sched/em_meta.c b/net/sched/em_meta.c index 00eae5f9a01..cf68a59fdc5 100644 --- a/net/sched/em_meta.c +++ b/net/sched/em_meta.c @@ -393,10 +393,10 @@ META_COLLECTOR(int_sk_route_caps) dst->value = skb->sk->sk_route_caps; } -META_COLLECTOR(int_sk_hashent) +META_COLLECTOR(int_sk_hash) { SKIP_NONLOCAL(skb); - dst->value = skb->sk->sk_hashent; + dst->value = skb->sk->sk_hash; } META_COLLECTOR(int_sk_lingertime) @@ -515,7 +515,7 @@ static struct meta_ops __meta_ops[TCF_META_TYPE_MAX+1][TCF_META_ID_MAX+1] = { [META_ID(SK_FORWARD_ALLOCS)] = META_FUNC(int_sk_fwd_alloc), [META_ID(SK_ALLOCS)] = META_FUNC(int_sk_alloc), [META_ID(SK_ROUTE_CAPS)] = META_FUNC(int_sk_route_caps), - [META_ID(SK_HASHENT)] = META_FUNC(int_sk_hashent), + [META_ID(SK_HASH)] = META_FUNC(int_sk_hash), [META_ID(SK_LINGERTIME)] = META_FUNC(int_sk_lingertime), [META_ID(SK_ACK_BACKLOG)] = META_FUNC(int_sk_ack_bl), [META_ID(SK_MAX_ACK_BACKLOG)] = META_FUNC(int_sk_max_ack_bl), -- cgit v1.2.3 From 496a22b08fa326bf17c11eb900e0505aa9da3506 Mon Sep 17 00:00:00 2001 From: Russell King Date: Mon, 3 Oct 2005 14:16:34 -0700 Subject: [NET]: Fix "sysctl_net.c:36: error: 'core_table' undeclared here" During the build for ARM machine type "fortunet", this error occurred: CC net/sysctl_net.o net/sysctl_net.c:36: error: 'core_table' undeclared here (not in a function) It appears that the following configuration settings cause this error due to a missing include: CONFIG_SYSCTL=y CONFIG_NET=y # CONFIG_INET is not set core_table appears to be declared in net/sock.h. if CONFIG_INET were defined, net/sock.h would have been included via: sysctl_net.c -> net/ip.h -> linux/ip.h -> net/sock.h so include it directly. Signed-off-by: Russell King Signed-off-by: David S. Miller --- net/sysctl_net.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/net/sysctl_net.c b/net/sysctl_net.c index c5241fcbb96..55538f6b60f 100644 --- a/net/sysctl_net.c +++ b/net/sysctl_net.c @@ -16,6 +16,8 @@ #include #include +#include + #ifdef CONFIG_INET #include #endif -- cgit v1.2.3 From 444fc8fc3a1f926fa224655b8950bd853368c1a3 Mon Sep 17 00:00:00 2001 From: Herbert Xu Date: Mon, 3 Oct 2005 14:18:10 -0700 Subject: [IPV4]: Fix "Proxy ARP seems broken" Meelis Roos wrote: > RK> My firewall setup relies on proxyarp working. However, with 2.6.14-rc3, > RK> it appears to be completely broken. The firewall is 212.18.232.186, > > Same here with some kernel between 14-rc2 and 14-rc3 - no reposnse to > ARP on a proxyarp gateway. Sorry, no exact revison and no more debugging > yet since it'a a production gateway. The breakage is caused by the change to use the CB area for flagging whether a packet has been queued due to proxy_delay. This area gets cleared every time arp_rcv gets called. Unfortunately packets delayed due to proxy_delay also go through arp_rcv when they are reprocessed. In fact, I can't think of a reason why delayed proxy packets should go through netfilter again at all. So the easiest solution is to bypass that and go straight to arp_process. This is essentially what would've happened before netfilter support was added to ARP. Signed-off-by: Herbert Xu Signed-off-by: David S. Miller --- net/ipv4/arp.c | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/net/ipv4/arp.c b/net/ipv4/arp.c index 8bf312bdea1..ec0e36893b0 100644 --- a/net/ipv4/arp.c +++ b/net/ipv4/arp.c @@ -697,12 +697,6 @@ void arp_send(int type, int ptype, u32 dest_ip, arp_xmit(skb); } -static void parp_redo(struct sk_buff *skb) -{ - nf_reset(skb); - arp_rcv(skb, skb->dev, NULL, skb->dev); -} - /* * Process an arp request. */ @@ -922,6 +916,11 @@ out: return 0; } +static void parp_redo(struct sk_buff *skb) +{ + arp_process(skb); +} + /* * Receive an arp request from the device layer. -- cgit v1.2.3 From f36d6ab182a5c68e92ea3e85821dde9d29bfe284 Mon Sep 17 00:00:00 2001 From: Yan Zheng Date: Mon, 3 Oct 2005 14:19:15 -0700 Subject: [IPV6]: Fix ipv6 fragment ID selection at slow path Signed-Off-By: Yan Zheng Signed-off-by: David S. Miller --- net/ipv6/ip6_output.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/ipv6/ip6_output.c b/net/ipv6/ip6_output.c index 2f589f24c09..563b442ffab 100644 --- a/net/ipv6/ip6_output.c +++ b/net/ipv6/ip6_output.c @@ -666,7 +666,7 @@ slow_path: */ fh->nexthdr = nexthdr; fh->reserved = 0; - if (frag_id) { + if (!frag_id) { ipv6_select_ident(skb, fh); frag_id = fh->identification; } else -- cgit v1.2.3 From a5e7c210fefd2454c757a3542e41063407ca7108 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Mon, 3 Oct 2005 14:21:58 -0700 Subject: [IPV6]: Fix leak added by udp connect dst caching fix. Based upon a patch from Mitsuru KANDA Signed-off-by: David S. Miller --- net/ipv6/udp.c | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/net/ipv6/udp.c b/net/ipv6/udp.c index 6001948600f..e4cad11f284 100644 --- a/net/ipv6/udp.c +++ b/net/ipv6/udp.c @@ -852,10 +852,16 @@ do_append_data: else if (!corkreq) err = udp_v6_push_pending_frames(sk, up); - if (dst && connected) - ip6_dst_store(sk, dst, - ipv6_addr_equal(&fl->fl6_dst, &np->daddr) ? - &np->daddr : NULL); + if (dst) { + if (connected) { + ip6_dst_store(sk, dst, + ipv6_addr_equal(&fl->fl6_dst, &np->daddr) ? + &np->daddr : NULL); + } else { + dst_release(dst); + } + } + if (err > 0) err = np->recverr ? net_xmit_errno(err) : 0; release_sock(sk); -- cgit v1.2.3 From e5ed639913eea3e4783a550291775ab78dd84966 Mon Sep 17 00:00:00 2001 From: Herbert Xu Date: Mon, 3 Oct 2005 14:35:55 -0700 Subject: [IPV4]: Replace __in_dev_get with __in_dev_get_rcu/rtnl The following patch renames __in_dev_get() to __in_dev_get_rtnl() and introduces __in_dev_get_rcu() to cover the second case. 1) RCU with refcnt should use in_dev_get(). 2) RCU without refcnt should use __in_dev_get_rcu(). 3) All others must hold RTNL and use __in_dev_get_rtnl(). There is one exception in net/ipv4/route.c which is in fact a pre-existing race condition. I've marked it as such so that we remember to fix it. This patch is based on suggestions and prior work by Suzanne Wood and Paul McKenney. Signed-off-by: Herbert Xu Signed-off-by: David S. Miller --- drivers/net/bonding/bond_main.c | 2 +- drivers/net/wan/sdlamain.c | 23 ++++++++++++++--------- drivers/net/wan/syncppp.c | 2 +- drivers/net/wireless/strip.c | 4 ++-- drivers/parisc/led.c | 5 ++++- drivers/s390/net/qeth_main.c | 4 ++-- include/linux/inetdevice.h | 12 ++++++++++-- net/atm/clip.c | 2 +- net/core/netpoll.c | 2 +- net/core/pktgen.c | 2 +- net/econet/af_econet.c | 2 +- net/ipv4/arp.c | 10 +++++----- net/ipv4/devinet.c | 22 +++++++++++----------- net/ipv4/fib_frontend.c | 4 ++-- net/ipv4/fib_semantics.c | 4 ++-- net/ipv4/igmp.c | 2 +- net/ipv4/ip_gre.c | 4 ++-- net/ipv4/ipmr.c | 6 +++--- net/ipv4/netfilter/ip_conntrack_netbios_ns.c | 2 +- net/ipv4/netfilter/ipt_REDIRECT.c | 2 +- net/ipv4/route.c | 6 ++++-- net/ipv6/addrconf.c | 2 +- net/irda/irlan/irlan_eth.c | 2 +- net/sctp/protocol.c | 2 +- 24 files changed, 73 insertions(+), 55 deletions(-) diff --git a/drivers/net/bonding/bond_main.c b/drivers/net/bonding/bond_main.c index 6d00c3de1a8..bf81cd45e4d 100644 --- a/drivers/net/bonding/bond_main.c +++ b/drivers/net/bonding/bond_main.c @@ -2776,7 +2776,7 @@ static u32 bond_glean_dev_ip(struct net_device *dev) return 0; rcu_read_lock(); - idev = __in_dev_get(dev); + idev = __in_dev_get_rcu(dev); if (!idev) goto out; diff --git a/drivers/net/wan/sdlamain.c b/drivers/net/wan/sdlamain.c index 74e151acef3..7a8b22a7ea3 100644 --- a/drivers/net/wan/sdlamain.c +++ b/drivers/net/wan/sdlamain.c @@ -57,6 +57,7 @@ #include /* request_region(), release_region() */ #include /* WAN router definitions */ #include /* WANPIPE common user API definitions */ +#include #include #include /* phys_to_virt() */ @@ -1268,37 +1269,41 @@ unsigned long get_ip_address(struct net_device *dev, int option) struct in_ifaddr *ifaddr; struct in_device *in_dev; + unsigned long addr = 0; - if ((in_dev = __in_dev_get(dev)) == NULL){ - return 0; + rcu_read_lock(); + if ((in_dev = __in_dev_get_rcu(dev)) == NULL){ + goto out; } if ((ifaddr = in_dev->ifa_list)== NULL ){ - return 0; + goto out; } switch (option){ case WAN_LOCAL_IP: - return ifaddr->ifa_local; + addr = ifaddr->ifa_local; break; case WAN_POINTOPOINT_IP: - return ifaddr->ifa_address; + addr = ifaddr->ifa_address; break; case WAN_NETMASK_IP: - return ifaddr->ifa_mask; + addr = ifaddr->ifa_mask; break; case WAN_BROADCAST_IP: - return ifaddr->ifa_broadcast; + addr = ifaddr->ifa_broadcast; break; default: - return 0; + break; } - return 0; +out: + rcu_read_unlock(); + return addr; } void add_gateway(sdla_t *card, struct net_device *dev) diff --git a/drivers/net/wan/syncppp.c b/drivers/net/wan/syncppp.c index b56a7b516d2..a6d3b55013a 100644 --- a/drivers/net/wan/syncppp.c +++ b/drivers/net/wan/syncppp.c @@ -769,7 +769,7 @@ static void sppp_cisco_input (struct sppp *sp, struct sk_buff *skb) u32 addr = 0, mask = ~0; /* FIXME: is the mask correct? */ #ifdef CONFIG_INET rcu_read_lock(); - if ((in_dev = __in_dev_get(dev)) != NULL) + if ((in_dev = __in_dev_get_rcu(dev)) != NULL) { for (ifa=in_dev->ifa_list; ifa != NULL; ifa=ifa->ifa_next) { diff --git a/drivers/net/wireless/strip.c b/drivers/net/wireless/strip.c index 4b0acae22b0..7bc7fc82312 100644 --- a/drivers/net/wireless/strip.c +++ b/drivers/net/wireless/strip.c @@ -1352,7 +1352,7 @@ static unsigned char *strip_make_packet(unsigned char *buffer, struct in_device *in_dev; rcu_read_lock(); - in_dev = __in_dev_get(strip_info->dev); + in_dev = __in_dev_get_rcu(strip_info->dev); if (in_dev == NULL) { rcu_read_unlock(); return NULL; @@ -1508,7 +1508,7 @@ static void strip_send(struct strip *strip_info, struct sk_buff *skb) brd = addr = 0; rcu_read_lock(); - in_dev = __in_dev_get(strip_info->dev); + in_dev = __in_dev_get_rcu(strip_info->dev); if (in_dev) { if (in_dev->ifa_list) { brd = in_dev->ifa_list->ifa_broadcast; diff --git a/drivers/parisc/led.c b/drivers/parisc/led.c index e90fb72a696..286902298e3 100644 --- a/drivers/parisc/led.c +++ b/drivers/parisc/led.c @@ -37,6 +37,7 @@ #include #include #include +#include #include #include #include @@ -358,9 +359,10 @@ static __inline__ int led_get_net_activity(void) /* we are running as tasklet, so locking dev_base * for reading should be OK */ read_lock(&dev_base_lock); + rcu_read_lock(); for (dev = dev_base; dev; dev = dev->next) { struct net_device_stats *stats; - struct in_device *in_dev = __in_dev_get(dev); + struct in_device *in_dev = __in_dev_get_rcu(dev); if (!in_dev || !in_dev->ifa_list) continue; if (LOOPBACK(in_dev->ifa_list->ifa_local)) @@ -371,6 +373,7 @@ static __inline__ int led_get_net_activity(void) rx_total += stats->rx_packets; tx_total += stats->tx_packets; } + rcu_read_unlock(); read_unlock(&dev_base_lock); retval = 0; diff --git a/drivers/s390/net/qeth_main.c b/drivers/s390/net/qeth_main.c index 86582cf1e19..71de834ece1 100644 --- a/drivers/s390/net/qeth_main.c +++ b/drivers/s390/net/qeth_main.c @@ -5200,7 +5200,7 @@ qeth_free_vlan_addresses4(struct qeth_card *card, unsigned short vid) if (!card->vlangrp) return; rcu_read_lock(); - in_dev = __in_dev_get(card->vlangrp->vlan_devices[vid]); + in_dev = __in_dev_get_rcu(card->vlangrp->vlan_devices[vid]); if (!in_dev) goto out; for (ifa = in_dev->ifa_list; ifa; ifa = ifa->ifa_next) { @@ -7725,7 +7725,7 @@ qeth_arp_constructor(struct neighbour *neigh) goto out; rcu_read_lock(); - in_dev = rcu_dereference(__in_dev_get(dev)); + in_dev = __in_dev_get_rcu(dev); if (in_dev == NULL) { rcu_read_unlock(); return -EINVAL; diff --git a/include/linux/inetdevice.h b/include/linux/inetdevice.h index 7e1e15f934f..fd7af86151b 100644 --- a/include/linux/inetdevice.h +++ b/include/linux/inetdevice.h @@ -142,13 +142,21 @@ static __inline__ int bad_mask(u32 mask, u32 addr) #define endfor_ifa(in_dev) } +static inline struct in_device *__in_dev_get_rcu(const struct net_device *dev) +{ + struct in_device *in_dev = dev->ip_ptr; + if (in_dev) + in_dev = rcu_dereference(in_dev); + return in_dev; +} + static __inline__ struct in_device * in_dev_get(const struct net_device *dev) { struct in_device *in_dev; rcu_read_lock(); - in_dev = dev->ip_ptr; + in_dev = __in_dev_get_rcu(dev); if (in_dev) atomic_inc(&in_dev->refcnt); rcu_read_unlock(); @@ -156,7 +164,7 @@ in_dev_get(const struct net_device *dev) } static __inline__ struct in_device * -__in_dev_get(const struct net_device *dev) +__in_dev_get_rtnl(const struct net_device *dev) { return (struct in_device*)dev->ip_ptr; } diff --git a/net/atm/clip.c b/net/atm/clip.c index 28dab55a438..4f54c9a5e84 100644 --- a/net/atm/clip.c +++ b/net/atm/clip.c @@ -310,7 +310,7 @@ static int clip_constructor(struct neighbour *neigh) if (neigh->type != RTN_UNICAST) return -EINVAL; rcu_read_lock(); - in_dev = rcu_dereference(__in_dev_get(dev)); + in_dev = __in_dev_get_rcu(dev); if (!in_dev) { rcu_read_unlock(); return -EINVAL; diff --git a/net/core/netpoll.c b/net/core/netpoll.c index 5265dfd6992..802fe11efad 100644 --- a/net/core/netpoll.c +++ b/net/core/netpoll.c @@ -703,7 +703,7 @@ int netpoll_setup(struct netpoll *np) if (!np->local_ip) { rcu_read_lock(); - in_dev = __in_dev_get(ndev); + in_dev = __in_dev_get_rcu(ndev); if (!in_dev || !in_dev->ifa_list) { rcu_read_unlock(); diff --git a/net/core/pktgen.c b/net/core/pktgen.c index b7f2d65a614..44de070b604 100644 --- a/net/core/pktgen.c +++ b/net/core/pktgen.c @@ -1667,7 +1667,7 @@ static void pktgen_setup_inject(struct pktgen_dev *pkt_dev) struct in_device *in_dev; rcu_read_lock(); - in_dev = __in_dev_get(pkt_dev->odev); + in_dev = __in_dev_get_rcu(pkt_dev->odev); if (in_dev) { if (in_dev->ifa_list) { pkt_dev->saddr_min = in_dev->ifa_list->ifa_address; diff --git a/net/econet/af_econet.c b/net/econet/af_econet.c index 4a62093eb34..34fdac51df9 100644 --- a/net/econet/af_econet.c +++ b/net/econet/af_econet.c @@ -406,7 +406,7 @@ static int econet_sendmsg(struct kiocb *iocb, struct socket *sock, unsigned long network = 0; rcu_read_lock(); - idev = __in_dev_get(dev); + idev = __in_dev_get_rcu(dev); if (idev) { if (idev->ifa_list) network = ntohl(idev->ifa_list->ifa_address) & diff --git a/net/ipv4/arp.c b/net/ipv4/arp.c index ec0e36893b0..b425748f02d 100644 --- a/net/ipv4/arp.c +++ b/net/ipv4/arp.c @@ -241,7 +241,7 @@ static int arp_constructor(struct neighbour *neigh) neigh->type = inet_addr_type(addr); rcu_read_lock(); - in_dev = rcu_dereference(__in_dev_get(dev)); + in_dev = __in_dev_get_rcu(dev); if (in_dev == NULL) { rcu_read_unlock(); return -EINVAL; @@ -989,8 +989,8 @@ static int arp_req_set(struct arpreq *r, struct net_device * dev) ipv4_devconf.proxy_arp = 1; return 0; } - if (__in_dev_get(dev)) { - __in_dev_get(dev)->cnf.proxy_arp = 1; + if (__in_dev_get_rtnl(dev)) { + __in_dev_get_rtnl(dev)->cnf.proxy_arp = 1; return 0; } return -ENXIO; @@ -1095,8 +1095,8 @@ static int arp_req_delete(struct arpreq *r, struct net_device * dev) ipv4_devconf.proxy_arp = 0; return 0; } - if (__in_dev_get(dev)) { - __in_dev_get(dev)->cnf.proxy_arp = 0; + if (__in_dev_get_rtnl(dev)) { + __in_dev_get_rtnl(dev)->cnf.proxy_arp = 0; return 0; } return -ENXIO; diff --git a/net/ipv4/devinet.c b/net/ipv4/devinet.c index ba2895ae815..74f2207e131 100644 --- a/net/ipv4/devinet.c +++ b/net/ipv4/devinet.c @@ -351,7 +351,7 @@ static int inet_insert_ifa(struct in_ifaddr *ifa) static int inet_set_ifa(struct net_device *dev, struct in_ifaddr *ifa) { - struct in_device *in_dev = __in_dev_get(dev); + struct in_device *in_dev = __in_dev_get_rtnl(dev); ASSERT_RTNL(); @@ -449,7 +449,7 @@ static int inet_rtm_newaddr(struct sk_buff *skb, struct nlmsghdr *nlh, void *arg goto out; rc = -ENOBUFS; - if ((in_dev = __in_dev_get(dev)) == NULL) { + if ((in_dev = __in_dev_get_rtnl(dev)) == NULL) { in_dev = inetdev_init(dev); if (!in_dev) goto out; @@ -584,7 +584,7 @@ int devinet_ioctl(unsigned int cmd, void __user *arg) if (colon) *colon = ':'; - if ((in_dev = __in_dev_get(dev)) != NULL) { + if ((in_dev = __in_dev_get_rtnl(dev)) != NULL) { if (tryaddrmatch) { /* Matthias Andree */ /* compare label and address (4.4BSD style) */ @@ -748,7 +748,7 @@ rarok: static int inet_gifconf(struct net_device *dev, char __user *buf, int len) { - struct in_device *in_dev = __in_dev_get(dev); + struct in_device *in_dev = __in_dev_get_rtnl(dev); struct in_ifaddr *ifa; struct ifreq ifr; int done = 0; @@ -791,7 +791,7 @@ u32 inet_select_addr(const struct net_device *dev, u32 dst, int scope) struct in_device *in_dev; rcu_read_lock(); - in_dev = __in_dev_get(dev); + in_dev = __in_dev_get_rcu(dev); if (!in_dev) goto no_in_dev; @@ -818,7 +818,7 @@ no_in_dev: read_lock(&dev_base_lock); rcu_read_lock(); for (dev = dev_base; dev; dev = dev->next) { - if ((in_dev = __in_dev_get(dev)) == NULL) + if ((in_dev = __in_dev_get_rcu(dev)) == NULL) continue; for_primary_ifa(in_dev) { @@ -887,7 +887,7 @@ u32 inet_confirm_addr(const struct net_device *dev, u32 dst, u32 local, int scop if (dev) { rcu_read_lock(); - if ((in_dev = __in_dev_get(dev))) + if ((in_dev = __in_dev_get_rcu(dev))) addr = confirm_addr_indev(in_dev, dst, local, scope); rcu_read_unlock(); @@ -897,7 +897,7 @@ u32 inet_confirm_addr(const struct net_device *dev, u32 dst, u32 local, int scop read_lock(&dev_base_lock); rcu_read_lock(); for (dev = dev_base; dev; dev = dev->next) { - if ((in_dev = __in_dev_get(dev))) { + if ((in_dev = __in_dev_get_rcu(dev))) { addr = confirm_addr_indev(in_dev, dst, local, scope); if (addr) break; @@ -957,7 +957,7 @@ static int inetdev_event(struct notifier_block *this, unsigned long event, void *ptr) { struct net_device *dev = ptr; - struct in_device *in_dev = __in_dev_get(dev); + struct in_device *in_dev = __in_dev_get_rtnl(dev); ASSERT_RTNL(); @@ -1078,7 +1078,7 @@ static int inet_dump_ifaddr(struct sk_buff *skb, struct netlink_callback *cb) if (idx > s_idx) s_ip_idx = 0; rcu_read_lock(); - if ((in_dev = __in_dev_get(dev)) == NULL) { + if ((in_dev = __in_dev_get_rcu(dev)) == NULL) { rcu_read_unlock(); continue; } @@ -1149,7 +1149,7 @@ void inet_forward_change(void) for (dev = dev_base; dev; dev = dev->next) { struct in_device *in_dev; rcu_read_lock(); - in_dev = __in_dev_get(dev); + in_dev = __in_dev_get_rcu(dev); if (in_dev) in_dev->cnf.forwarding = on; rcu_read_unlock(); diff --git a/net/ipv4/fib_frontend.c b/net/ipv4/fib_frontend.c index 4e1379f7126..e61bc7177eb 100644 --- a/net/ipv4/fib_frontend.c +++ b/net/ipv4/fib_frontend.c @@ -173,7 +173,7 @@ int fib_validate_source(u32 src, u32 dst, u8 tos, int oif, no_addr = rpf = 0; rcu_read_lock(); - in_dev = __in_dev_get(dev); + in_dev = __in_dev_get_rcu(dev); if (in_dev) { no_addr = in_dev->ifa_list == NULL; rpf = IN_DEV_RPFILTER(in_dev); @@ -607,7 +607,7 @@ static int fib_inetaddr_event(struct notifier_block *this, unsigned long event, static int fib_netdev_event(struct notifier_block *this, unsigned long event, void *ptr) { struct net_device *dev = ptr; - struct in_device *in_dev = __in_dev_get(dev); + struct in_device *in_dev = __in_dev_get_rtnl(dev); if (event == NETDEV_UNREGISTER) { fib_disable_ip(dev, 2); diff --git a/net/ipv4/fib_semantics.c b/net/ipv4/fib_semantics.c index d41219e8037..186f20c4a45 100644 --- a/net/ipv4/fib_semantics.c +++ b/net/ipv4/fib_semantics.c @@ -1087,7 +1087,7 @@ fib_convert_rtentry(int cmd, struct nlmsghdr *nl, struct rtmsg *rtm, rta->rta_oif = &dev->ifindex; if (colon) { struct in_ifaddr *ifa; - struct in_device *in_dev = __in_dev_get(dev); + struct in_device *in_dev = __in_dev_get_rtnl(dev); if (!in_dev) return -ENODEV; *colon = ':'; @@ -1268,7 +1268,7 @@ int fib_sync_up(struct net_device *dev) } if (nh->nh_dev == NULL || !(nh->nh_dev->flags&IFF_UP)) continue; - if (nh->nh_dev != dev || __in_dev_get(dev) == NULL) + if (nh->nh_dev != dev || !__in_dev_get_rtnl(dev)) continue; alive++; spin_lock_bh(&fib_multipath_lock); diff --git a/net/ipv4/igmp.c b/net/ipv4/igmp.c index 70c44e4c3ce..8b6d3939e1e 100644 --- a/net/ipv4/igmp.c +++ b/net/ipv4/igmp.c @@ -1323,7 +1323,7 @@ static struct in_device * ip_mc_find_dev(struct ip_mreqn *imr) } if (dev) { imr->imr_ifindex = dev->ifindex; - idev = __in_dev_get(dev); + idev = __in_dev_get_rtnl(dev); } return idev; } diff --git a/net/ipv4/ip_gre.c b/net/ipv4/ip_gre.c index f0d5740d7e2..896ce3f8f53 100644 --- a/net/ipv4/ip_gre.c +++ b/net/ipv4/ip_gre.c @@ -1104,10 +1104,10 @@ static int ipgre_open(struct net_device *dev) return -EADDRNOTAVAIL; dev = rt->u.dst.dev; ip_rt_put(rt); - if (__in_dev_get(dev) == NULL) + if (__in_dev_get_rtnl(dev) == NULL) return -EADDRNOTAVAIL; t->mlink = dev->ifindex; - ip_mc_inc_group(__in_dev_get(dev), t->parms.iph.daddr); + ip_mc_inc_group(__in_dev_get_rtnl(dev), t->parms.iph.daddr); } return 0; } diff --git a/net/ipv4/ipmr.c b/net/ipv4/ipmr.c index 9dbf5909f3a..302b7eb507c 100644 --- a/net/ipv4/ipmr.c +++ b/net/ipv4/ipmr.c @@ -149,7 +149,7 @@ struct net_device *ipmr_new_tunnel(struct vifctl *v) if (err == 0 && (dev = __dev_get_by_name(p.name)) != NULL) { dev->flags |= IFF_MULTICAST; - in_dev = __in_dev_get(dev); + in_dev = __in_dev_get_rtnl(dev); if (in_dev == NULL && (in_dev = inetdev_init(dev)) == NULL) goto failure; in_dev->cnf.rp_filter = 0; @@ -278,7 +278,7 @@ static int vif_delete(int vifi) dev_set_allmulti(dev, -1); - if ((in_dev = __in_dev_get(dev)) != NULL) { + if ((in_dev = __in_dev_get_rtnl(dev)) != NULL) { in_dev->cnf.mc_forwarding--; ip_rt_multicast_event(in_dev); } @@ -421,7 +421,7 @@ static int vif_add(struct vifctl *vifc, int mrtsock) return -EINVAL; } - if ((in_dev = __in_dev_get(dev)) == NULL) + if ((in_dev = __in_dev_get_rtnl(dev)) == NULL) return -EADDRNOTAVAIL; in_dev->cnf.mc_forwarding++; dev_set_allmulti(dev, +1); diff --git a/net/ipv4/netfilter/ip_conntrack_netbios_ns.c b/net/ipv4/netfilter/ip_conntrack_netbios_ns.c index 577bac22dcc..186646eb249 100644 --- a/net/ipv4/netfilter/ip_conntrack_netbios_ns.c +++ b/net/ipv4/netfilter/ip_conntrack_netbios_ns.c @@ -58,7 +58,7 @@ static int help(struct sk_buff **pskb, goto out; rcu_read_lock(); - in_dev = __in_dev_get(rt->u.dst.dev); + in_dev = __in_dev_get_rcu(rt->u.dst.dev); if (in_dev != NULL) { for_primary_ifa(in_dev) { if (ifa->ifa_broadcast == iph->daddr) { diff --git a/net/ipv4/netfilter/ipt_REDIRECT.c b/net/ipv4/netfilter/ipt_REDIRECT.c index 715cb613405..5245bfd33d5 100644 --- a/net/ipv4/netfilter/ipt_REDIRECT.c +++ b/net/ipv4/netfilter/ipt_REDIRECT.c @@ -93,7 +93,7 @@ redirect_target(struct sk_buff **pskb, newdst = 0; rcu_read_lock(); - indev = __in_dev_get((*pskb)->dev); + indev = __in_dev_get_rcu((*pskb)->dev); if (indev && (ifa = indev->ifa_list)) newdst = ifa->ifa_local; rcu_read_unlock(); diff --git a/net/ipv4/route.c b/net/ipv4/route.c index 8549f26e249..381dd6a6aeb 100644 --- a/net/ipv4/route.c +++ b/net/ipv4/route.c @@ -2128,7 +2128,7 @@ int ip_route_input(struct sk_buff *skb, u32 daddr, u32 saddr, struct in_device *in_dev; rcu_read_lock(); - if ((in_dev = __in_dev_get(dev)) != NULL) { + if ((in_dev = __in_dev_get_rcu(dev)) != NULL) { int our = ip_check_mc(in_dev, daddr, saddr, skb->nh.iph->protocol); if (our @@ -2443,7 +2443,9 @@ static int ip_route_output_slow(struct rtable **rp, const struct flowi *oldflp) err = -ENODEV; if (dev_out == NULL) goto out; - if (__in_dev_get(dev_out) == NULL) { + + /* RACE: Check return value of inet_select_addr instead. */ + if (__in_dev_get_rtnl(dev_out) == NULL) { dev_put(dev_out); goto out; /* Wrong error code */ } diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c index 4e509e52fbc..a970b4727ce 100644 --- a/net/ipv6/addrconf.c +++ b/net/ipv6/addrconf.c @@ -1806,7 +1806,7 @@ static void sit_add_v4_addrs(struct inet6_dev *idev) } for (dev = dev_base; dev != NULL; dev = dev->next) { - struct in_device * in_dev = __in_dev_get(dev); + struct in_device * in_dev = __in_dev_get_rtnl(dev); if (in_dev && (dev->flags & IFF_UP)) { struct in_ifaddr * ifa; diff --git a/net/irda/irlan/irlan_eth.c b/net/irda/irlan/irlan_eth.c index 071cd2cefd8..953e255d2bc 100644 --- a/net/irda/irlan/irlan_eth.c +++ b/net/irda/irlan/irlan_eth.c @@ -310,7 +310,7 @@ void irlan_eth_send_gratuitous_arp(struct net_device *dev) #ifdef CONFIG_INET IRDA_DEBUG(4, "IrLAN: Sending gratuitous ARP\n"); rcu_read_lock(); - in_dev = __in_dev_get(dev); + in_dev = __in_dev_get_rcu(dev); if (in_dev == NULL) goto out; if (in_dev->ifa_list) diff --git a/net/sctp/protocol.c b/net/sctp/protocol.c index e7025be7769..f01d1c9002a 100644 --- a/net/sctp/protocol.c +++ b/net/sctp/protocol.c @@ -147,7 +147,7 @@ static void sctp_v4_copy_addrlist(struct list_head *addrlist, struct sctp_sockaddr_entry *addr; rcu_read_lock(); - if ((in_dev = __in_dev_get(dev)) == NULL) { + if ((in_dev = __in_dev_get_rcu(dev)) == NULL) { rcu_read_unlock(); return; } -- cgit v1.2.3 From 3e56a40bb36f1f73b4eac2ffe267c5357811e321 Mon Sep 17 00:00:00 2001 From: Herbert Xu Date: Mon, 3 Oct 2005 14:36:32 -0700 Subject: [IPV4]: Get rid of bogus __in_put_dev in pktgen This patch gets rid of a bogus __in_dev_put() in pktgen.c. This was spotted by Suzanne Wood. Signed-off-by: Herbert Xu Signed-off-by: David S. Miller --- net/core/pktgen.c | 1 - 1 file changed, 1 deletion(-) diff --git a/net/core/pktgen.c b/net/core/pktgen.c index 44de070b604..5f043d34669 100644 --- a/net/core/pktgen.c +++ b/net/core/pktgen.c @@ -1673,7 +1673,6 @@ static void pktgen_setup_inject(struct pktgen_dev *pkt_dev) pkt_dev->saddr_min = in_dev->ifa_list->ifa_address; pkt_dev->saddr_max = pkt_dev->saddr_min; } - __in_dev_put(in_dev); } rcu_read_unlock(); } -- cgit v1.2.3 From 7ce312467edc270fcbd8a699efabb37ce1802b98 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Mon, 3 Oct 2005 16:07:30 -0700 Subject: [IPV4]: Update icmp sysctl docs and disable broadcast ECHO/TIMESTAMP by default It's not a good idea to be smurf'able by default. The few people who need this can turn it on. Signed-off-by: David S. Miller --- Documentation/networking/ip-sysctl.txt | 10 +++++++--- net/ipv4/icmp.c | 2 +- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/Documentation/networking/ip-sysctl.txt b/Documentation/networking/ip-sysctl.txt index ab65714d95f..b433c8a27e2 100644 --- a/Documentation/networking/ip-sysctl.txt +++ b/Documentation/networking/ip-sysctl.txt @@ -355,10 +355,14 @@ ip_dynaddr - BOOLEAN Default: 0 icmp_echo_ignore_all - BOOLEAN + If set non-zero, then the kernel will ignore all ICMP ECHO + requests sent to it. + Default: 0 + icmp_echo_ignore_broadcasts - BOOLEAN - If either is set to true, then the kernel will ignore either all - ICMP ECHO requests sent to it or just those to broadcast/multicast - addresses, respectively. + If set non-zero, then the kernel will ignore all ICMP ECHO and + TIMESTAMP requests sent to it via broadcast/multicast. + Default: 1 icmp_ratelimit - INTEGER Limit the maximal rates for sending ICMP packets whose type matches diff --git a/net/ipv4/icmp.c b/net/ipv4/icmp.c index 24eb56ae1b5..90dca711ac9 100644 --- a/net/ipv4/icmp.c +++ b/net/ipv4/icmp.c @@ -188,7 +188,7 @@ struct icmp_err icmp_err_convert[] = { /* Control parameters for ECHO replies. */ int sysctl_icmp_echo_ignore_all; -int sysctl_icmp_echo_ignore_broadcasts; +int sysctl_icmp_echo_ignore_broadcasts = 1; /* Control parameter - ignore bogus broadcast responses? */ int sysctl_icmp_ignore_bogus_error_responses; -- cgit v1.2.3 From ed39f731ab2e77e58122232f6e27333331d7793d Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Mon, 3 Oct 2005 16:25:23 -0700 Subject: [TG3]: Update driver version and release date. Signed-off-by: David S. Miller --- drivers/net/tg3.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/tg3.c b/drivers/net/tg3.c index fee0e6e5ff1..1802c3b4879 100644 --- a/drivers/net/tg3.c +++ b/drivers/net/tg3.c @@ -67,8 +67,8 @@ #define DRV_MODULE_NAME "tg3" #define PFX DRV_MODULE_NAME ": " -#define DRV_MODULE_VERSION "3.41" -#define DRV_MODULE_RELDATE "September 27, 2005" +#define DRV_MODULE_VERSION "3.42" +#define DRV_MODULE_RELDATE "Oct 3, 2005" #define TG3_DEF_MAC_MODE 0 #define TG3_DEF_RX_MODE 0 -- cgit v1.2.3 From 3115624eda34d0f4e673fc6bcea36b7ad701ee33 Mon Sep 17 00:00:00 2001 From: Adrian Bunk Date: Mon, 3 Oct 2005 17:37:02 -0700 Subject: [SPARC]: "extern inline" doesn't make much sense. Signed-off-by: Adrian Bunk Signed-off-by: David S. Miller --- arch/sparc/kernel/time.c | 2 +- arch/sparc/mm/srmmu.c | 2 +- include/asm-sparc/btfixup.h | 12 ++++++------ include/asm-sparc/cache.h | 18 +++++++++--------- include/asm-sparc/cypress.h | 8 ++++---- include/asm-sparc/delay.h | 2 +- include/asm-sparc/dma.h | 2 +- include/asm-sparc/iommu.h | 4 ++-- include/asm-sparc/kdebug.h | 2 +- include/asm-sparc/mbus.h | 4 ++-- include/asm-sparc/msi.h | 2 +- include/asm-sparc/mxcc.h | 8 ++++---- include/asm-sparc/obio.h | 30 +++++++++++++++--------------- include/asm-sparc/pci.h | 6 +++--- include/asm-sparc/pgtable.h | 28 ++++++++++++++-------------- include/asm-sparc/pgtsrmmu.h | 30 +++++++++++++++--------------- include/asm-sparc/processor.h | 2 +- include/asm-sparc/psr.h | 6 +++--- include/asm-sparc/sbi.h | 10 +++++----- include/asm-sparc/sbus.h | 6 +++--- include/asm-sparc/smp.h | 26 +++++++++++++------------- include/asm-sparc/smpprim.h | 8 ++++---- include/asm-sparc/spinlock.h | 10 +++++----- include/asm-sparc/system.h | 2 +- include/asm-sparc/traps.h | 2 +- 25 files changed, 116 insertions(+), 116 deletions(-) diff --git a/arch/sparc/kernel/time.c b/arch/sparc/kernel/time.c index bc015e98034..279a62627c1 100644 --- a/arch/sparc/kernel/time.c +++ b/arch/sparc/kernel/time.c @@ -457,7 +457,7 @@ void __init time_init(void) sbus_time_init(); } -extern __inline__ unsigned long do_gettimeoffset(void) +static inline unsigned long do_gettimeoffset(void) { return (*master_l10_counter >> 10) & 0x1fffff; } diff --git a/arch/sparc/mm/srmmu.c b/arch/sparc/mm/srmmu.c index c89a803cbc2..c664b962987 100644 --- a/arch/sparc/mm/srmmu.c +++ b/arch/sparc/mm/srmmu.c @@ -260,7 +260,7 @@ static inline pte_t srmmu_pte_modify(pte_t pte, pgprot_t newprot) { return __pte((pte_val(pte) & SRMMU_CHG_MASK) | pgprot_val(newprot)); } /* to find an entry in a top-level page table... */ -extern inline pgd_t *srmmu_pgd_offset(struct mm_struct * mm, unsigned long address) +static inline pgd_t *srmmu_pgd_offset(struct mm_struct * mm, unsigned long address) { return mm->pgd + (address >> SRMMU_PGDIR_SHIFT); } /* Find an entry in the second-level page table.. */ diff --git a/include/asm-sparc/btfixup.h b/include/asm-sparc/btfixup.h index b84c96c8958..6b29503256f 100644 --- a/include/asm-sparc/btfixup.h +++ b/include/asm-sparc/btfixup.h @@ -51,7 +51,7 @@ extern unsigned int ___illegal_use_of_BTFIXUP_INT_in_module(void); #define BTFIXUPDEF_SIMM13(__name) \ extern unsigned int ___sf_##__name(void) __attribute_const__; \ extern unsigned ___ss_##__name[2]; \ - extern __inline__ unsigned int ___sf_##__name(void) { \ + static inline unsigned int ___sf_##__name(void) { \ unsigned int ret; \ __asm__ ("or %%g0, ___s_" #__name ", %0" : "=r"(ret)); \ return ret; \ @@ -59,7 +59,7 @@ extern unsigned int ___illegal_use_of_BTFIXUP_INT_in_module(void); #define BTFIXUPDEF_SIMM13_INIT(__name,__val) \ extern unsigned int ___sf_##__name(void) __attribute_const__; \ extern unsigned ___ss_##__name[2]; \ - extern __inline__ unsigned int ___sf_##__name(void) { \ + static inline unsigned int ___sf_##__name(void) { \ unsigned int ret; \ __asm__ ("or %%g0, ___s_" #__name "__btset_" #__val ", %0" : "=r"(ret));\ return ret; \ @@ -73,7 +73,7 @@ extern unsigned int ___illegal_use_of_BTFIXUP_INT_in_module(void); #define BTFIXUPDEF_HALF(__name) \ extern unsigned int ___af_##__name(void) __attribute_const__; \ extern unsigned ___as_##__name[2]; \ - extern __inline__ unsigned int ___af_##__name(void) { \ + static inline unsigned int ___af_##__name(void) { \ unsigned int ret; \ __asm__ ("or %%g0, ___a_" #__name ", %0" : "=r"(ret)); \ return ret; \ @@ -81,7 +81,7 @@ extern unsigned int ___illegal_use_of_BTFIXUP_INT_in_module(void); #define BTFIXUPDEF_HALF_INIT(__name,__val) \ extern unsigned int ___af_##__name(void) __attribute_const__; \ extern unsigned ___as_##__name[2]; \ - extern __inline__ unsigned int ___af_##__name(void) { \ + static inline unsigned int ___af_##__name(void) { \ unsigned int ret; \ __asm__ ("or %%g0, ___a_" #__name "__btset_" #__val ", %0" : "=r"(ret));\ return ret; \ @@ -92,7 +92,7 @@ extern unsigned int ___illegal_use_of_BTFIXUP_INT_in_module(void); #define BTFIXUPDEF_SETHI(__name) \ extern unsigned int ___hf_##__name(void) __attribute_const__; \ extern unsigned ___hs_##__name[2]; \ - extern __inline__ unsigned int ___hf_##__name(void) { \ + static inline unsigned int ___hf_##__name(void) { \ unsigned int ret; \ __asm__ ("sethi %%hi(___h_" #__name "), %0" : "=r"(ret)); \ return ret; \ @@ -100,7 +100,7 @@ extern unsigned int ___illegal_use_of_BTFIXUP_INT_in_module(void); #define BTFIXUPDEF_SETHI_INIT(__name,__val) \ extern unsigned int ___hf_##__name(void) __attribute_const__; \ extern unsigned ___hs_##__name[2]; \ - extern __inline__ unsigned int ___hf_##__name(void) { \ + static inline unsigned int ___hf_##__name(void) { \ unsigned int ret; \ __asm__ ("sethi %%hi(___h_" #__name "__btset_" #__val "), %0" : \ "=r"(ret)); \ diff --git a/include/asm-sparc/cache.h b/include/asm-sparc/cache.h index e6316fd7e1a..a10522cb21b 100644 --- a/include/asm-sparc/cache.h +++ b/include/asm-sparc/cache.h @@ -27,7 +27,7 @@ */ /* First, cache-tag access. */ -extern __inline__ unsigned int get_icache_tag(int setnum, int tagnum) +static inline unsigned int get_icache_tag(int setnum, int tagnum) { unsigned int vaddr, retval; @@ -38,7 +38,7 @@ extern __inline__ unsigned int get_icache_tag(int setnum, int tagnum) return retval; } -extern __inline__ void put_icache_tag(int setnum, int tagnum, unsigned int entry) +static inline void put_icache_tag(int setnum, int tagnum, unsigned int entry) { unsigned int vaddr; @@ -51,7 +51,7 @@ extern __inline__ void put_icache_tag(int setnum, int tagnum, unsigned int entry /* Second cache-data access. The data is returned two-32bit quantities * at a time. */ -extern __inline__ void get_icache_data(int setnum, int tagnum, int subblock, +static inline void get_icache_data(int setnum, int tagnum, int subblock, unsigned int *data) { unsigned int value1, value2, vaddr; @@ -67,7 +67,7 @@ extern __inline__ void get_icache_data(int setnum, int tagnum, int subblock, data[0] = value1; data[1] = value2; } -extern __inline__ void put_icache_data(int setnum, int tagnum, int subblock, +static inline void put_icache_data(int setnum, int tagnum, int subblock, unsigned int *data) { unsigned int value1, value2, vaddr; @@ -92,35 +92,35 @@ extern __inline__ void put_icache_data(int setnum, int tagnum, int subblock, */ /* Flushes which clear out both the on-chip and external caches */ -extern __inline__ void flush_ei_page(unsigned int addr) +static inline void flush_ei_page(unsigned int addr) { __asm__ __volatile__("sta %%g0, [%0] %1\n\t" : : "r" (addr), "i" (ASI_M_FLUSH_PAGE) : "memory"); } -extern __inline__ void flush_ei_seg(unsigned int addr) +static inline void flush_ei_seg(unsigned int addr) { __asm__ __volatile__("sta %%g0, [%0] %1\n\t" : : "r" (addr), "i" (ASI_M_FLUSH_SEG) : "memory"); } -extern __inline__ void flush_ei_region(unsigned int addr) +static inline void flush_ei_region(unsigned int addr) { __asm__ __volatile__("sta %%g0, [%0] %1\n\t" : : "r" (addr), "i" (ASI_M_FLUSH_REGION) : "memory"); } -extern __inline__ void flush_ei_ctx(unsigned int addr) +static inline void flush_ei_ctx(unsigned int addr) { __asm__ __volatile__("sta %%g0, [%0] %1\n\t" : : "r" (addr), "i" (ASI_M_FLUSH_CTX) : "memory"); } -extern __inline__ void flush_ei_user(unsigned int addr) +static inline void flush_ei_user(unsigned int addr) { __asm__ __volatile__("sta %%g0, [%0] %1\n\t" : : "r" (addr), "i" (ASI_M_FLUSH_USER) : diff --git a/include/asm-sparc/cypress.h b/include/asm-sparc/cypress.h index fc92fc839c3..99599533efb 100644 --- a/include/asm-sparc/cypress.h +++ b/include/asm-sparc/cypress.h @@ -48,25 +48,25 @@ #define CYPRESS_NFAULT 0x00000002 #define CYPRESS_MENABLE 0x00000001 -extern __inline__ void cypress_flush_page(unsigned long page) +static inline void cypress_flush_page(unsigned long page) { __asm__ __volatile__("sta %%g0, [%0] %1\n\t" : : "r" (page), "i" (ASI_M_FLUSH_PAGE)); } -extern __inline__ void cypress_flush_segment(unsigned long addr) +static inline void cypress_flush_segment(unsigned long addr) { __asm__ __volatile__("sta %%g0, [%0] %1\n\t" : : "r" (addr), "i" (ASI_M_FLUSH_SEG)); } -extern __inline__ void cypress_flush_region(unsigned long addr) +static inline void cypress_flush_region(unsigned long addr) { __asm__ __volatile__("sta %%g0, [%0] %1\n\t" : : "r" (addr), "i" (ASI_M_FLUSH_REGION)); } -extern __inline__ void cypress_flush_context(void) +static inline void cypress_flush_context(void) { __asm__ __volatile__("sta %%g0, [%%g0] %0\n\t" : : "i" (ASI_M_FLUSH_CTX)); diff --git a/include/asm-sparc/delay.h b/include/asm-sparc/delay.h index 6edf2cbb246..7ec8e9f7ad4 100644 --- a/include/asm-sparc/delay.h +++ b/include/asm-sparc/delay.h @@ -10,7 +10,7 @@ #include #include -extern __inline__ void __delay(unsigned long loops) +static inline void __delay(unsigned long loops) { __asm__ __volatile__("cmp %0, 0\n\t" "1: bne 1b\n\t" diff --git a/include/asm-sparc/dma.h b/include/asm-sparc/dma.h index 07e6368a252..8ec206aa5f2 100644 --- a/include/asm-sparc/dma.h +++ b/include/asm-sparc/dma.h @@ -198,7 +198,7 @@ extern void dvma_init(struct sbus_bus *); /* Pause until counter runs out or BIT isn't set in the DMA condition * register. */ -extern __inline__ void sparc_dma_pause(struct sparc_dma_registers *regs, +static inline void sparc_dma_pause(struct sparc_dma_registers *regs, unsigned long bit) { int ctr = 50000; /* Let's find some bugs ;) */ diff --git a/include/asm-sparc/iommu.h b/include/asm-sparc/iommu.h index 8171362d56b..70c589c05a1 100644 --- a/include/asm-sparc/iommu.h +++ b/include/asm-sparc/iommu.h @@ -108,12 +108,12 @@ struct iommu_struct { struct bit_map usemap; }; -extern __inline__ void iommu_invalidate(struct iommu_regs *regs) +static inline void iommu_invalidate(struct iommu_regs *regs) { regs->tlbflush = 0; } -extern __inline__ void iommu_invalidate_page(struct iommu_regs *regs, unsigned long ba) +static inline void iommu_invalidate_page(struct iommu_regs *regs, unsigned long ba) { regs->pageflush = (ba & PAGE_MASK); } diff --git a/include/asm-sparc/kdebug.h b/include/asm-sparc/kdebug.h index 3ea4916635e..fba92485fdb 100644 --- a/include/asm-sparc/kdebug.h +++ b/include/asm-sparc/kdebug.h @@ -46,7 +46,7 @@ struct kernel_debug { extern struct kernel_debug *linux_dbvec; /* Use this macro in C-code to enter the debugger. */ -extern __inline__ void sp_enter_debugger(void) +static inline void sp_enter_debugger(void) { __asm__ __volatile__("jmpl %0, %%o7\n\t" "nop\n\t" : : diff --git a/include/asm-sparc/mbus.h b/include/asm-sparc/mbus.h index 5f274901534..ecacdf4075d 100644 --- a/include/asm-sparc/mbus.h +++ b/include/asm-sparc/mbus.h @@ -83,7 +83,7 @@ extern unsigned int hwbug_bitmask; */ #define TBR_ID_SHIFT 20 -extern __inline__ int get_cpuid(void) +static inline int get_cpuid(void) { register int retval; __asm__ __volatile__("rd %%tbr, %0\n\t" @@ -93,7 +93,7 @@ extern __inline__ int get_cpuid(void) return (retval & 3); } -extern __inline__ int get_modid(void) +static inline int get_modid(void) { return (get_cpuid() | 0x8); } diff --git a/include/asm-sparc/msi.h b/include/asm-sparc/msi.h index b69543dd3b4..ff72cbd946a 100644 --- a/include/asm-sparc/msi.h +++ b/include/asm-sparc/msi.h @@ -19,7 +19,7 @@ #define MSI_ASYNC_MODE 0x80000000 /* Operate the MSI asynchronously */ -extern __inline__ void msi_set_sync(void) +static inline void msi_set_sync(void) { __asm__ __volatile__ ("lda [%0] %1, %%g3\n\t" "andn %%g3, %2, %%g3\n\t" diff --git a/include/asm-sparc/mxcc.h b/include/asm-sparc/mxcc.h index 60ef9d6fe7b..128fe970813 100644 --- a/include/asm-sparc/mxcc.h +++ b/include/asm-sparc/mxcc.h @@ -85,7 +85,7 @@ #ifndef __ASSEMBLY__ -extern __inline__ void mxcc_set_stream_src(unsigned long *paddr) +static inline void mxcc_set_stream_src(unsigned long *paddr) { unsigned long data0 = paddr[0]; unsigned long data1 = paddr[1]; @@ -98,7 +98,7 @@ extern __inline__ void mxcc_set_stream_src(unsigned long *paddr) "i" (ASI_M_MXCC) : "g2", "g3"); } -extern __inline__ void mxcc_set_stream_dst(unsigned long *paddr) +static inline void mxcc_set_stream_dst(unsigned long *paddr) { unsigned long data0 = paddr[0]; unsigned long data1 = paddr[1]; @@ -111,7 +111,7 @@ extern __inline__ void mxcc_set_stream_dst(unsigned long *paddr) "i" (ASI_M_MXCC) : "g2", "g3"); } -extern __inline__ unsigned long mxcc_get_creg(void) +static inline unsigned long mxcc_get_creg(void) { unsigned long mxcc_control; @@ -125,7 +125,7 @@ extern __inline__ unsigned long mxcc_get_creg(void) return mxcc_control; } -extern __inline__ void mxcc_set_creg(unsigned long mxcc_control) +static inline void mxcc_set_creg(unsigned long mxcc_control) { __asm__ __volatile__("sta %0, [%1] %2\n\t" : : "r" (mxcc_control), "r" (MXCC_CREG), diff --git a/include/asm-sparc/obio.h b/include/asm-sparc/obio.h index 62e1d77965f..47854a2a12c 100644 --- a/include/asm-sparc/obio.h +++ b/include/asm-sparc/obio.h @@ -98,7 +98,7 @@ #ifndef __ASSEMBLY__ -extern __inline__ int bw_get_intr_mask(int sbus_level) +static inline int bw_get_intr_mask(int sbus_level) { int mask; @@ -109,7 +109,7 @@ extern __inline__ int bw_get_intr_mask(int sbus_level) return mask; } -extern __inline__ void bw_clear_intr_mask(int sbus_level, int mask) +static inline void bw_clear_intr_mask(int sbus_level, int mask) { __asm__ __volatile__ ("stha %0, [%1] %2" : : "r" (mask), @@ -117,7 +117,7 @@ extern __inline__ void bw_clear_intr_mask(int sbus_level, int mask) "i" (ASI_M_CTL)); } -extern __inline__ unsigned bw_get_prof_limit(int cpu) +static inline unsigned bw_get_prof_limit(int cpu) { unsigned limit; @@ -128,7 +128,7 @@ extern __inline__ unsigned bw_get_prof_limit(int cpu) return limit; } -extern __inline__ void bw_set_prof_limit(int cpu, unsigned limit) +static inline void bw_set_prof_limit(int cpu, unsigned limit) { __asm__ __volatile__ ("sta %0, [%1] %2" : : "r" (limit), @@ -136,7 +136,7 @@ extern __inline__ void bw_set_prof_limit(int cpu, unsigned limit) "i" (ASI_M_CTL)); } -extern __inline__ unsigned bw_get_ctrl(int cpu) +static inline unsigned bw_get_ctrl(int cpu) { unsigned ctrl; @@ -147,7 +147,7 @@ extern __inline__ unsigned bw_get_ctrl(int cpu) return ctrl; } -extern __inline__ void bw_set_ctrl(int cpu, unsigned ctrl) +static inline void bw_set_ctrl(int cpu, unsigned ctrl) { __asm__ __volatile__ ("sta %0, [%1] %2" : : "r" (ctrl), @@ -157,7 +157,7 @@ extern __inline__ void bw_set_ctrl(int cpu, unsigned ctrl) extern unsigned char cpu_leds[32]; -extern __inline__ void show_leds(int cpuid) +static inline void show_leds(int cpuid) { cpuid &= 0x1e; __asm__ __volatile__ ("stba %0, [%1] %2" : : @@ -166,7 +166,7 @@ extern __inline__ void show_leds(int cpuid) "i" (ASI_M_CTL)); } -extern __inline__ unsigned cc_get_ipen(void) +static inline unsigned cc_get_ipen(void) { unsigned pending; @@ -177,7 +177,7 @@ extern __inline__ unsigned cc_get_ipen(void) return pending; } -extern __inline__ void cc_set_iclr(unsigned clear) +static inline void cc_set_iclr(unsigned clear) { __asm__ __volatile__ ("stha %0, [%1] %2" : : "r" (clear), @@ -185,7 +185,7 @@ extern __inline__ void cc_set_iclr(unsigned clear) "i" (ASI_M_MXCC)); } -extern __inline__ unsigned cc_get_imsk(void) +static inline unsigned cc_get_imsk(void) { unsigned mask; @@ -196,7 +196,7 @@ extern __inline__ unsigned cc_get_imsk(void) return mask; } -extern __inline__ void cc_set_imsk(unsigned mask) +static inline void cc_set_imsk(unsigned mask) { __asm__ __volatile__ ("stha %0, [%1] %2" : : "r" (mask), @@ -204,7 +204,7 @@ extern __inline__ void cc_set_imsk(unsigned mask) "i" (ASI_M_MXCC)); } -extern __inline__ unsigned cc_get_imsk_other(int cpuid) +static inline unsigned cc_get_imsk_other(int cpuid) { unsigned mask; @@ -215,7 +215,7 @@ extern __inline__ unsigned cc_get_imsk_other(int cpuid) return mask; } -extern __inline__ void cc_set_imsk_other(int cpuid, unsigned mask) +static inline void cc_set_imsk_other(int cpuid, unsigned mask) { __asm__ __volatile__ ("stha %0, [%1] %2" : : "r" (mask), @@ -223,7 +223,7 @@ extern __inline__ void cc_set_imsk_other(int cpuid, unsigned mask) "i" (ASI_M_CTL)); } -extern __inline__ void cc_set_igen(unsigned gen) +static inline void cc_set_igen(unsigned gen) { __asm__ __volatile__ ("sta %0, [%1] %2" : : "r" (gen), @@ -239,7 +239,7 @@ extern __inline__ void cc_set_igen(unsigned gen) #define IGEN_MESSAGE(bcast, devid, sid, levels) \ (((bcast) << 31) | ((devid) << 23) | ((sid) << 15) | (levels)) -extern __inline__ void sun4d_send_ipi(int cpu, int level) +static inline void sun4d_send_ipi(int cpu, int level) { cc_set_igen(IGEN_MESSAGE(0, cpu << 3, 6 + ((level >> 1) & 7), 1 << (level - 1))); } diff --git a/include/asm-sparc/pci.h b/include/asm-sparc/pci.h index 97052baf90c..38644742f01 100644 --- a/include/asm-sparc/pci.h +++ b/include/asm-sparc/pci.h @@ -15,12 +15,12 @@ #define PCI_IRQ_NONE 0xffffffff -extern inline void pcibios_set_master(struct pci_dev *dev) +static inline void pcibios_set_master(struct pci_dev *dev) { /* No special bus mastering setup handling */ } -extern inline void pcibios_penalize_isa_irq(int irq, int active) +static inline void pcibios_penalize_isa_irq(int irq, int active) { /* We don't do dynamic PCI IRQ allocation */ } @@ -137,7 +137,7 @@ extern void pci_dma_sync_sg_for_device(struct pci_dev *hwdev, struct scatterlist * only drive the low 24-bits during PCI bus mastering, then * you would pass 0x00ffffff as the mask to this function. */ -extern inline int pci_dma_supported(struct pci_dev *hwdev, u64 mask) +static inline int pci_dma_supported(struct pci_dev *hwdev, u64 mask) { return 1; } diff --git a/include/asm-sparc/pgtable.h b/include/asm-sparc/pgtable.h index 8395ad2f1c0..ae883f295f1 100644 --- a/include/asm-sparc/pgtable.h +++ b/include/asm-sparc/pgtable.h @@ -154,7 +154,7 @@ BTFIXUPDEF_CALL_CONST(int, pte_present, pte_t) BTFIXUPDEF_CALL(void, pte_clear, pte_t *) BTFIXUPDEF_CALL(int, pte_read, pte_t) -extern __inline__ int pte_none(pte_t pte) +static inline int pte_none(pte_t pte) { return !(pte_val(pte) & ~BTFIXUP_SETHI(none_mask)); } @@ -167,7 +167,7 @@ BTFIXUPDEF_CALL_CONST(int, pmd_bad, pmd_t) BTFIXUPDEF_CALL_CONST(int, pmd_present, pmd_t) BTFIXUPDEF_CALL(void, pmd_clear, pmd_t *) -extern __inline__ int pmd_none(pmd_t pmd) +static inline int pmd_none(pmd_t pmd) { return !(pmd_val(pmd) & ~BTFIXUP_SETHI(none_mask)); } @@ -195,19 +195,19 @@ BTFIXUPDEF_HALF(pte_dirtyi) BTFIXUPDEF_HALF(pte_youngi) extern int pte_write(pte_t pte) __attribute_const__; -extern __inline__ int pte_write(pte_t pte) +static inline int pte_write(pte_t pte) { return pte_val(pte) & BTFIXUP_HALF(pte_writei); } extern int pte_dirty(pte_t pte) __attribute_const__; -extern __inline__ int pte_dirty(pte_t pte) +static inline int pte_dirty(pte_t pte) { return pte_val(pte) & BTFIXUP_HALF(pte_dirtyi); } extern int pte_young(pte_t pte) __attribute_const__; -extern __inline__ int pte_young(pte_t pte) +static inline int pte_young(pte_t pte) { return pte_val(pte) & BTFIXUP_HALF(pte_youngi); } @@ -218,7 +218,7 @@ extern __inline__ int pte_young(pte_t pte) BTFIXUPDEF_HALF(pte_filei) extern int pte_file(pte_t pte) __attribute_const__; -extern __inline__ int pte_file(pte_t pte) +static inline int pte_file(pte_t pte) { return pte_val(pte) & BTFIXUP_HALF(pte_filei); } @@ -230,19 +230,19 @@ BTFIXUPDEF_HALF(pte_mkcleani) BTFIXUPDEF_HALF(pte_mkoldi) extern pte_t pte_wrprotect(pte_t pte) __attribute_const__; -extern __inline__ pte_t pte_wrprotect(pte_t pte) +static inline pte_t pte_wrprotect(pte_t pte) { return __pte(pte_val(pte) & ~BTFIXUP_HALF(pte_wrprotecti)); } extern pte_t pte_mkclean(pte_t pte) __attribute_const__; -extern __inline__ pte_t pte_mkclean(pte_t pte) +static inline pte_t pte_mkclean(pte_t pte) { return __pte(pte_val(pte) & ~BTFIXUP_HALF(pte_mkcleani)); } extern pte_t pte_mkold(pte_t pte) __attribute_const__; -extern __inline__ pte_t pte_mkold(pte_t pte) +static inline pte_t pte_mkold(pte_t pte) { return __pte(pte_val(pte) & ~BTFIXUP_HALF(pte_mkoldi)); } @@ -279,7 +279,7 @@ BTFIXUPDEF_CALL_CONST(pte_t, mk_pte_io, unsigned long, pgprot_t, int) BTFIXUPDEF_INT(pte_modify_mask) extern pte_t pte_modify(pte_t pte, pgprot_t newprot) __attribute_const__; -extern __inline__ pte_t pte_modify(pte_t pte, pgprot_t newprot) +static inline pte_t pte_modify(pte_t pte, pgprot_t newprot) { return __pte((pte_val(pte) & BTFIXUP_INT(pte_modify_mask)) | pgprot_val(newprot)); @@ -386,13 +386,13 @@ extern struct ctx_list ctx_used; /* Head of used contexts list */ #define NO_CONTEXT -1 -extern __inline__ void remove_from_ctx_list(struct ctx_list *entry) +static inline void remove_from_ctx_list(struct ctx_list *entry) { entry->next->prev = entry->prev; entry->prev->next = entry->next; } -extern __inline__ void add_to_ctx_list(struct ctx_list *head, struct ctx_list *entry) +static inline void add_to_ctx_list(struct ctx_list *head, struct ctx_list *entry) { entry->next = head; (entry->prev = head->prev)->next = entry; @@ -401,7 +401,7 @@ extern __inline__ void add_to_ctx_list(struct ctx_list *head, struct ctx_list *e #define add_to_free_ctxlist(entry) add_to_ctx_list(&ctx_free, entry) #define add_to_used_ctxlist(entry) add_to_ctx_list(&ctx_used, entry) -extern __inline__ unsigned long +static inline unsigned long __get_phys (unsigned long addr) { switch (sparc_cpu_model){ @@ -416,7 +416,7 @@ __get_phys (unsigned long addr) } } -extern __inline__ int +static inline int __get_iospace (unsigned long addr) { switch (sparc_cpu_model){ diff --git a/include/asm-sparc/pgtsrmmu.h b/include/asm-sparc/pgtsrmmu.h index ee3b9d93187..edeb9811e72 100644 --- a/include/asm-sparc/pgtsrmmu.h +++ b/include/asm-sparc/pgtsrmmu.h @@ -148,7 +148,7 @@ extern void *srmmu_nocache_pool; #define __nocache_fix(VADDR) __va(__nocache_pa(VADDR)) /* Accessing the MMU control register. */ -extern __inline__ unsigned int srmmu_get_mmureg(void) +static inline unsigned int srmmu_get_mmureg(void) { unsigned int retval; __asm__ __volatile__("lda [%%g0] %1, %0\n\t" : @@ -157,14 +157,14 @@ extern __inline__ unsigned int srmmu_get_mmureg(void) return retval; } -extern __inline__ void srmmu_set_mmureg(unsigned long regval) +static inline void srmmu_set_mmureg(unsigned long regval) { __asm__ __volatile__("sta %0, [%%g0] %1\n\t" : : "r" (regval), "i" (ASI_M_MMUREGS) : "memory"); } -extern __inline__ void srmmu_set_ctable_ptr(unsigned long paddr) +static inline void srmmu_set_ctable_ptr(unsigned long paddr) { paddr = ((paddr >> 4) & SRMMU_CTX_PMASK); __asm__ __volatile__("sta %0, [%1] %2\n\t" : : @@ -173,7 +173,7 @@ extern __inline__ void srmmu_set_ctable_ptr(unsigned long paddr) "memory"); } -extern __inline__ unsigned long srmmu_get_ctable_ptr(void) +static inline unsigned long srmmu_get_ctable_ptr(void) { unsigned int retval; @@ -184,14 +184,14 @@ extern __inline__ unsigned long srmmu_get_ctable_ptr(void) return (retval & SRMMU_CTX_PMASK) << 4; } -extern __inline__ void srmmu_set_context(int context) +static inline void srmmu_set_context(int context) { __asm__ __volatile__("sta %0, [%1] %2\n\t" : : "r" (context), "r" (SRMMU_CTX_REG), "i" (ASI_M_MMUREGS) : "memory"); } -extern __inline__ int srmmu_get_context(void) +static inline int srmmu_get_context(void) { register int retval; __asm__ __volatile__("lda [%1] %2, %0\n\t" : @@ -201,7 +201,7 @@ extern __inline__ int srmmu_get_context(void) return retval; } -extern __inline__ unsigned int srmmu_get_fstatus(void) +static inline unsigned int srmmu_get_fstatus(void) { unsigned int retval; @@ -211,7 +211,7 @@ extern __inline__ unsigned int srmmu_get_fstatus(void) return retval; } -extern __inline__ unsigned int srmmu_get_faddr(void) +static inline unsigned int srmmu_get_faddr(void) { unsigned int retval; @@ -222,7 +222,7 @@ extern __inline__ unsigned int srmmu_get_faddr(void) } /* This is guaranteed on all SRMMU's. */ -extern __inline__ void srmmu_flush_whole_tlb(void) +static inline void srmmu_flush_whole_tlb(void) { __asm__ __volatile__("sta %%g0, [%0] %1\n\t": : "r" (0x400), /* Flush entire TLB!! */ @@ -231,7 +231,7 @@ extern __inline__ void srmmu_flush_whole_tlb(void) } /* These flush types are not available on all chips... */ -extern __inline__ void srmmu_flush_tlb_ctx(void) +static inline void srmmu_flush_tlb_ctx(void) { __asm__ __volatile__("sta %%g0, [%0] %1\n\t": : "r" (0x300), /* Flush TLB ctx.. */ @@ -239,7 +239,7 @@ extern __inline__ void srmmu_flush_tlb_ctx(void) } -extern __inline__ void srmmu_flush_tlb_region(unsigned long addr) +static inline void srmmu_flush_tlb_region(unsigned long addr) { addr &= SRMMU_PGDIR_MASK; __asm__ __volatile__("sta %%g0, [%0] %1\n\t": : @@ -249,7 +249,7 @@ extern __inline__ void srmmu_flush_tlb_region(unsigned long addr) } -extern __inline__ void srmmu_flush_tlb_segment(unsigned long addr) +static inline void srmmu_flush_tlb_segment(unsigned long addr) { addr &= SRMMU_REAL_PMD_MASK; __asm__ __volatile__("sta %%g0, [%0] %1\n\t": : @@ -258,7 +258,7 @@ extern __inline__ void srmmu_flush_tlb_segment(unsigned long addr) } -extern __inline__ void srmmu_flush_tlb_page(unsigned long page) +static inline void srmmu_flush_tlb_page(unsigned long page) { page &= PAGE_MASK; __asm__ __volatile__("sta %%g0, [%0] %1\n\t": : @@ -267,7 +267,7 @@ extern __inline__ void srmmu_flush_tlb_page(unsigned long page) } -extern __inline__ unsigned long srmmu_hwprobe(unsigned long vaddr) +static inline unsigned long srmmu_hwprobe(unsigned long vaddr) { unsigned long retval; @@ -279,7 +279,7 @@ extern __inline__ unsigned long srmmu_hwprobe(unsigned long vaddr) return retval; } -extern __inline__ int +static inline int srmmu_get_pte (unsigned long addr) { register unsigned long entry; diff --git a/include/asm-sparc/processor.h b/include/asm-sparc/processor.h index 5a7a1a8d29a..6fbb3f0af8d 100644 --- a/include/asm-sparc/processor.h +++ b/include/asm-sparc/processor.h @@ -79,7 +79,7 @@ struct thread_struct { extern unsigned long thread_saved_pc(struct task_struct *t); /* Do necessary setup to start up a newly executed thread. */ -extern __inline__ void start_thread(struct pt_regs * regs, unsigned long pc, +static inline void start_thread(struct pt_regs * regs, unsigned long pc, unsigned long sp) { register unsigned long zero asm("g1"); diff --git a/include/asm-sparc/psr.h b/include/asm-sparc/psr.h index 9778b8c8b15..19c97805111 100644 --- a/include/asm-sparc/psr.h +++ b/include/asm-sparc/psr.h @@ -38,7 +38,7 @@ #ifndef __ASSEMBLY__ /* Get the %psr register. */ -extern __inline__ unsigned int get_psr(void) +static inline unsigned int get_psr(void) { unsigned int psr; __asm__ __volatile__( @@ -53,7 +53,7 @@ extern __inline__ unsigned int get_psr(void) return psr; } -extern __inline__ void put_psr(unsigned int new_psr) +static inline void put_psr(unsigned int new_psr) { __asm__ __volatile__( "wr %0, 0x0, %%psr\n\t" @@ -72,7 +72,7 @@ extern __inline__ void put_psr(unsigned int new_psr) extern unsigned int fsr_storage; -extern __inline__ unsigned int get_fsr(void) +static inline unsigned int get_fsr(void) { unsigned int fsr = 0; diff --git a/include/asm-sparc/sbi.h b/include/asm-sparc/sbi.h index 739ccac5dcf..86a603ac7b2 100644 --- a/include/asm-sparc/sbi.h +++ b/include/asm-sparc/sbi.h @@ -65,7 +65,7 @@ struct sbi_regs { #ifndef __ASSEMBLY__ -extern __inline__ int acquire_sbi(int devid, int mask) +static inline int acquire_sbi(int devid, int mask) { __asm__ __volatile__ ("swapa [%2] %3, %0" : "=r" (mask) : @@ -75,7 +75,7 @@ extern __inline__ int acquire_sbi(int devid, int mask) return mask; } -extern __inline__ void release_sbi(int devid, int mask) +static inline void release_sbi(int devid, int mask) { __asm__ __volatile__ ("sta %0, [%1] %2" : : "r" (mask), @@ -83,7 +83,7 @@ extern __inline__ void release_sbi(int devid, int mask) "i" (ASI_M_CTL)); } -extern __inline__ void set_sbi_tid(int devid, int targetid) +static inline void set_sbi_tid(int devid, int targetid) { __asm__ __volatile__ ("sta %0, [%1] %2" : : "r" (targetid), @@ -91,7 +91,7 @@ extern __inline__ void set_sbi_tid(int devid, int targetid) "i" (ASI_M_CTL)); } -extern __inline__ int get_sbi_ctl(int devid, int cfgno) +static inline int get_sbi_ctl(int devid, int cfgno) { int cfg; @@ -102,7 +102,7 @@ extern __inline__ int get_sbi_ctl(int devid, int cfgno) return cfg; } -extern __inline__ void set_sbi_ctl(int devid, int cfgno, int cfg) +static inline void set_sbi_ctl(int devid, int cfgno, int cfg) { __asm__ __volatile__ ("sta %0, [%1] %2" : : "r" (cfg), diff --git a/include/asm-sparc/sbus.h b/include/asm-sparc/sbus.h index 3a8b3908728..a13cddcecec 100644 --- a/include/asm-sparc/sbus.h +++ b/include/asm-sparc/sbus.h @@ -28,12 +28,12 @@ * numbers + offsets, and vice versa. */ -extern __inline__ unsigned long sbus_devaddr(int slotnum, unsigned long offset) +static inline unsigned long sbus_devaddr(int slotnum, unsigned long offset) { return (unsigned long) (SUN_SBUS_BVADDR+((slotnum)<<25)+(offset)); } -extern __inline__ int sbus_dev_slot(unsigned long dev_addr) +static inline int sbus_dev_slot(unsigned long dev_addr) { return (int) (((dev_addr)-SUN_SBUS_BVADDR)>>25); } @@ -80,7 +80,7 @@ struct sbus_bus { extern struct sbus_bus *sbus_root; -extern __inline__ int +static inline int sbus_is_slave(struct sbus_dev *dev) { /* XXX Have to write this for sun4c's */ diff --git a/include/asm-sparc/smp.h b/include/asm-sparc/smp.h index 4f96d8333a1..580c51d011d 100644 --- a/include/asm-sparc/smp.h +++ b/include/asm-sparc/smp.h @@ -60,22 +60,22 @@ BTFIXUPDEF_BLACKBOX(load_current) #define smp_cross_call(func,arg1,arg2,arg3,arg4,arg5) BTFIXUP_CALL(smp_cross_call)(func,arg1,arg2,arg3,arg4,arg5) #define smp_message_pass(target,msg,data,wait) BTFIXUP_CALL(smp_message_pass)(target,msg,data,wait) -extern __inline__ void xc0(smpfunc_t func) { smp_cross_call(func, 0, 0, 0, 0, 0); } -extern __inline__ void xc1(smpfunc_t func, unsigned long arg1) +static inline void xc0(smpfunc_t func) { smp_cross_call(func, 0, 0, 0, 0, 0); } +static inline void xc1(smpfunc_t func, unsigned long arg1) { smp_cross_call(func, arg1, 0, 0, 0, 0); } -extern __inline__ void xc2(smpfunc_t func, unsigned long arg1, unsigned long arg2) +static inline void xc2(smpfunc_t func, unsigned long arg1, unsigned long arg2) { smp_cross_call(func, arg1, arg2, 0, 0, 0); } -extern __inline__ void xc3(smpfunc_t func, unsigned long arg1, unsigned long arg2, +static inline void xc3(smpfunc_t func, unsigned long arg1, unsigned long arg2, unsigned long arg3) { smp_cross_call(func, arg1, arg2, arg3, 0, 0); } -extern __inline__ void xc4(smpfunc_t func, unsigned long arg1, unsigned long arg2, +static inline void xc4(smpfunc_t func, unsigned long arg1, unsigned long arg2, unsigned long arg3, unsigned long arg4) { smp_cross_call(func, arg1, arg2, arg3, arg4, 0); } -extern __inline__ void xc5(smpfunc_t func, unsigned long arg1, unsigned long arg2, +static inline void xc5(smpfunc_t func, unsigned long arg1, unsigned long arg2, unsigned long arg3, unsigned long arg4, unsigned long arg5) { smp_cross_call(func, arg1, arg2, arg3, arg4, arg5); } -extern __inline__ int smp_call_function(void (*func)(void *info), void *info, int nonatomic, int wait) +static inline int smp_call_function(void (*func)(void *info), void *info, int nonatomic, int wait) { xc1((smpfunc_t)func, (unsigned long)info); return 0; @@ -84,16 +84,16 @@ extern __inline__ int smp_call_function(void (*func)(void *info), void *info, in extern __volatile__ int __cpu_number_map[NR_CPUS]; extern __volatile__ int __cpu_logical_map[NR_CPUS]; -extern __inline__ int cpu_logical_map(int cpu) +static inline int cpu_logical_map(int cpu) { return __cpu_logical_map[cpu]; } -extern __inline__ int cpu_number_map(int cpu) +static inline int cpu_number_map(int cpu) { return __cpu_number_map[cpu]; } -extern __inline__ int hard_smp4m_processor_id(void) +static inline int hard_smp4m_processor_id(void) { int cpuid; @@ -104,7 +104,7 @@ extern __inline__ int hard_smp4m_processor_id(void) return cpuid; } -extern __inline__ int hard_smp4d_processor_id(void) +static inline int hard_smp4d_processor_id(void) { int cpuid; @@ -114,7 +114,7 @@ extern __inline__ int hard_smp4d_processor_id(void) } #ifndef MODULE -extern __inline__ int hard_smp_processor_id(void) +static inline int hard_smp_processor_id(void) { int cpuid; @@ -136,7 +136,7 @@ extern __inline__ int hard_smp_processor_id(void) return cpuid; } #else -extern __inline__ int hard_smp_processor_id(void) +static inline int hard_smp_processor_id(void) { int cpuid; diff --git a/include/asm-sparc/smpprim.h b/include/asm-sparc/smpprim.h index 9b9c28ed748..e7b6d346ae1 100644 --- a/include/asm-sparc/smpprim.h +++ b/include/asm-sparc/smpprim.h @@ -15,7 +15,7 @@ * atomic. */ -extern __inline__ __volatile__ char test_and_set(void *addr) +static inline __volatile__ char test_and_set(void *addr) { char state = 0; @@ -27,7 +27,7 @@ extern __inline__ __volatile__ char test_and_set(void *addr) } /* Initialize a spin-lock. */ -extern __inline__ __volatile__ smp_initlock(void *spinlock) +static inline __volatile__ smp_initlock(void *spinlock) { /* Unset the lock. */ *((unsigned char *) spinlock) = 0; @@ -36,7 +36,7 @@ extern __inline__ __volatile__ smp_initlock(void *spinlock) } /* This routine spins until it acquires the lock at ADDR. */ -extern __inline__ __volatile__ smp_lock(void *addr) +static inline __volatile__ smp_lock(void *addr) { while(test_and_set(addr) == 0xff) ; @@ -46,7 +46,7 @@ extern __inline__ __volatile__ smp_lock(void *addr) } /* This routine releases the lock at ADDR. */ -extern __inline__ __volatile__ smp_unlock(void *addr) +static inline __volatile__ smp_unlock(void *addr) { *((unsigned char *) addr) = 0; } diff --git a/include/asm-sparc/spinlock.h b/include/asm-sparc/spinlock.h index 111727a2bb4..e344c98a6f5 100644 --- a/include/asm-sparc/spinlock.h +++ b/include/asm-sparc/spinlock.h @@ -17,7 +17,7 @@ #define __raw_spin_unlock_wait(lock) \ do { while (__raw_spin_is_locked(lock)) cpu_relax(); } while (0) -extern __inline__ void __raw_spin_lock(raw_spinlock_t *lock) +static inline void __raw_spin_lock(raw_spinlock_t *lock) { __asm__ __volatile__( "\n1:\n\t" @@ -37,7 +37,7 @@ extern __inline__ void __raw_spin_lock(raw_spinlock_t *lock) : "g2", "memory", "cc"); } -extern __inline__ int __raw_spin_trylock(raw_spinlock_t *lock) +static inline int __raw_spin_trylock(raw_spinlock_t *lock) { unsigned int result; __asm__ __volatile__("ldstub [%1], %0" @@ -47,7 +47,7 @@ extern __inline__ int __raw_spin_trylock(raw_spinlock_t *lock) return (result == 0); } -extern __inline__ void __raw_spin_unlock(raw_spinlock_t *lock) +static inline void __raw_spin_unlock(raw_spinlock_t *lock) { __asm__ __volatile__("stb %%g0, [%0]" : : "r" (lock) : "memory"); } @@ -78,7 +78,7 @@ extern __inline__ void __raw_spin_unlock(raw_spinlock_t *lock) * * Unfortunately this scheme limits us to ~16,000,000 cpus. */ -extern __inline__ void __read_lock(raw_rwlock_t *rw) +static inline void __read_lock(raw_rwlock_t *rw) { register raw_rwlock_t *lp asm("g1"); lp = rw; @@ -98,7 +98,7 @@ do { unsigned long flags; \ local_irq_restore(flags); \ } while(0) -extern __inline__ void __read_unlock(raw_rwlock_t *rw) +static inline void __read_unlock(raw_rwlock_t *rw) { register raw_rwlock_t *lp asm("g1"); lp = rw; diff --git a/include/asm-sparc/system.h b/include/asm-sparc/system.h index 3557781a4bf..1f6b71f9e1b 100644 --- a/include/asm-sparc/system.h +++ b/include/asm-sparc/system.h @@ -204,7 +204,7 @@ static inline unsigned long getipl(void) BTFIXUPDEF_CALL(void, ___xchg32, void) #endif -extern __inline__ unsigned long xchg_u32(__volatile__ unsigned long *m, unsigned long val) +static inline unsigned long xchg_u32(__volatile__ unsigned long *m, unsigned long val) { #ifdef CONFIG_SMP __asm__ __volatile__("swap [%2], %0" diff --git a/include/asm-sparc/traps.h b/include/asm-sparc/traps.h index 6690ab956ea..f62c7f878ee 100644 --- a/include/asm-sparc/traps.h +++ b/include/asm-sparc/traps.h @@ -22,7 +22,7 @@ struct tt_entry { /* We set this to _start in system setup. */ extern struct tt_entry *sparc_ttable; -extern __inline__ unsigned long get_tbr(void) +static inline unsigned long get_tbr(void) { unsigned long tbr; -- cgit v1.2.3 From fdc657c66678551c7987dc23a78ae1a26251276f Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Mon, 3 Oct 2005 17:37:27 -0700 Subject: [SUNSU]: Fix bogus locking in sunsu_change_mouse_baud() The lock is not held when calling this function, so we shouldn't drop then reacquire it. Based upon a report from Jim MacBaine. Signed-off-by: David S. Miller --- drivers/serial/sunsu.c | 4 ---- 1 file changed, 4 deletions(-) diff --git a/drivers/serial/sunsu.c b/drivers/serial/sunsu.c index 5959e6755a8..656c0e8d160 100644 --- a/drivers/serial/sunsu.c +++ b/drivers/serial/sunsu.c @@ -518,11 +518,7 @@ static void sunsu_change_mouse_baud(struct uart_sunsu_port *up) quot = up->port.uartclk / (16 * new_baud); - spin_unlock(&up->port.lock); - sunsu_change_speed(&up->port, up->cflag, 0, quot); - - spin_lock(&up->port.lock); } static void receive_kbd_ms_chars(struct uart_sunsu_port *up, struct pt_regs *regs, int is_break) -- cgit v1.2.3 From c2681dd8c71c8fb4ca530f94536550fcd843aae4 Mon Sep 17 00:00:00 2001 From: Stephen Hemminger Date: Mon, 3 Oct 2005 12:03:13 -0700 Subject: [PATCH] skge: set mac address oops with bonding Skge driver was bringing link up/down when changing mac address. This doesn't work in the bonding environment, and is more effort than needed. Fixes-bug: http://bugzilla.kernel.org/show_bug.cgi?id=5271 Signed-off-by: Stephen Hemminger Signed-off-by: Jeff Garzik --- drivers/net/skge.c | 24 ++++++++++++++++-------- 1 file changed, 16 insertions(+), 8 deletions(-) diff --git a/drivers/net/skge.c b/drivers/net/skge.c index fd398da4993..c2e6484ef13 100644 --- a/drivers/net/skge.c +++ b/drivers/net/skge.c @@ -2837,21 +2837,29 @@ static void skge_netpoll(struct net_device *dev) static int skge_set_mac_address(struct net_device *dev, void *p) { struct skge_port *skge = netdev_priv(dev); - struct sockaddr *addr = p; - int err = 0; + struct skge_hw *hw = skge->hw; + unsigned port = skge->port; + const struct sockaddr *addr = p; if (!is_valid_ether_addr(addr->sa_data)) return -EADDRNOTAVAIL; - skge_down(dev); + spin_lock_bh(&hw->phy_lock); memcpy(dev->dev_addr, addr->sa_data, ETH_ALEN); - memcpy_toio(skge->hw->regs + B2_MAC_1 + skge->port*8, + memcpy_toio(hw->regs + B2_MAC_1 + port*8, dev->dev_addr, ETH_ALEN); - memcpy_toio(skge->hw->regs + B2_MAC_2 + skge->port*8, + memcpy_toio(hw->regs + B2_MAC_2 + port*8, dev->dev_addr, ETH_ALEN); - if (dev->flags & IFF_UP) - err = skge_up(dev); - return err; + + if (hw->chip_id == CHIP_ID_GENESIS) + xm_outaddr(hw, port, XM_SA, dev->dev_addr); + else { + gma_set_addr(hw, port, GM_SRC_ADDR_1L, dev->dev_addr); + gma_set_addr(hw, port, GM_SRC_ADDR_2L, dev->dev_addr); + } + spin_unlock_bh(&hw->phy_lock); + + return 0; } static const struct { -- cgit v1.2.3 From 0a1c80f1115b9a1aacf00a312a532ceef49dfa1b Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Sun, 2 Oct 2005 22:42:11 -0700 Subject: [PATCH] ns83820: fix gfp flags type Fix implicit nocast warnings in ns83820 code: drivers/net/ns83820.c:603:46: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: Jeff Garzik --- drivers/net/ns83820.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/ns83820.c b/drivers/net/ns83820.c index e64df4d0800..1d123d2b53f 100644 --- a/drivers/net/ns83820.c +++ b/drivers/net/ns83820.c @@ -584,7 +584,7 @@ static inline int ns83820_add_rx_skb(struct ns83820 *dev, struct sk_buff *skb) return 0; } -static inline int rx_refill(struct net_device *ndev, int gfp) +static inline int rx_refill(struct net_device *ndev, unsigned int gfp) { struct ns83820 *dev = PRIV(ndev); unsigned i; -- cgit v1.2.3 From 8cb6108baee9dcd1dc96f476fe217d6a6b53c994 Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Sun, 2 Oct 2005 22:41:09 -0700 Subject: [PATCH] ieee80211: fix gfp flags type Fix implicit nocast warnings in ieee80211 code: net/ieee80211/ieee80211_tx.c:215:9: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: Jeff Garzik --- net/ieee80211/ieee80211_tx.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/ieee80211/ieee80211_tx.c b/net/ieee80211/ieee80211_tx.c index c9aaff3fea1..f9153671168 100644 --- a/net/ieee80211/ieee80211_tx.c +++ b/net/ieee80211/ieee80211_tx.c @@ -207,7 +207,7 @@ void ieee80211_txb_free(struct ieee80211_txb *txb) } static struct ieee80211_txb *ieee80211_alloc_txb(int nr_frags, int txb_size, - int gfp_mask) + unsigned int gfp_mask) { struct ieee80211_txb *txb; int i; -- cgit v1.2.3 From bb53d6d0e70cd0749a7844efc62cefeb24b134b6 Mon Sep 17 00:00:00 2001 From: Komuro Date: Mon, 3 Oct 2005 22:03:28 -0400 Subject: [netdrvr] fix smc91c92_cs multicast bug The smc91c92_cs multicast does not work if the count of multicast address is 1. Signed-off-by: Signed-off-by: Jeff Garzik --- drivers/net/pcmcia/smc91c92_cs.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/pcmcia/smc91c92_cs.c b/drivers/net/pcmcia/smc91c92_cs.c index d652e1eddb4..c7cca842e5e 100644 --- a/drivers/net/pcmcia/smc91c92_cs.c +++ b/drivers/net/pcmcia/smc91c92_cs.c @@ -1832,7 +1832,7 @@ static void fill_multicast_tbl(int count, struct dev_mc_list *addrs, { struct dev_mc_list *mc_addr; - for (mc_addr = addrs; mc_addr && --count > 0; mc_addr = mc_addr->next) { + for (mc_addr = addrs; mc_addr && count-- > 0; mc_addr = mc_addr->next) { u_int position = ether_crc(6, mc_addr->dmi_addr); #ifndef final_version /* Verify multicast address. */ if ((mc_addr->dmi_addr[0] & 1) == 0) -- cgit v1.2.3 From 9123e0d78990246304fe681167b8d8097f1e02d7 Mon Sep 17 00:00:00 2001 From: Ursula Braun Date: Fri, 30 Sep 2005 10:17:24 +0200 Subject: [PATCH] s390: qeth driver fixes From: Peter Tiedemann From: Frank Pavlic minor qeth fixes: - free old skb in qeth_realloc_headroom after duplicating skb - disable IPV6 support for Hipersockets devices - call ccw_device_set_offline on every channel regardless of the return value of the prior ccw_device_set_offline calls - allocate qdio structures in DMA-area - schedule recovery of appropriate card when cable has been inserted again. - add missing initialization of card->lock - write sequence number in skb->cb for SNA protocol which requires strictly serialized packets. Signed-off-by: Frank Pavlic diffstat: qeth.h | 2 ++ qeth_main.c | 37 +++++++++++++++++-------------------- 2 files changed, 19 insertions(+), 20 deletions(-) Signed-off-by: Jeff Garzik --- drivers/s390/net/qeth.h | 2 ++ drivers/s390/net/qeth_main.c | 37 +++++++++++++++++-------------------- 2 files changed, 19 insertions(+), 20 deletions(-) diff --git a/drivers/s390/net/qeth.h b/drivers/s390/net/qeth.h index 2ad4797ce02..9963479ba89 100644 --- a/drivers/s390/net/qeth.h +++ b/drivers/s390/net/qeth.h @@ -686,6 +686,7 @@ struct qeth_seqno { __u32 pdu_hdr; __u32 pdu_hdr_ack; __u16 ipa; + __u32 pkt_seqno; }; struct qeth_reply { @@ -848,6 +849,7 @@ qeth_realloc_headroom(struct qeth_card *card, struct sk_buff **skb, int size) "on interface %s", QETH_CARD_IFNAME(card)); return -ENOMEM; } + kfree_skb(*skb); *skb = new_skb; } return 0; diff --git a/drivers/s390/net/qeth_main.c b/drivers/s390/net/qeth_main.c index 71de834ece1..bd28e2438d7 100644 --- a/drivers/s390/net/qeth_main.c +++ b/drivers/s390/net/qeth_main.c @@ -511,7 +511,7 @@ static int __qeth_set_offline(struct ccwgroup_device *cgdev, int recovery_mode) { struct qeth_card *card = (struct qeth_card *) cgdev->dev.driver_data; - int rc = 0; + int rc = 0, rc2 = 0, rc3 = 0; enum qeth_card_states recover_flag; QETH_DBF_TEXT(setup, 3, "setoffl"); @@ -523,11 +523,13 @@ __qeth_set_offline(struct ccwgroup_device *cgdev, int recovery_mode) CARD_BUS_ID(card)); return -ERESTARTSYS; } - if ((rc = ccw_device_set_offline(CARD_DDEV(card))) || - (rc = ccw_device_set_offline(CARD_WDEV(card))) || - (rc = ccw_device_set_offline(CARD_RDEV(card)))) { + rc = ccw_device_set_offline(CARD_DDEV(card)); + rc2 = ccw_device_set_offline(CARD_WDEV(card)); + rc3 = ccw_device_set_offline(CARD_RDEV(card)); + if (!rc) + rc = (rc2) ? rc2 : rc3; + if (rc) QETH_DBF_TEXT_(setup, 2, "1err%d", rc); - } if (recover_flag == CARD_STATE_UP) card->state = CARD_STATE_RECOVER; qeth_notify_processes(); @@ -1046,6 +1048,7 @@ qeth_setup_card(struct qeth_card *card) spin_lock_init(&card->vlanlock); card->vlangrp = NULL; #endif + spin_lock_init(&card->lock); spin_lock_init(&card->ip_lock); spin_lock_init(&card->thread_mask_lock); card->thread_start_mask = 0; @@ -1626,16 +1629,6 @@ qeth_cmd_timeout(unsigned long data) spin_unlock_irqrestore(&reply->card->lock, flags); } -static void -qeth_reset_ip_addresses(struct qeth_card *card) -{ - QETH_DBF_TEXT(trace, 2, "rstipadd"); - - qeth_clear_ip_list(card, 0, 1); - /* this function will also schedule the SET_IP_THREAD */ - qeth_set_multicast_list(card->dev); -} - static struct qeth_ipa_cmd * qeth_check_ipa_data(struct qeth_card *card, struct qeth_cmd_buffer *iob) { @@ -1664,9 +1657,8 @@ qeth_check_ipa_data(struct qeth_card *card, struct qeth_cmd_buffer *iob) "IP address reset.\n", QETH_CARD_IFNAME(card), card->info.chpid); - card->lan_online = 1; netif_carrier_on(card->dev); - qeth_reset_ip_addresses(card); + qeth_schedule_recovery(card); return NULL; case IPA_CMD_REGISTER_LOCAL_ADDR: QETH_DBF_TEXT(trace,3, "irla"); @@ -2387,6 +2379,7 @@ qeth_layer2_rebuild_skb(struct qeth_card *card, struct sk_buff *skb, skb_pull(skb, VLAN_HLEN); } #endif + *((__u32 *)skb->cb) = ++card->seqno.pkt_seqno; return vlan_id; } @@ -3014,7 +3007,7 @@ qeth_alloc_buffer_pool(struct qeth_card *card) return -ENOMEM; } for(j = 0; j < QETH_MAX_BUFFER_ELEMENTS(card); ++j){ - ptr = (void *) __get_free_page(GFP_KERNEL); + ptr = (void *) __get_free_page(GFP_KERNEL|GFP_DMA); if (!ptr) { while (j > 0) free_page((unsigned long) @@ -3058,7 +3051,8 @@ qeth_alloc_qdio_buffers(struct qeth_card *card) if (card->qdio.state == QETH_QDIO_ALLOCATED) return 0; - card->qdio.in_q = kmalloc(sizeof(struct qeth_qdio_q), GFP_KERNEL); + card->qdio.in_q = kmalloc(sizeof(struct qeth_qdio_q), + GFP_KERNEL|GFP_DMA); if (!card->qdio.in_q) return - ENOMEM; QETH_DBF_TEXT(setup, 2, "inq"); @@ -3083,7 +3077,7 @@ qeth_alloc_qdio_buffers(struct qeth_card *card) } for (i = 0; i < card->qdio.no_out_queues; ++i){ card->qdio.out_qs[i] = kmalloc(sizeof(struct qeth_qdio_out_q), - GFP_KERNEL); + GFP_KERNEL|GFP_DMA); if (!card->qdio.out_qs[i]){ while (i > 0) kfree(card->qdio.out_qs[--i]); @@ -6470,6 +6464,9 @@ qeth_query_ipassists_cb(struct qeth_card *card, struct qeth_reply *reply, if (cmd->hdr.prot_version == QETH_PROT_IPV4) { card->options.ipa4.supported_funcs = cmd->hdr.ipa_supported; card->options.ipa4.enabled_funcs = cmd->hdr.ipa_enabled; + /* Disable IPV6 support hard coded for Hipersockets */ + if(card->info.type == QETH_CARD_TYPE_IQD) + card->options.ipa4.supported_funcs &= ~IPA_IPV6; } else { #ifdef CONFIG_QETH_IPV6 card->options.ipa6.supported_funcs = cmd->hdr.ipa_supported; -- cgit v1.2.3 From 217df670d9a4da036d68b22500ac06128811d5c8 Mon Sep 17 00:00:00 2001 From: Jay Vosburgh Date: Mon, 26 Sep 2005 16:11:50 -0700 Subject: [PATCH] fix bonding crash, remove old ABI support David S. Miller wrote: >I think removing support for older ifenslave binaries is >the least painful solution to this problem. This patch removes backwards compatibility for old ifenslave binaries (ifenslave prior to verison 1.0.0). I did not similarly modify ifenslave itself; with sysfs on the horizon, I don't see that as being worthwhile. Signed-off-by: Jay Vosburgh Signed-off-by: Jeff Garzik --- drivers/net/bonding/bond_main.c | 280 ++++++++++------------------------------ drivers/net/bonding/bonding.h | 4 +- 2 files changed, 71 insertions(+), 213 deletions(-) diff --git a/drivers/net/bonding/bond_main.c b/drivers/net/bonding/bond_main.c index bf81cd45e4d..fd62e43a351 100644 --- a/drivers/net/bonding/bond_main.c +++ b/drivers/net/bonding/bond_main.c @@ -487,6 +487,8 @@ * * Added xmit_hash_policy_layer34() * - Modified by Jay Vosburgh to also support mode 4. * Set version to 2.6.3. + * 2005/09/26 - Jay Vosburgh + * - Removed backwards compatibility for old ifenslaves. Version 2.6.4. */ //#define BONDING_DEBUG 1 @@ -595,14 +597,7 @@ static int arp_ip_count = 0; static int bond_mode = BOND_MODE_ROUNDROBIN; static int xmit_hashtype= BOND_XMIT_POLICY_LAYER2; static int lacp_fast = 0; -static int app_abi_ver = 0; -static int orig_app_abi_ver = -1; /* This is used to save the first ABI version - * we receive from the application. Once set, - * it won't be changed, and the module will - * refuse to enslave/release interfaces if the - * command comes from an application using - * another ABI version. - */ + struct bond_parm_tbl { char *modename; int mode; @@ -1702,51 +1697,29 @@ static int bond_enslave(struct net_device *bond_dev, struct net_device *slave_de } } - if (app_abi_ver >= 1) { - /* The application is using an ABI, which requires the - * slave interface to be closed. - */ - if ((slave_dev->flags & IFF_UP)) { - printk(KERN_ERR DRV_NAME - ": Error: %s is up\n", - slave_dev->name); - res = -EPERM; - goto err_undo_flags; - } - - if (slave_dev->set_mac_address == NULL) { - printk(KERN_ERR DRV_NAME - ": Error: The slave device you specified does " - "not support setting the MAC address.\n"); - printk(KERN_ERR - "Your kernel likely does not support slave " - "devices.\n"); + /* + * Old ifenslave binaries are no longer supported. These can + * be identified with moderate accurary by the state of the slave: + * the current ifenslave will set the interface down prior to + * enslaving it; the old ifenslave will not. + */ + if ((slave_dev->flags & IFF_UP)) { + printk(KERN_ERR DRV_NAME ": %s is up. " + "This may be due to an out of date ifenslave.\n", + slave_dev->name); + res = -EPERM; + goto err_undo_flags; + } - res = -EOPNOTSUPP; - goto err_undo_flags; - } - } else { - /* The application is not using an ABI, which requires the - * slave interface to be open. - */ - if (!(slave_dev->flags & IFF_UP)) { - printk(KERN_ERR DRV_NAME - ": Error: %s is not running\n", - slave_dev->name); - res = -EINVAL; - goto err_undo_flags; - } + if (slave_dev->set_mac_address == NULL) { + printk(KERN_ERR DRV_NAME + ": Error: The slave device you specified does " + "not support setting the MAC address.\n"); + printk(KERN_ERR + "Your kernel likely does not support slave devices.\n"); - if ((bond->params.mode == BOND_MODE_8023AD) || - (bond->params.mode == BOND_MODE_TLB) || - (bond->params.mode == BOND_MODE_ALB)) { - printk(KERN_ERR DRV_NAME - ": Error: to use %s mode, you must upgrade " - "ifenslave.\n", - bond_mode_name(bond->params.mode)); - res = -EOPNOTSUPP; - goto err_undo_flags; - } + res = -EOPNOTSUPP; + goto err_undo_flags; } new_slave = kmalloc(sizeof(struct slave), GFP_KERNEL); @@ -1762,41 +1735,36 @@ static int bond_enslave(struct net_device *bond_dev, struct net_device *slave_de */ new_slave->original_flags = slave_dev->flags; - if (app_abi_ver >= 1) { - /* save slave's original ("permanent") mac address for - * modes that needs it, and for restoring it upon release, - * and then set it to the master's address - */ - memcpy(new_slave->perm_hwaddr, slave_dev->dev_addr, ETH_ALEN); + /* + * Save slave's original ("permanent") mac address for modes + * that need it, and for restoring it upon release, and then + * set it to the master's address + */ + memcpy(new_slave->perm_hwaddr, slave_dev->dev_addr, ETH_ALEN); - /* set slave to master's mac address - * The application already set the master's - * mac address to that of the first slave - */ - memcpy(addr.sa_data, bond_dev->dev_addr, bond_dev->addr_len); - addr.sa_family = slave_dev->type; - res = dev_set_mac_address(slave_dev, &addr); - if (res) { - dprintk("Error %d calling set_mac_address\n", res); - goto err_free; - } + /* + * Set slave to master's mac address. The application already + * set the master's mac address to that of the first slave + */ + memcpy(addr.sa_data, bond_dev->dev_addr, bond_dev->addr_len); + addr.sa_family = slave_dev->type; + res = dev_set_mac_address(slave_dev, &addr); + if (res) { + dprintk("Error %d calling set_mac_address\n", res); + goto err_free; + } - /* open the slave since the application closed it */ - res = dev_open(slave_dev); - if (res) { - dprintk("Openning slave %s failed\n", slave_dev->name); - goto err_restore_mac; - } + /* open the slave since the application closed it */ + res = dev_open(slave_dev); + if (res) { + dprintk("Openning slave %s failed\n", slave_dev->name); + goto err_restore_mac; } res = netdev_set_master(slave_dev, bond_dev); if (res) { dprintk("Error %d calling netdev_set_master\n", res); - if (app_abi_ver < 1) { - goto err_free; - } else { - goto err_close; - } + goto err_close; } new_slave->dev = slave_dev; @@ -1997,39 +1965,6 @@ static int bond_enslave(struct net_device *bond_dev, struct net_device *slave_de write_unlock_bh(&bond->lock); - if (app_abi_ver < 1) { - /* - * !!! This is to support old versions of ifenslave. - * We can remove this in 2.5 because our ifenslave takes - * care of this for us. - * We check to see if the master has a mac address yet. - * If not, we'll give it the mac address of our slave device. - */ - int ndx = 0; - - for (ndx = 0; ndx < bond_dev->addr_len; ndx++) { - dprintk("Checking ndx=%d of bond_dev->dev_addr\n", - ndx); - if (bond_dev->dev_addr[ndx] != 0) { - dprintk("Found non-zero byte at ndx=%d\n", - ndx); - break; - } - } - - if (ndx == bond_dev->addr_len) { - /* - * We got all the way through the address and it was - * all 0's. - */ - dprintk("%s doesn't have a MAC address yet. \n", - bond_dev->name); - dprintk("Going to give assign it from %s.\n", - slave_dev->name); - bond_sethwaddr(bond_dev, slave_dev); - } - } - printk(KERN_INFO DRV_NAME ": %s: enslaving %s as a%s interface with a%s link.\n", bond_dev->name, slave_dev->name, @@ -2227,12 +2162,10 @@ static int bond_release(struct net_device *bond_dev, struct net_device *slave_de /* close slave before restoring its mac address */ dev_close(slave_dev); - if (app_abi_ver >= 1) { - /* restore original ("permanent") mac address */ - memcpy(addr.sa_data, slave->perm_hwaddr, ETH_ALEN); - addr.sa_family = slave_dev->type; - dev_set_mac_address(slave_dev, &addr); - } + /* restore original ("permanent") mac address */ + memcpy(addr.sa_data, slave->perm_hwaddr, ETH_ALEN); + addr.sa_family = slave_dev->type; + dev_set_mac_address(slave_dev, &addr); /* restore the original state of the * IFF_NOARP flag that might have been @@ -2320,12 +2253,10 @@ static int bond_release_all(struct net_device *bond_dev) /* close slave before restoring its mac address */ dev_close(slave_dev); - if (app_abi_ver >= 1) { - /* restore original ("permanent") mac address*/ - memcpy(addr.sa_data, slave->perm_hwaddr, ETH_ALEN); - addr.sa_family = slave_dev->type; - dev_set_mac_address(slave_dev, &addr); - } + /* restore original ("permanent") mac address*/ + memcpy(addr.sa_data, slave->perm_hwaddr, ETH_ALEN); + addr.sa_family = slave_dev->type; + dev_set_mac_address(slave_dev, &addr); /* restore the original state of the IFF_NOARP flag that might have * been set by bond_set_slave_inactive_flags() @@ -2423,57 +2354,6 @@ static int bond_ioctl_change_active(struct net_device *bond_dev, struct net_devi return res; } -static int bond_ethtool_ioctl(struct net_device *bond_dev, struct ifreq *ifr) -{ - struct ethtool_drvinfo info; - void __user *addr = ifr->ifr_data; - uint32_t cmd; - - if (get_user(cmd, (uint32_t __user *)addr)) { - return -EFAULT; - } - - switch (cmd) { - case ETHTOOL_GDRVINFO: - if (copy_from_user(&info, addr, sizeof(info))) { - return -EFAULT; - } - - if (strcmp(info.driver, "ifenslave") == 0) { - int new_abi_ver; - char *endptr; - - new_abi_ver = simple_strtoul(info.fw_version, - &endptr, 0); - if (*endptr) { - printk(KERN_ERR DRV_NAME - ": Error: got invalid ABI " - "version from application\n"); - - return -EINVAL; - } - - if (orig_app_abi_ver == -1) { - orig_app_abi_ver = new_abi_ver; - } - - app_abi_ver = new_abi_ver; - } - - strncpy(info.driver, DRV_NAME, 32); - strncpy(info.version, DRV_VERSION, 32); - snprintf(info.fw_version, 32, "%d", BOND_ABI_VERSION); - - if (copy_to_user(addr, &info, sizeof(info))) { - return -EFAULT; - } - - return 0; - default: - return -EOPNOTSUPP; - } -} - static int bond_info_query(struct net_device *bond_dev, struct ifbond *info) { struct bonding *bond = bond_dev->priv; @@ -3442,16 +3322,11 @@ static void bond_info_show_slave(struct seq_file *seq, const struct slave *slave seq_printf(seq, "Link Failure Count: %d\n", slave->link_failure_count); - if (app_abi_ver >= 1) { - seq_printf(seq, - "Permanent HW addr: %02x:%02x:%02x:%02x:%02x:%02x\n", - slave->perm_hwaddr[0], - slave->perm_hwaddr[1], - slave->perm_hwaddr[2], - slave->perm_hwaddr[3], - slave->perm_hwaddr[4], - slave->perm_hwaddr[5]); - } + seq_printf(seq, + "Permanent HW addr: %02x:%02x:%02x:%02x:%02x:%02x\n", + slave->perm_hwaddr[0], slave->perm_hwaddr[1], + slave->perm_hwaddr[2], slave->perm_hwaddr[3], + slave->perm_hwaddr[4], slave->perm_hwaddr[5]); if (bond->params.mode == BOND_MODE_8023AD) { const struct aggregator *agg @@ -4010,15 +3885,12 @@ static int bond_do_ioctl(struct net_device *bond_dev, struct ifreq *ifr, int cmd struct ifslave k_sinfo; struct ifslave __user *u_sinfo = NULL; struct mii_ioctl_data *mii = NULL; - int prev_abi_ver = orig_app_abi_ver; int res = 0; dprintk("bond_ioctl: master=%s, cmd=%d\n", bond_dev->name, cmd); switch (cmd) { - case SIOCETHTOOL: - return bond_ethtool_ioctl(bond_dev, ifr); case SIOCGMIIPHY: mii = if_mii(ifr); if (!mii) { @@ -4090,21 +3962,6 @@ static int bond_do_ioctl(struct net_device *bond_dev, struct ifreq *ifr, int cmd return -EPERM; } - if (orig_app_abi_ver == -1) { - /* no orig_app_abi_ver was provided yet, so we'll use the - * current one from now on, even if it's 0 - */ - orig_app_abi_ver = app_abi_ver; - - } else if (orig_app_abi_ver != app_abi_ver) { - printk(KERN_ERR DRV_NAME - ": Error: already using ifenslave ABI version %d; to " - "upgrade ifenslave to version %d, you must first " - "reload bonding.\n", - orig_app_abi_ver, app_abi_ver); - return -EINVAL; - } - slave_dev = dev_get_by_name(ifr->ifr_slave); dprintk("slave_dev=%p: \n", slave_dev); @@ -4137,14 +3994,6 @@ static int bond_do_ioctl(struct net_device *bond_dev, struct ifreq *ifr, int cmd dev_put(slave_dev); } - if (res < 0) { - /* The ioctl failed, so there's no point in changing the - * orig_app_abi_ver. We'll restore it's value just in case - * we've changed it earlier in this function. - */ - orig_app_abi_ver = prev_abi_ver; - } - return res; } @@ -4578,9 +4427,18 @@ static inline void bond_set_mode_ops(struct bonding *bond, int mode) } } +static void bond_ethtool_get_drvinfo(struct net_device *bond_dev, + struct ethtool_drvinfo *drvinfo) +{ + strncpy(drvinfo->driver, DRV_NAME, 32); + strncpy(drvinfo->version, DRV_VERSION, 32); + snprintf(drvinfo->fw_version, 32, "%d", BOND_ABI_VERSION); +} + static struct ethtool_ops bond_ethtool_ops = { .get_tx_csum = ethtool_op_get_tx_csum, .get_sg = ethtool_op_get_sg, + .get_drvinfo = bond_ethtool_get_drvinfo, }; /* diff --git a/drivers/net/bonding/bonding.h b/drivers/net/bonding/bonding.h index 38819698086..bbf9da8af62 100644 --- a/drivers/net/bonding/bonding.h +++ b/drivers/net/bonding/bonding.h @@ -40,8 +40,8 @@ #include "bond_3ad.h" #include "bond_alb.h" -#define DRV_VERSION "2.6.3" -#define DRV_RELDATE "June 8, 2005" +#define DRV_VERSION "2.6.4" +#define DRV_RELDATE "September 26, 2005" #define DRV_NAME "bonding" #define DRV_DESCRIPTION "Ethernet Channel Bonding Driver" -- cgit v1.2.3 From 32b5bfab9a09b19ea9a7d902b249ebf311fd2999 Mon Sep 17 00:00:00 2001 From: Philippe De Muyter Date: Thu, 22 Sep 2005 11:09:44 +0200 Subject: [PATCH] tulip DC21143 rev 48 10Mbit HDX fix The patch below is necessary to allow my Digital DS21143 Tulip rev 48 ethernet interface to work in a 10Mbit Half Duplex network. Without it, the driver keeps retrying other modes in an endless loop. It seems like someone already had the same problem with a rev 65 board :) Signed-off-by: Philippe De Muyter Signed-off-by: Jeff Garzik --- drivers/net/tulip/21142.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/tulip/21142.c b/drivers/net/tulip/21142.c index 5db694c4eb0..683f14b01c0 100644 --- a/drivers/net/tulip/21142.c +++ b/drivers/net/tulip/21142.c @@ -172,7 +172,7 @@ void t21142_lnk_change(struct net_device *dev, int csr5) int i; for (i = 0; i < tp->mtable->leafcount; i++) if (tp->mtable->mleaf[i].media == dev->if_port) { - int startup = ! ((tp->chip_id == DC21143 && tp->revision == 65)); + int startup = ! ((tp->chip_id == DC21143 && (tp->revision == 48 || tp->revision == 65))); tp->cur_index = i; tulip_select_media(dev, startup); setup_done = 1; -- cgit v1.2.3 From 49a9db07abd4ac89693dbd4dcd92fcd1f30ece00 Mon Sep 17 00:00:00 2001 From: Wade Farnsworth Date: Mon, 3 Oct 2005 22:21:33 -0400 Subject: [PATCH] emac: add support for platform-specific unsupported PHY features This patch adds support to the ibm_emac driver for platform-specific unsupported PHY features. The patch attempts to determine the highest speed and duplex when autonegotiation is unsupported. Signed-off-by: Wade Farnsworth Signed-off-by: Jeff Garzik --- drivers/net/ibm_emac/ibm_emac_core.c | 31 +++++++++++++++++++++++++++++++ 1 file changed, 31 insertions(+) diff --git a/drivers/net/ibm_emac/ibm_emac_core.c b/drivers/net/ibm_emac/ibm_emac_core.c index 0de3bb90617..14e9b6315f2 100644 --- a/drivers/net/ibm_emac/ibm_emac_core.c +++ b/drivers/net/ibm_emac/ibm_emac_core.c @@ -1875,6 +1875,9 @@ static int emac_init_device(struct ocp_device *ocpdev, struct ibm_ocp_mal *mal) rc = -ENODEV; goto bail; } + + /* Disable any PHY features not supported by the platform */ + ep->phy_mii.def->features &= ~emacdata->phy_feat_exc; /* Setup initial PHY config & startup aneg */ if (ep->phy_mii.def->ops->init) @@ -1882,6 +1885,34 @@ static int emac_init_device(struct ocp_device *ocpdev, struct ibm_ocp_mal *mal) netif_carrier_off(ndev); if (ep->phy_mii.def->features & SUPPORTED_Autoneg) ep->want_autoneg = 1; + else { + ep->want_autoneg = 0; + + /* Select highest supported speed/duplex */ + if (ep->phy_mii.def->features & SUPPORTED_1000baseT_Full) { + ep->phy_mii.speed = SPEED_1000; + ep->phy_mii.duplex = DUPLEX_FULL; + } else if (ep->phy_mii.def->features & + SUPPORTED_1000baseT_Half) { + ep->phy_mii.speed = SPEED_1000; + ep->phy_mii.duplex = DUPLEX_HALF; + } else if (ep->phy_mii.def->features & + SUPPORTED_100baseT_Full) { + ep->phy_mii.speed = SPEED_100; + ep->phy_mii.duplex = DUPLEX_FULL; + } else if (ep->phy_mii.def->features & + SUPPORTED_100baseT_Half) { + ep->phy_mii.speed = SPEED_100; + ep->phy_mii.duplex = DUPLEX_HALF; + } else if (ep->phy_mii.def->features & + SUPPORTED_10baseT_Full) { + ep->phy_mii.speed = SPEED_10; + ep->phy_mii.duplex = DUPLEX_FULL; + } else { + ep->phy_mii.speed = SPEED_10; + ep->phy_mii.duplex = DUPLEX_HALF; + } + } emac_start_link(ep, NULL); /* read the MAC Address */ -- cgit v1.2.3 From 32fa2bfcf882f8901ca206e33b0d8975cc8e89a2 Mon Sep 17 00:00:00 2001 From: Grant Coady Date: Sat, 10 Sep 2005 00:14:05 +1000 Subject: [PATCH] net/Kconfig: convert pocket_adapter ISA to PARPORT This patch changes pocket and parallel adaptors to depend on PARPORT instead of ISA in order to get the option in newer SuperIO based systems. Signed-off-by: Grant Coady Signed-off-by: Jeff Garzik --- drivers/net/Kconfig | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/drivers/net/Kconfig b/drivers/net/Kconfig index 2a908c4690a..c748b0e1641 100644 --- a/drivers/net/Kconfig +++ b/drivers/net/Kconfig @@ -1655,7 +1655,7 @@ config LAN_SAA9730 config NET_POCKET bool "Pocket and portable adapters" - depends on NET_ETHERNET && ISA + depends on NET_ETHERNET && PARPORT ---help--- Cute little network (Ethernet) devices which attach to the parallel port ("pocket adapters"), commonly used with laptops. If you have @@ -1679,7 +1679,7 @@ config NET_POCKET config ATP tristate "AT-LAN-TEC/RealTek pocket adapter support" - depends on NET_POCKET && ISA && X86 + depends on NET_POCKET && PARPORT && X86 select CRC32 ---help--- This is a network (Ethernet) device which attaches to your parallel @@ -1694,7 +1694,7 @@ config ATP config DE600 tristate "D-Link DE600 pocket adapter support" - depends on NET_POCKET && ISA + depends on NET_POCKET && PARPORT ---help--- This is a network (Ethernet) device which attaches to your parallel port. Read as well as the @@ -1709,7 +1709,7 @@ config DE600 config DE620 tristate "D-Link DE620 pocket adapter support" - depends on NET_POCKET && ISA + depends on NET_POCKET && PARPORT ---help--- This is a network (Ethernet) device which attaches to your parallel port. Read as well as the -- cgit v1.2.3 From 67974231d4354fe26aaa39a3153b5c0945b94858 Mon Sep 17 00:00:00 2001 From: Ion Badulescu Date: Mon, 3 Oct 2005 22:31:36 -0400 Subject: [netdrvr starfire] fix highmem and broken firmware issues Unfortunately, [your patch] might address the crash but doesn't address the real problem. It turns out that the problem is one of padding (the firmware cksum engine works only on 32-bit chunks, yuck), so the special casing for length == 1 wasn't sufficient anyway. This patch addresses the issue, as well the other issue of i386 + CONFIG_HIGHMEM being broken. It is pretty much the same workaround that Adaptec themselves used in their Windows driver. I have yet to check if it fixes the problem when the skb is non-linear, but this patch _will_ solve the problem for 99% of the users out there (those not using sendfile). Signed-off-by: Ion Badulescu Signed-off-by: Jeff Garzik --- drivers/net/starfire.c | 46 ++++++++++++++++++++++++---------------------- 1 file changed, 24 insertions(+), 22 deletions(-) diff --git a/drivers/net/starfire.c b/drivers/net/starfire.c index 88b89dc95c7..efdb179ecc8 100644 --- a/drivers/net/starfire.c +++ b/drivers/net/starfire.c @@ -133,14 +133,18 @@ - finally added firmware (GPL'ed by Adaptec) - removed compatibility code for 2.2.x + LK1.4.2.1 (Ion Badulescu) + - fixed 32/64 bit issues on i386 + CONFIG_HIGHMEM + - added 32-bit padding to outgoing skb's, removed previous workaround + TODO: - fix forced speed/duplexing code (broken a long time ago, when somebody converted the driver to use the generic MII code) - fix VLAN support */ #define DRV_NAME "starfire" -#define DRV_VERSION "1.03+LK1.4.2" -#define DRV_RELDATE "January 19, 2005" +#define DRV_VERSION "1.03+LK1.4.2.1" +#define DRV_RELDATE "October 3, 2005" #include #include @@ -165,6 +169,14 @@ TODO: - fix forced speed/duplexing code (broken a long time ago, when * of length 1. If and when this is fixed, the #define below can be removed. */ #define HAS_BROKEN_FIRMWARE + +/* + * If using the broken firmware, data must be padded to the next 32-bit boundary. + */ +#ifdef HAS_BROKEN_FIRMWARE +#define PADDING_MASK 3 +#endif + /* * Define this if using the driver with the zero-copy patch */ @@ -257,9 +269,10 @@ static int full_duplex[MAX_UNITS] = {0, }; * This SUCKS. * We need a much better method to determine if dma_addr_t is 64-bit. */ -#if (defined(__i386__) && defined(CONFIG_HIGHMEM) && (LINUX_VERSION_CODE > 0x20500 || defined(CONFIG_HIGHMEM64G))) || defined(__x86_64__) || defined (__ia64__) || defined(__mips64__) || (defined(__mips__) && defined(CONFIG_HIGHMEM) && defined(CONFIG_64BIT_PHYS_ADDR)) +#if (defined(__i386__) && defined(CONFIG_HIGHMEM64G)) || defined(__x86_64__) || defined (__ia64__) || defined(__mips64__) || (defined(__mips__) && defined(CONFIG_HIGHMEM) && defined(CONFIG_64BIT_PHYS_ADDR)) /* 64-bit dma_addr_t */ #define ADDR_64BITS /* This chip uses 64 bit addresses. */ +#define netdrv_addr_t u64 #define cpu_to_dma(x) cpu_to_le64(x) #define dma_to_cpu(x) le64_to_cpu(x) #define RX_DESC_Q_ADDR_SIZE RxDescQAddr64bit @@ -268,6 +281,7 @@ static int full_duplex[MAX_UNITS] = {0, }; #define TX_COMPL_Q_ADDR_SIZE TxComplQAddr64bit #define RX_DESC_ADDR_SIZE RxDescAddr64bit #else /* 32-bit dma_addr_t */ +#define netdrv_addr_t u32 #define cpu_to_dma(x) cpu_to_le32(x) #define dma_to_cpu(x) le32_to_cpu(x) #define RX_DESC_Q_ADDR_SIZE RxDescQAddr32bit @@ -1333,21 +1347,10 @@ static int start_tx(struct sk_buff *skb, struct net_device *dev) } #if defined(ZEROCOPY) && defined(HAS_BROKEN_FIRMWARE) - { - int has_bad_length = 0; - - if (skb_first_frag_len(skb) == 1) - has_bad_length = 1; - else { - for (i = 0; i < skb_shinfo(skb)->nr_frags; i++) - if (skb_shinfo(skb)->frags[i].size == 1) { - has_bad_length = 1; - break; - } - } - - if (has_bad_length) - skb_checksum_help(skb, 0); + if (skb->ip_summed == CHECKSUM_HW) { + skb = skb_padto(skb, (skb->len + PADDING_MASK) & ~PADDING_MASK); + if (skb == NULL) + return NETDEV_TX_OK; } #endif /* ZEROCOPY && HAS_BROKEN_FIRMWARE */ @@ -2127,13 +2130,12 @@ static int __init starfire_init (void) #endif #endif -#ifndef ADDR_64BITS /* we can do this test only at run-time... sigh */ - if (sizeof(dma_addr_t) == sizeof(u64)) { - printk("This driver has not been ported to this 64-bit architecture yet\n"); + if (sizeof(dma_addr_t) != sizeof(netdrv_addr_t)) { + printk("This driver has dma_addr_t issues, please send email to maintainer\n"); return -ENODEV; } -#endif /* not ADDR_64BITS */ + return pci_module_init (&starfire_driver); } -- cgit v1.2.3 From f36a29d5672c7698ffe55c7c05107ae77fa698cc Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Mon, 3 Oct 2005 21:24:45 -0700 Subject: [PATCH] ieee80211: fix gfp flags type Fix implicit nocast warnings in ieee80211 code, including __nocast: net/ieee80211/ieee80211_tx.c:215:9: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: Jeff Garzik --- net/ieee80211/ieee80211_tx.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/ieee80211/ieee80211_tx.c b/net/ieee80211/ieee80211_tx.c index f9153671168..ecdf9f7a538 100644 --- a/net/ieee80211/ieee80211_tx.c +++ b/net/ieee80211/ieee80211_tx.c @@ -207,7 +207,7 @@ void ieee80211_txb_free(struct ieee80211_txb *txb) } static struct ieee80211_txb *ieee80211_alloc_txb(int nr_frags, int txb_size, - unsigned int gfp_mask) + unsigned int __nocast gfp_mask) { struct ieee80211_txb *txb; int i; -- cgit v1.2.3 From 81c58732277654a51bb52832e1bc74234bb977bc Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Mon, 3 Oct 2005 21:24:36 -0700 Subject: [PATCH] ns83820: fix gfp flags type Fix implicit nocast warnings in ns83820 code, including __nocast: drivers/net/ns83820.c:603:46: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: Jeff Garzik --- drivers/net/ns83820.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/ns83820.c b/drivers/net/ns83820.c index 1d123d2b53f..83334db2921 100644 --- a/drivers/net/ns83820.c +++ b/drivers/net/ns83820.c @@ -584,7 +584,7 @@ static inline int ns83820_add_rx_skb(struct ns83820 *dev, struct sk_buff *skb) return 0; } -static inline int rx_refill(struct net_device *ndev, unsigned int gfp) +static inline int rx_refill(struct net_device *ndev, unsigned int __nocast gfp) { struct ns83820 *dev = PRIV(ndev); unsigned i; -- cgit v1.2.3 From 832f8f0378ff1566f2a222352c7ad5df3f8d0d9d Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Tue, 4 Oct 2005 00:41:22 -0700 Subject: [PATCH] sungem: fix gfp flags type Fix nocast sparse warnings in sungen: drivers/net/sungem.h:1040:45: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: Jeff Garzik --- drivers/net/sungem.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/net/sungem.h b/drivers/net/sungem.h index ff8ae5f7997..16edbb1a4a7 100644 --- a/drivers/net/sungem.h +++ b/drivers/net/sungem.h @@ -1035,7 +1035,8 @@ struct gem { #define ALIGNED_RX_SKB_ADDR(addr) \ ((((unsigned long)(addr) + (64UL - 1UL)) & ~(64UL - 1UL)) - (unsigned long)(addr)) -static __inline__ struct sk_buff *gem_alloc_skb(int size, int gfp_flags) +static __inline__ struct sk_buff *gem_alloc_skb(int size, + unsigned int __nocast gfp_flags) { struct sk_buff *skb = alloc_skb(size + 64, gfp_flags); -- cgit v1.2.3 From 18efefa9355119b4f6d9b73b074ebbf9882c37c3 Mon Sep 17 00:00:00 2001 From: Anton Altaparmakov Date: Tue, 4 Oct 2005 13:06:00 +0100 Subject: NTFS: Fix a stupid bug in __ntfs_bitmap_set_bits_in_run() which caused the count to become negative and hence we had a wild memset() scribbling all over the system's ram. Signed-off-by: Anton Altaparmakov --- fs/ntfs/ChangeLog | 3 +++ fs/ntfs/bitmap.c | 5 +++-- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/fs/ntfs/ChangeLog b/fs/ntfs/ChangeLog index 83f3322765c..de58579a1d0 100644 --- a/fs/ntfs/ChangeLog +++ b/fs/ntfs/ChangeLog @@ -102,6 +102,9 @@ ToDo/Notes: inode instead of a vfs inode as parameter. - Fix the definition of the CHKD ntfs record magic. It had an off by two error causing it to be CHKB instead of CHKD. + - Fix a stupid bug in __ntfs_bitmap_set_bits_in_run() which caused the + count to become negative and hence we had a wild memset() scribbling + all over the system's ram. 2.1.23 - Implement extension of resident files and make writing safe as well as many bug fixes, cleanups, and enhancements... diff --git a/fs/ntfs/bitmap.c b/fs/ntfs/bitmap.c index 12cf2e30c7d..7a190cdc60e 100644 --- a/fs/ntfs/bitmap.c +++ b/fs/ntfs/bitmap.c @@ -1,7 +1,7 @@ /* * bitmap.c - NTFS kernel bitmap handling. Part of the Linux-NTFS project. * - * Copyright (c) 2004 Anton Altaparmakov + * Copyright (c) 2004-2005 Anton Altaparmakov * * This program/include file is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as published @@ -90,7 +90,8 @@ int __ntfs_bitmap_set_bits_in_run(struct inode *vi, const s64 start_bit, /* If the first byte is partial, modify the appropriate bits in it. */ if (bit) { u8 *byte = kaddr + pos; - while ((bit & 7) && cnt--) { + while ((bit & 7) && cnt) { + cnt--; if (value) *byte |= 1 << bit++; else -- cgit v1.2.3 From c394e458b69632902d65f9e2f39df79314f72908 Mon Sep 17 00:00:00 2001 From: Anton Altaparmakov Date: Tue, 4 Oct 2005 13:08:53 +0100 Subject: NTFS: Fix a 64-bitness bug where a left-shift could overflow a 32-bit variable which we now cast to 64-bit first (fs/ntfs/mft.c::map_mft_record_page(). Signed-off-by: Anton Altaparmakov --- fs/ntfs/layout.h | 2 +- fs/ntfs/mft.c | 3 ++- fs/ntfs/unistr.c | 2 +- 3 files changed, 4 insertions(+), 3 deletions(-) diff --git a/fs/ntfs/layout.h b/fs/ntfs/layout.h index 01f2dfa39ce..5c248d404f0 100644 --- a/fs/ntfs/layout.h +++ b/fs/ntfs/layout.h @@ -309,7 +309,7 @@ typedef le16 MFT_RECORD_FLAGS; * Note: The _LE versions will return a CPU endian formatted value! */ #define MFT_REF_MASK_CPU 0x0000ffffffffffffULL -#define MFT_REF_MASK_LE const_cpu_to_le64(0x0000ffffffffffffULL) +#define MFT_REF_MASK_LE const_cpu_to_le64(MFT_REF_MASK_CPU) typedef u64 MFT_REF; typedef le64 leMFT_REF; diff --git a/fs/ntfs/mft.c b/fs/ntfs/mft.c index 247586d1d5d..b011369b595 100644 --- a/fs/ntfs/mft.c +++ b/fs/ntfs/mft.c @@ -58,7 +58,8 @@ static inline MFT_RECORD *map_mft_record_page(ntfs_inode *ni) * overflowing the unsigned long, but I don't think we would ever get * here if the volume was that big... */ - index = ni->mft_no << vol->mft_record_size_bits >> PAGE_CACHE_SHIFT; + index = (u64)ni->mft_no << vol->mft_record_size_bits >> + PAGE_CACHE_SHIFT; ofs = (ni->mft_no << vol->mft_record_size_bits) & ~PAGE_CACHE_MASK; i_size = i_size_read(mft_vi); diff --git a/fs/ntfs/unistr.c b/fs/ntfs/unistr.c index a389a5a16c8..0ea887fc859 100644 --- a/fs/ntfs/unistr.c +++ b/fs/ntfs/unistr.c @@ -1,7 +1,7 @@ /* * unistr.c - NTFS Unicode string handling. Part of the Linux-NTFS project. * - * Copyright (c) 2001-2004 Anton Altaparmakov + * Copyright (c) 2001-2005 Anton Altaparmakov * * This program/include file is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as published -- cgit v1.2.3 From 87bf9c97b4b3af8dec7b2b79cdfe7bfc0a0a03b2 Mon Sep 17 00:00:00 2001 From: YOSHIFUJI Hideaki Date: Tue, 4 Oct 2005 13:00:39 -0700 Subject: [IPV6]: Fix infinite loop in udp_v6_get_port(). Signed-off-by: YOSHIFUJI Hideaki Signed-off-by: David S. Miller --- net/ipv6/udp.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/net/ipv6/udp.c b/net/ipv6/udp.c index e4cad11f284..bf9519341fd 100644 --- a/net/ipv6/udp.c +++ b/net/ipv6/udp.c @@ -99,7 +99,7 @@ static int udp_v6_get_port(struct sock *sk, unsigned short snum) next:; } result = best; - for(;; result += UDP_HTABLE_SIZE) { + for(i = 0; i < (1 << 16) / UDP_HTABLE_SIZE; i++, result += UDP_HTABLE_SIZE) { if (result > sysctl_local_port_range[1]) result = sysctl_local_port_range[0] + ((result - sysctl_local_port_range[0]) & @@ -107,6 +107,8 @@ static int udp_v6_get_port(struct sock *sk, unsigned short snum) if (!udp_lport_inuse(result)) break; } + if (i >= (1 << 16) / UDP_HTABLE_SIZE) + goto fail; gotit: udp_port_rover = snum = result; } else { -- cgit v1.2.3 From e6308be85afee685347fa3440bed10faaa5d6c1a Mon Sep 17 00:00:00 2001 From: Robert Olsson Date: Tue, 4 Oct 2005 13:01:58 -0700 Subject: [IPV4]: fib_trie root-node expansion The patch below introduces special thresholds to keep root node in the trie large. This gives a flatter tree at the cost of a modest memory increase. Overall it seems to be gain and this was also proposed by one the authors of the paper in recent a seminar. Main table after loading 123 k routes. Aver depth: 3.30 Max depth: 9 Root-node size 12 bits Total size: 4044 kB With the patch: Aver depth: 2.78 Max depth: 8 Root-node size 15 bits Total size: 4150 kB An increase of 8-10% was seen in forwading performance for an rDoS attack. Signed-off-by: Robert Olsson Signed-off-by: David S. Miller --- net/ipv4/fib_trie.c | 23 +++++++++++++++++++++-- 1 file changed, 21 insertions(+), 2 deletions(-) diff --git a/net/ipv4/fib_trie.c b/net/ipv4/fib_trie.c index 50c0519cd70..0093ea08c7f 100644 --- a/net/ipv4/fib_trie.c +++ b/net/ipv4/fib_trie.c @@ -286,6 +286,8 @@ static inline void check_tnode(const struct tnode *tn) static int halve_threshold = 25; static int inflate_threshold = 50; +static int halve_threshold_root = 15; +static int inflate_threshold_root = 25; static void __alias_free_mem(struct rcu_head *head) @@ -449,6 +451,8 @@ static struct node *resize(struct trie *t, struct tnode *tn) int i; int err = 0; struct tnode *old_tn; + int inflate_threshold_use; + int halve_threshold_use; if (!tn) return NULL; @@ -541,10 +545,17 @@ static struct node *resize(struct trie *t, struct tnode *tn) check_tnode(tn); + /* Keep root node larger */ + + if(!tn->parent) + inflate_threshold_use = inflate_threshold_root; + else + inflate_threshold_use = inflate_threshold; + err = 0; while ((tn->full_children > 0 && 50 * (tn->full_children + tnode_child_length(tn) - tn->empty_children) >= - inflate_threshold * tnode_child_length(tn))) { + inflate_threshold_use * tnode_child_length(tn))) { old_tn = tn; tn = inflate(t, tn); @@ -564,10 +575,18 @@ static struct node *resize(struct trie *t, struct tnode *tn) * node is above threshold. */ + + /* Keep root node larger */ + + if(!tn->parent) + halve_threshold_use = halve_threshold_root; + else + halve_threshold_use = halve_threshold; + err = 0; while (tn->bits > 1 && 100 * (tnode_child_length(tn) - tn->empty_children) < - halve_threshold * tnode_child_length(tn)) { + halve_threshold_use * tnode_child_length(tn)) { old_tn = tn; tn = halve(t, tn); -- cgit v1.2.3 From 433992361ce95a1da76b76c9c24d4c957b058aff Mon Sep 17 00:00:00 2001 From: Al Viro Date: Tue, 4 Oct 2005 17:36:04 +0100 Subject: [PATCH] missing include in megaraid_sas megaraid_sas depends on arch-specific indirect includes pulling fs.h in; on alpha they do not. Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- drivers/scsi/megaraid/megaraid_sas.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/scsi/megaraid/megaraid_sas.c b/drivers/scsi/megaraid/megaraid_sas.c index 1b3148e842a..c3f63739573 100644 --- a/drivers/scsi/megaraid/megaraid_sas.c +++ b/drivers/scsi/megaraid/megaraid_sas.c @@ -34,6 +34,7 @@ #include #include #include +#include #include #include -- cgit v1.2.3 From 25e2d79f527b7abce624f30516f3167195b69a2e Mon Sep 17 00:00:00 2001 From: Al Viro Date: Tue, 4 Oct 2005 17:40:44 +0100 Subject: [PATCH] bogus kfree() in ibmtr On several failure exits in ibmtr we end up doing kfree() on dev->priv, with dev allocated by alloc_trdev() and ->priv never reassigned. Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- drivers/net/tokenring/ibmtr.c | 5 ----- 1 file changed, 5 deletions(-) diff --git a/drivers/net/tokenring/ibmtr.c b/drivers/net/tokenring/ibmtr.c index e7b001017b9..32057e65808 100644 --- a/drivers/net/tokenring/ibmtr.c +++ b/drivers/net/tokenring/ibmtr.c @@ -531,7 +531,6 @@ static int __devinit ibmtr_probe1(struct net_device *dev, int PIOaddr) if (!time_after(jiffies, timeout)) continue; DPRINTK( "Hardware timeout during initialization.\n"); iounmap(t_mmio); - kfree(ti); return -ENODEV; } ti->sram_phys = @@ -645,7 +644,6 @@ static int __devinit ibmtr_probe1(struct net_device *dev, int PIOaddr) DPRINTK("Unknown shared ram paging info %01X\n", ti->shared_ram_paging); iounmap(t_mmio); - kfree(ti); return -ENODEV; break; } /*end switch shared_ram_paging */ @@ -675,7 +673,6 @@ static int __devinit ibmtr_probe1(struct net_device *dev, int PIOaddr) "driver limit (%05x), adapter not started.\n", chk_base, ibmtr_mem_base + IBMTR_SHARED_RAM_SIZE); iounmap(t_mmio); - kfree(ti); return -ENODEV; } else { /* seems cool, record what we have figured out */ ti->sram_base = new_base >> 12; @@ -690,7 +687,6 @@ static int __devinit ibmtr_probe1(struct net_device *dev, int PIOaddr) DPRINTK("Could not grab irq %d. Halting Token Ring driver.\n", irq); iounmap(t_mmio); - kfree(ti); return -ENODEV; } /*?? Now, allocate some of the PIO PORTs for this driver.. */ @@ -699,7 +695,6 @@ static int __devinit ibmtr_probe1(struct net_device *dev, int PIOaddr) DPRINTK("Could not grab PIO range. Halting driver.\n"); free_irq(dev->irq, dev); iounmap(t_mmio); - kfree(ti); return -EBUSY; } -- cgit v1.2.3 From ce0fe7e70a0ad11097a3773e9f3f0de3d859edf0 Mon Sep 17 00:00:00 2001 From: Alexey Dobriyan Date: Tue, 4 Oct 2005 17:43:06 +0100 Subject: [PATCH] bfs endianness annotations Signed-off-by: Alexey Dobriyan Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- fs/bfs/dir.c | 2 +- fs/bfs/inode.c | 2 +- include/linux/bfs_fs.h | 42 +++++++++++++++++++++--------------------- 3 files changed, 23 insertions(+), 23 deletions(-) diff --git a/fs/bfs/dir.c b/fs/bfs/dir.c index e240c335eb2..5af928fa044 100644 --- a/fs/bfs/dir.c +++ b/fs/bfs/dir.c @@ -108,7 +108,7 @@ static int bfs_create(struct inode * dir, struct dentry * dentry, int mode, inode->i_mapping->a_ops = &bfs_aops; inode->i_mode = mode; inode->i_ino = ino; - BFS_I(inode)->i_dsk_ino = cpu_to_le16(ino); + BFS_I(inode)->i_dsk_ino = ino; BFS_I(inode)->i_sblock = 0; BFS_I(inode)->i_eblock = 0; insert_inode_hash(inode); diff --git a/fs/bfs/inode.c b/fs/bfs/inode.c index c7b39aa279d..868af0f224f 100644 --- a/fs/bfs/inode.c +++ b/fs/bfs/inode.c @@ -357,7 +357,7 @@ static int bfs_fill_super(struct super_block *s, void *data, int silent) } info->si_blocks = (le32_to_cpu(bfs_sb->s_end) + 1)>>BFS_BSIZE_BITS; /* for statfs(2) */ - info->si_freeb = (le32_to_cpu(bfs_sb->s_end) + 1 - cpu_to_le32(bfs_sb->s_start))>>BFS_BSIZE_BITS; + info->si_freeb = (le32_to_cpu(bfs_sb->s_end) + 1 - le32_to_cpu(bfs_sb->s_start))>>BFS_BSIZE_BITS; info->si_freei = 0; info->si_lf_eblk = 0; info->si_lf_sblk = 0; diff --git a/include/linux/bfs_fs.h b/include/linux/bfs_fs.h index c1237aa92e3..8ed6dfdcd78 100644 --- a/include/linux/bfs_fs.h +++ b/include/linux/bfs_fs.h @@ -20,19 +20,19 @@ /* BFS inode layout on disk */ struct bfs_inode { - __u16 i_ino; + __le16 i_ino; __u16 i_unused; - __u32 i_sblock; - __u32 i_eblock; - __u32 i_eoffset; - __u32 i_vtype; - __u32 i_mode; - __s32 i_uid; - __s32 i_gid; - __u32 i_nlink; - __u32 i_atime; - __u32 i_mtime; - __u32 i_ctime; + __le32 i_sblock; + __le32 i_eblock; + __le32 i_eoffset; + __le32 i_vtype; + __le32 i_mode; + __le32 i_uid; + __le32 i_gid; + __le32 i_nlink; + __le32 i_atime; + __le32 i_mtime; + __le32 i_ctime; __u32 i_padding[4]; }; @@ -41,17 +41,17 @@ struct bfs_inode { #define BFS_DIRS_PER_BLOCK 32 struct bfs_dirent { - __u16 ino; + __le16 ino; char name[BFS_NAMELEN]; }; /* BFS superblock layout on disk */ struct bfs_super_block { - __u32 s_magic; - __u32 s_start; - __u32 s_end; - __s32 s_from; - __s32 s_to; + __le32 s_magic; + __le32 s_start; + __le32 s_end; + __le32 s_from; + __le32 s_to; __s32 s_bfrom; __s32 s_bto; char s_fsname[6]; @@ -66,15 +66,15 @@ struct bfs_super_block { #define BFS_INO2OFF(ino) \ ((__u32)(((ino) - BFS_ROOT_INO) * sizeof(struct bfs_inode)) + BFS_BSIZE) #define BFS_NZFILESIZE(ip) \ - ((cpu_to_le32((ip)->i_eoffset) + 1) - cpu_to_le32((ip)->i_sblock) * BFS_BSIZE) + ((le32_to_cpu((ip)->i_eoffset) + 1) - le32_to_cpu((ip)->i_sblock) * BFS_BSIZE) #define BFS_FILESIZE(ip) \ ((ip)->i_sblock == 0 ? 0 : BFS_NZFILESIZE(ip)) #define BFS_FILEBLOCKS(ip) \ - ((ip)->i_sblock == 0 ? 0 : (cpu_to_le32((ip)->i_eblock) + 1) - cpu_to_le32((ip)->i_sblock)) + ((ip)->i_sblock == 0 ? 0 : (le32_to_cpu((ip)->i_eblock) + 1) - le32_to_cpu((ip)->i_sblock)) #define BFS_UNCLEAN(bfs_sb, sb) \ - ((cpu_to_le32(bfs_sb->s_from) != -1) && (cpu_to_le32(bfs_sb->s_to) != -1) && !(sb->s_flags & MS_RDONLY)) + ((le32_to_cpu(bfs_sb->s_from) != -1) && (le32_to_cpu(bfs_sb->s_to) != -1) && !(sb->s_flags & MS_RDONLY)) #endif /* _LINUX_BFS_FS_H */ -- cgit v1.2.3 From c2b513dfbb04d7c94cca145172cfeb91f7683e54 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Tue, 4 Oct 2005 17:48:44 +0100 Subject: [PATCH] bfs iget() abuses bfs_fill_super() walks the inode table to get the bitmap of free inodes and collect stats. It has no business using iget() for that - it's a lot of extra work, extra icache pollution and more complex code. Switched to walking the damn thing directly. Note: that also allows to kill ->i_dsk_ino in there - separate patch if Tigran can confirm that this field can be zero only for deleted inodes (i.e. something that could only be found during that scan and not by normal lookups). Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- fs/bfs/inode.c | 42 ++++++++++++++++++++++++++++++------------ 1 file changed, 30 insertions(+), 12 deletions(-) diff --git a/fs/bfs/inode.c b/fs/bfs/inode.c index 868af0f224f..3af6c73c5b5 100644 --- a/fs/bfs/inode.c +++ b/fs/bfs/inode.c @@ -362,23 +362,41 @@ static int bfs_fill_super(struct super_block *s, void *data, int silent) info->si_lf_eblk = 0; info->si_lf_sblk = 0; info->si_lf_ioff = 0; + bh = NULL; for (i=BFS_ROOT_INO; i<=info->si_lasti; i++) { - inode = iget(s,i); - if (BFS_I(inode)->i_dsk_ino == 0) + struct bfs_inode *di; + int block = (i - BFS_ROOT_INO)/BFS_INODES_PER_BLOCK + 1; + int off = (i - BFS_ROOT_INO) % BFS_INODES_PER_BLOCK; + unsigned long sblock, eblock; + + if (!off) { + brelse(bh); + bh = sb_bread(s, block); + } + + if (!bh) + continue; + + di = (struct bfs_inode *)bh->b_data + off; + + if (!di->i_ino) { info->si_freei++; - else { - set_bit(i, info->si_imap); - info->si_freeb -= inode->i_blocks; - if (BFS_I(inode)->i_eblock > info->si_lf_eblk) { - info->si_lf_eblk = BFS_I(inode)->i_eblock; - info->si_lf_sblk = BFS_I(inode)->i_sblock; - info->si_lf_ioff = BFS_INO2OFF(i); - } + continue; + } + set_bit(i, info->si_imap); + info->si_freeb -= BFS_FILEBLOCKS(di); + + sblock = le32_to_cpu(di->i_sblock); + eblock = le32_to_cpu(di->i_eblock); + if (eblock > info->si_lf_eblk) { + info->si_lf_eblk = eblock; + info->si_lf_sblk = sblock; + info->si_lf_ioff = BFS_INO2OFF(i); } - iput(inode); } + brelse(bh); if (!(s->s_flags & MS_RDONLY)) { - mark_buffer_dirty(bh); + mark_buffer_dirty(info->si_sbh); s->s_dirt = 1; } dump_imap("read_super", s); -- cgit v1.2.3 From 71dc036247573e377703233af289019f4aa3176e Mon Sep 17 00:00:00 2001 From: Jeff Dike Date: Tue, 4 Oct 2005 14:53:49 -0400 Subject: [PATCH] UML - Fix Al's build tidying Al's build tidying missed one bit from me - without this UML doesn't boot. Signed-off-by: Jeff Dike Acked-by: Al Viro Signed-off-by: Linus Torvalds --- arch/um/sys-i386/user-offsets.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/um/sys-i386/user-offsets.c b/arch/um/sys-i386/user-offsets.c index 677fc26a9bb..26b68675053 100644 --- a/arch/um/sys-i386/user-offsets.c +++ b/arch/um/sys-i386/user-offsets.c @@ -46,7 +46,7 @@ void foo(void) OFFSET(HOST_SC_FP_ST, _fpstate, _st); OFFSET(HOST_SC_FXSR_ENV, _fpstate, _fxsr_env); - DEFINE_LONGS(HOST_FRAME_SIZE, FRAME_SIZE); + DEFINE(HOST_FRAME_SIZE, FRAME_SIZE); DEFINE_LONGS(HOST_FP_SIZE, sizeof(struct user_i387_struct)); DEFINE_LONGS(HOST_XFP_SIZE, sizeof(struct user_fxsr_struct)); -- cgit v1.2.3 From fad1c45c939bb246a488be1fa06f539e85b80545 Mon Sep 17 00:00:00 2001 From: Allan Graves Date: Tue, 4 Oct 2005 14:53:52 -0400 Subject: [PATCH] uml: Fix sysrq-r support for skas mode The old code had the IP and SP coming from the registers in the thread struct, which are completely wrong since those are the userspace registers. This fixes that by pulling the correct values from the jmp_buf in which the kernel state of each thread is stored. Signed-off-by: Allan Graves Signed-off-by: Jeff Dike Signed-off-by: Linus Torvalds --- arch/um/include/registers.h | 12 +----------- arch/um/include/sysdep-x86_64/ptrace.h | 4 ---- arch/um/kernel/sysrq.c | 8 +------- arch/um/os-Linux/sys-i386/registers.c | 19 +++++++++---------- arch/um/os-Linux/sys-x86_64/registers.c | 19 +++++++++---------- arch/um/sys-i386/sysrq.c | 13 +------------ include/asm-um/processor-generic.h | 23 ++++++++++------------- include/asm-um/processor-i386.h | 15 ++++----------- include/asm-um/processor-x86_64.h | 14 +++----------- 9 files changed, 38 insertions(+), 89 deletions(-) diff --git a/arch/um/include/registers.h b/arch/um/include/registers.h index 0a35e6d0baa..4892e5fcef0 100644 --- a/arch/um/include/registers.h +++ b/arch/um/include/registers.h @@ -15,16 +15,6 @@ extern void save_registers(int pid, union uml_pt_regs *regs); extern void restore_registers(int pid, union uml_pt_regs *regs); extern void init_registers(int pid); extern void get_safe_registers(unsigned long * regs); +extern void get_thread_regs(union uml_pt_regs *uml_regs, void *buffer); #endif - -/* - * Overrides for Emacs so that we follow Linus's tabbing style. - * Emacs will notice this stuff at the end of the file and automatically - * adjust the settings for this buffer only. This must remain at the end - * of the file. - * --------------------------------------------------------------------------- - * Local variables: - * c-file-style: "linux" - * End: - */ diff --git a/arch/um/include/sysdep-x86_64/ptrace.h b/arch/um/include/sysdep-x86_64/ptrace.h index 331aa2d1f3f..8f0656766c2 100644 --- a/arch/um/include/sysdep-x86_64/ptrace.h +++ b/arch/um/include/sysdep-x86_64/ptrace.h @@ -218,10 +218,6 @@ struct syscall_args { case RBP: UPT_RBP(regs) = __upt_val; break; \ case ORIG_RAX: UPT_ORIG_RAX(regs) = __upt_val; break; \ case CS: UPT_CS(regs) = __upt_val; break; \ - case DS: UPT_DS(regs) = __upt_val; break; \ - case ES: UPT_ES(regs) = __upt_val; break; \ - case FS: UPT_FS(regs) = __upt_val; break; \ - case GS: UPT_GS(regs) = __upt_val; break; \ case EFLAGS: UPT_EFLAGS(regs) = __upt_val; break; \ default : \ panic("Bad register in UPT_SET : %d\n", reg); \ diff --git a/arch/um/kernel/sysrq.c b/arch/um/kernel/sysrq.c index f80850091e7..b331e970002 100644 --- a/arch/um/kernel/sysrq.c +++ b/arch/um/kernel/sysrq.c @@ -62,13 +62,7 @@ void show_stack(struct task_struct *task, unsigned long *esp) if (esp == NULL) { if (task != current && task != NULL) { - /* XXX: Isn't this bogus? I.e. isn't this the - * *userspace* stack of this task? If not so, use this - * even when task == current (as in i386). - */ esp = (unsigned long *) KSTK_ESP(task); - /* Which one? No actual difference - just coding style.*/ - //esp = (unsigned long *) PT_REGS_IP(&task->thread.regs); } else { esp = (unsigned long *) &esp; } @@ -84,5 +78,5 @@ void show_stack(struct task_struct *task, unsigned long *esp) } printk("Call Trace: \n"); - show_trace(current, esp); + show_trace(task, esp); } diff --git a/arch/um/os-Linux/sys-i386/registers.c b/arch/um/os-Linux/sys-i386/registers.c index 3125d320722..aee4812333c 100644 --- a/arch/um/os-Linux/sys-i386/registers.c +++ b/arch/um/os-Linux/sys-i386/registers.c @@ -5,6 +5,7 @@ #include #include +#include #include "sysdep/ptrace_user.h" #include "sysdep/ptrace.h" #include "uml-config.h" @@ -126,13 +127,11 @@ void get_safe_registers(unsigned long *regs) memcpy(regs, exec_regs, HOST_FRAME_SIZE * sizeof(unsigned long)); } -/* - * Overrides for Emacs so that we follow Linus's tabbing style. - * Emacs will notice this stuff at the end of the file and automatically - * adjust the settings for this buffer only. This must remain at the end - * of the file. - * --------------------------------------------------------------------------- - * Local variables: - * c-file-style: "linux" - * End: - */ +void get_thread_regs(union uml_pt_regs *uml_regs, void *buffer) +{ + struct __jmp_buf_tag *jmpbuf = buffer; + + UPT_SET(uml_regs, EIP, jmpbuf->__jmpbuf[JB_PC]); + UPT_SET(uml_regs, UESP, jmpbuf->__jmpbuf[JB_SP]); + UPT_SET(uml_regs, EBP, jmpbuf->__jmpbuf[JB_BP]); +} diff --git a/arch/um/os-Linux/sys-x86_64/registers.c b/arch/um/os-Linux/sys-x86_64/registers.c index 44438d15c3d..4b638dfb52b 100644 --- a/arch/um/os-Linux/sys-x86_64/registers.c +++ b/arch/um/os-Linux/sys-x86_64/registers.c @@ -5,6 +5,7 @@ #include #include +#include #include "ptrace_user.h" #include "uml-config.h" #include "skas_ptregs.h" @@ -74,13 +75,11 @@ void get_safe_registers(unsigned long *regs) memcpy(regs, exec_regs, HOST_FRAME_SIZE * sizeof(unsigned long)); } -/* - * Overrides for Emacs so that we follow Linus's tabbing style. - * Emacs will notice this stuff at the end of the file and automatically - * adjust the settings for this buffer only. This must remain at the end - * of the file. - * --------------------------------------------------------------------------- - * Local variables: - * c-file-style: "linux" - * End: - */ +void get_thread_regs(union uml_pt_regs *uml_regs, void *buffer) +{ + struct __jmp_buf_tag *jmpbuf = buffer; + + UPT_SET(uml_regs, RIP, jmpbuf->__jmpbuf[JB_PC]); + UPT_SET(uml_regs, RSP, jmpbuf->__jmpbuf[JB_RSP]); + UPT_SET(uml_regs, RBP, jmpbuf->__jmpbuf[JB_RBP]); +} diff --git a/arch/um/sys-i386/sysrq.c b/arch/um/sys-i386/sysrq.c index e3706d15c4f..d5244f07053 100644 --- a/arch/um/sys-i386/sysrq.c +++ b/arch/um/sys-i386/sysrq.c @@ -88,9 +88,7 @@ void show_trace(struct task_struct* task, unsigned long * stack) task = current; if (task != current) { - //ebp = (unsigned long) KSTK_EBP(task); - /* Which one? No actual difference - just coding style.*/ - ebp = (unsigned long) PT_REGS_EBP(&task->thread.regs); + ebp = (unsigned long) KSTK_EBP(task); } else { asm ("movl %%ebp, %0" : "=r" (ebp) : ); } @@ -99,15 +97,6 @@ void show_trace(struct task_struct* task, unsigned long * stack) ((unsigned long)stack & (~(THREAD_SIZE - 1))); print_context_stack(context, stack, ebp); - /*while (((long) stack & (THREAD_SIZE-1)) != 0) { - addr = *stack; - if (__kernel_text_address(addr)) { - printk("%08lx: [<%08lx>]", (unsigned long) stack, addr); - print_symbol(" %s", addr); - printk("\n"); - } - stack++; - }*/ printk("\n"); } diff --git a/include/asm-um/processor-generic.h b/include/asm-um/processor-generic.h index 2d242360c3d..075771c371f 100644 --- a/include/asm-um/processor-generic.h +++ b/include/asm-um/processor-generic.h @@ -13,6 +13,7 @@ struct task_struct; #include "linux/config.h" #include "asm/ptrace.h" #include "choose-mode.h" +#include "registers.h" struct mm_struct; @@ -136,19 +137,15 @@ extern struct cpuinfo_um cpu_data[]; #define current_cpu_data boot_cpu_data #endif -#define KSTK_EIP(tsk) (PT_REGS_IP(&tsk->thread.regs)) -#define KSTK_ESP(tsk) (PT_REGS_SP(&tsk->thread.regs)) -#define get_wchan(p) (0) +#ifdef CONFIG_MODE_SKAS +#define KSTK_REG(tsk, reg) \ + ({ union uml_pt_regs regs; \ + get_thread_regs(®s, tsk->thread.mode.skas.switch_buf); \ + UPT_REG(®s, reg); }) +#else +#define KSTK_REG(tsk, reg) (0xbadbabe) #endif +#define get_wchan(p) (0) -/* - * Overrides for Emacs so that we follow Linus's tabbing style. - * Emacs will notice this stuff at the end of the file and automatically - * adjust the settings for this buffer only. This must remain at the end - * of the file. - * --------------------------------------------------------------------------- - * Local variables: - * c-file-style: "linux" - * End: - */ +#endif diff --git a/include/asm-um/processor-i386.h b/include/asm-um/processor-i386.h index 431bad3ae9d..4108a579eb9 100644 --- a/include/asm-um/processor-i386.h +++ b/include/asm-um/processor-i386.h @@ -43,17 +43,10 @@ static inline void rep_nop(void) #define ARCH_IS_STACKGROW(address) \ (address + 32 >= UPT_SP(¤t->thread.regs.regs)) +#define KSTK_EIP(tsk) KSTK_REG(tsk, EIP) +#define KSTK_ESP(tsk) KSTK_REG(tsk, UESP) +#define KSTK_EBP(tsk) KSTK_REG(tsk, EBP) + #include "asm/processor-generic.h" #endif - -/* - * Overrides for Emacs so that we follow Linus's tabbing style. - * Emacs will notice this stuff at the end of the file and automatically - * adjust the settings for this buffer only. This must remain at the end - * of the file. - * --------------------------------------------------------------------------- - * Local variables: - * c-file-style: "linux" - * End: - */ diff --git a/include/asm-um/processor-x86_64.h b/include/asm-um/processor-x86_64.h index 0beb9a42ae0..e1e1255a1d3 100644 --- a/include/asm-um/processor-x86_64.h +++ b/include/asm-um/processor-x86_64.h @@ -36,17 +36,9 @@ extern inline void rep_nop(void) #define ARCH_IS_STACKGROW(address) \ (address + 128 >= UPT_SP(¤t->thread.regs.regs)) +#define KSTK_EIP(tsk) KSTK_REG(tsk, RIP) +#define KSTK_ESP(tsk) KSTK_REG(tsk, RSP) + #include "asm/processor-generic.h" #endif - -/* - * Overrides for Emacs so that we follow Linus's tabbing style. - * Emacs will notice this stuff at the end of the file and automatically - * adjust the settings for this buffer only. This must remain at the end - * of the file. - * --------------------------------------------------------------------------- - * Local variables: - * c-file-style: "linux" - * End: - */ -- cgit v1.2.3 From d78795b6930956fb66238d4d26242482d4a31470 Mon Sep 17 00:00:00 2001 From: Sascha Hauer Date: Tue, 4 Oct 2005 23:17:51 +0100 Subject: [ARM] 2949/1: Hynix h720x Run mode Patch from Sascha Hauer After coming out of idle mode the h720x goes into slow mode. Switch it back to run mode. Signed-off-by: Sascha Hauer Signed-off-by: Russell King --- include/asm-arm/arch-h720x/system.h | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/include/asm-arm/arch-h720x/system.h b/include/asm-arm/arch-h720x/system.h index 0b025e227ec..09eda84592f 100644 --- a/include/asm-arm/arch-h720x/system.h +++ b/include/asm-arm/arch-h720x/system.h @@ -17,9 +17,11 @@ static void arch_idle(void) { CPU_REG (PMU_BASE, PMU_MODE) = PMU_MODE_IDLE; - __asm__ __volatile__( - "mov r0, r0\n\t" - "mov r0, r0"); + nop(); + nop(); + CPU_REG (PMU_BASE, PMU_MODE) = PMU_MODE_RUN; + nop(); + nop(); } -- cgit v1.2.3 From 0a5b0aa8a331f4346b4b02bc653107304a6abdc5 Mon Sep 17 00:00:00 2001 From: Sascha Hauer Date: Tue, 4 Oct 2005 23:17:52 +0100 Subject: [ARM] 2950/1: i.MX gpio setup function Patch from Sascha Hauer Current implementation of imx_gpio_mode does not allow to configure all alternate routing possibilities of the i.MX. With this patch every bit in the gpio setup registers has a corresponding bit in the gpio_mode parameter, so every routing should be possible now. Signed-off-by: Sascha Hauer Signed-off-by: Russell King --- arch/arm/mach-imx/generic.c | 23 ++++++++++--------- arch/arm/mach-imx/mx1ads.c | 2 +- include/asm-arm/arch-imx/imx-regs.h | 46 +++++++++++++++++++++++++++---------- 3 files changed, 47 insertions(+), 24 deletions(-) diff --git a/arch/arm/mach-imx/generic.c b/arch/arm/mach-imx/generic.c index 41e5849ae8d..f8a742bb2d5 100644 --- a/arch/arm/mach-imx/generic.c +++ b/arch/arm/mach-imx/generic.c @@ -28,14 +28,15 @@ #include #include #include +#include #include void imx_gpio_mode(int gpio_mode) { unsigned int pin = gpio_mode & GPIO_PIN_MASK; - unsigned int port = (gpio_mode & GPIO_PORT_MASK) >> 5; - unsigned int ocr = (gpio_mode & GPIO_OCR_MASK) >> 10; + unsigned int port = (gpio_mode & GPIO_PORT_MASK) >> GPIO_PORT_SHIFT; + unsigned int ocr = (gpio_mode & GPIO_OCR_MASK) >> GPIO_OCR_SHIFT; unsigned int tmp; /* Pullup enable */ @@ -57,7 +58,7 @@ void imx_gpio_mode(int gpio_mode) GPR(port) &= ~(1<> GPIO_AOUT_SHIFT) & 3) << (pin * 2); + ICONFB1(port) &= ~( 3<<(pin*2)); + ICONFB1(port) |= ((gpio_mode >> GPIO_BOUT_SHIFT) & 3) << (pin * 2); } else { tmp = OCR2(port); tmp &= ~( 3<<((pin-16)*2)); tmp |= (ocr << ((pin-16)*2)); OCR2(port) = tmp; - if( gpio_mode & GPIO_AOUT ) - ICONFA2(port) &= ~( 3<<((pin-16)*2)); - if( gpio_mode & GPIO_BOUT ) - ICONFB2(port) &= ~( 3<<((pin-16)*2)); + ICONFA2(port) &= ~( 3<<((pin-16)*2)); + ICONFA2(port) |= ((gpio_mode >> GPIO_AOUT_SHIFT) & 3) << ((pin-16) * 2); + ICONFB2(port) &= ~( 3<<((pin-16)*2)); + ICONFB2(port) |= ((gpio_mode >> GPIO_BOUT_SHIFT) & 3) << ((pin-16) * 2); } } diff --git a/arch/arm/mach-imx/mx1ads.c b/arch/arm/mach-imx/mx1ads.c index 5d25434d332..a7511ddfe36 100644 --- a/arch/arm/mach-imx/mx1ads.c +++ b/arch/arm/mach-imx/mx1ads.c @@ -55,7 +55,7 @@ static void __init mx1ads_init(void) { #ifdef CONFIG_LEDS - imx_gpio_mode(GPIO_PORTA | GPIO_OUT | GPIO_GPIO | 2); + imx_gpio_mode(GPIO_PORTA | GPIO_OUT | 2); #endif platform_add_devices(devices, ARRAY_SIZE(devices)); } diff --git a/include/asm-arm/arch-imx/imx-regs.h b/include/asm-arm/arch-imx/imx-regs.h index 93b840e8fa6..229f7008d74 100644 --- a/include/asm-arm/arch-imx/imx-regs.h +++ b/include/asm-arm/arch-imx/imx-regs.h @@ -76,6 +76,7 @@ #define GPIO_PIN_MASK 0x1f #define GPIO_PORT_MASK (0x3 << 5) +#define GPIO_PORT_SHIFT 5 #define GPIO_PORTA (0<<5) #define GPIO_PORTB (1<<5) #define GPIO_PORTC (2<<5) @@ -88,24 +89,37 @@ #define GPIO_PF (0<<9) #define GPIO_AF (1<<9) +#define GPIO_OCR_SHIFT 10 #define GPIO_OCR_MASK (3<<10) #define GPIO_AIN (0<<10) #define GPIO_BIN (1<<10) #define GPIO_CIN (2<<10) -#define GPIO_GPIO (3<<10) +#define GPIO_DR (3<<10) -#define GPIO_AOUT (1<<12) -#define GPIO_BOUT (1<<13) +#define GPIO_AOUT_SHIFT 12 +#define GPIO_AOUT_MASK (3<<12) +#define GPIO_AOUT (0<<12) +#define GPIO_AOUT_ISR (1<<12) +#define GPIO_AOUT_0 (2<<12) +#define GPIO_AOUT_1 (3<<12) + +#define GPIO_BOUT_SHIFT 14 +#define GPIO_BOUT_MASK (3<<14) +#define GPIO_BOUT (0<<14) +#define GPIO_BOUT_ISR (1<<14) +#define GPIO_BOUT_0 (2<<14) +#define GPIO_BOUT_1 (3<<14) + +#define GPIO_GIUS (1<<16) /* assignements for GPIO alternate/primary functions */ /* FIXME: This list is not completed. The correct directions are * missing on some (many) pins */ -#define PA0_PF_A24 ( GPIO_PORTA | GPIO_PF | 0 ) -#define PA0_AIN_SPI2_CLK ( GPIO_PORTA | GPIO_OUT | GPIO_AIN | 0 ) +#define PA0_AIN_SPI2_CLK ( GPIO_GIUS | GPIO_PORTA | GPIO_OUT | 0 ) #define PA0_AF_ETMTRACESYNC ( GPIO_PORTA | GPIO_AF | 0 ) -#define PA1_AOUT_SPI2_RXD ( GPIO_PORTA | GPIO_IN | GPIO_AOUT | 1 ) +#define PA1_AOUT_SPI2_RXD ( GPIO_GIUS | GPIO_PORTA | GPIO_IN | 1 ) #define PA1_PF_TIN ( GPIO_PORTA | GPIO_PF | 1 ) #define PA2_PF_PWM0 ( GPIO_PORTA | GPIO_OUT | GPIO_PF | 2 ) #define PA3_PF_CSI_MCLK ( GPIO_PORTA | GPIO_PF | 3 ) @@ -123,7 +137,7 @@ #define PA15_PF_I2C_SDA ( GPIO_PORTA | GPIO_OUT | GPIO_PF | 15 ) #define PA16_PF_I2C_SCL ( GPIO_PORTA | GPIO_OUT | GPIO_PF | 16 ) #define PA17_AF_ETMTRACEPKT4 ( GPIO_PORTA | GPIO_AF | 17 ) -#define PA17_AIN_SPI2_SS ( GPIO_PORTA | GPIO_AIN | 17 ) +#define PA17_AIN_SPI2_SS ( GPIO_GIUS | GPIO_PORTA | GPIO_OUT | 17 ) #define PA18_AF_ETMTRACEPKT5 ( GPIO_PORTA | GPIO_AF | 18 ) #define PA19_AF_ETMTRACEPKT6 ( GPIO_PORTA | GPIO_AF | 19 ) #define PA20_AF_ETMTRACEPKT7 ( GPIO_PORTA | GPIO_AF | 20 ) @@ -191,19 +205,27 @@ #define PC15_PF_SPI1_SS ( GPIO_PORTC | GPIO_PF | 15 ) #define PC16_PF_SPI1_MISO ( GPIO_PORTC | GPIO_PF | 16 ) #define PC17_PF_SPI1_MOSI ( GPIO_PORTC | GPIO_PF | 17 ) +#define PC24_BIN_UART3_RI ( GPIO_GIUS | GPIO_PORTC | GPIO_OUT | GPIO_BIN | 24 ) +#define PC25_BIN_UART3_DSR ( GPIO_GIUS | GPIO_PORTC | GPIO_OUT | GPIO_BIN | 25 ) +#define PC26_AOUT_UART3_DTR ( GPIO_GIUS | GPIO_PORTC | GPIO_IN | 26 ) +#define PC27_BIN_UART3_DCD ( GPIO_GIUS | GPIO_PORTC | GPIO_OUT | GPIO_BIN | 27 ) +#define PC28_BIN_UART3_CTS ( GPIO_GIUS | GPIO_PORTC | GPIO_OUT | GPIO_BIN | 28 ) +#define PC29_AOUT_UART3_RTS ( GPIO_GIUS | GPIO_PORTC | GPIO_IN | 29 ) +#define PC30_BIN_UART3_TX ( GPIO_GIUS | GPIO_PORTC | GPIO_BIN | 30 ) +#define PC31_AOUT_UART3_RX ( GPIO_GIUS | GPIO_PORTC | GPIO_IN | 31) #define PD6_PF_LSCLK ( GPIO_PORTD | GPIO_OUT | GPIO_PF | 6 ) #define PD7_PF_REV ( GPIO_PORTD | GPIO_PF | 7 ) #define PD7_AF_UART2_DTR ( GPIO_PORTD | GPIO_IN | GPIO_AF | 7 ) -#define PD7_AIN_SPI2_SCLK ( GPIO_PORTD | GPIO_AIN | 7 ) +#define PD7_AIN_SPI2_SCLK ( GPIO_GIUS | GPIO_PORTD | GPIO_AIN | 7 ) #define PD8_PF_CLS ( GPIO_PORTD | GPIO_PF | 8 ) #define PD8_AF_UART2_DCD ( GPIO_PORTD | GPIO_OUT | GPIO_AF | 8 ) -#define PD8_AIN_SPI2_SS ( GPIO_PORTD | GPIO_AIN | 8 ) +#define PD8_AIN_SPI2_SS ( GPIO_GIUS | GPIO_PORTD | GPIO_AIN | 8 ) #define PD9_PF_PS ( GPIO_PORTD | GPIO_PF | 9 ) #define PD9_AF_UART2_RI ( GPIO_PORTD | GPIO_OUT | GPIO_AF | 9 ) -#define PD9_AOUT_SPI2_RXD ( GPIO_PORTD | GPIO_IN | GPIO_AOUT | 9 ) +#define PD9_AOUT_SPI2_RXD ( GPIO_GIUS | GPIO_PORTD | GPIO_IN | 9 ) #define PD10_PF_SPL_SPR ( GPIO_PORTD | GPIO_OUT | GPIO_PF | 10 ) #define PD10_AF_UART2_DSR ( GPIO_PORTD | GPIO_OUT | GPIO_AF | 10 ) -#define PD10_AIN_SPI2_TXD ( GPIO_PORTD | GPIO_OUT | GPIO_AIN | 10 ) +#define PD10_AIN_SPI2_TXD ( GPIO_GIUS | GPIO_PORTD | GPIO_OUT | 10 ) #define PD11_PF_CONTRAST ( GPIO_PORTD | GPIO_OUT | GPIO_PF | 11 ) #define PD12_PF_ACD_OE ( GPIO_PORTD | GPIO_OUT | GPIO_PF | 12 ) #define PD13_PF_LP_HSYNC ( GPIO_PORTD | GPIO_OUT | GPIO_PF | 13 ) @@ -225,7 +247,7 @@ #define PD29_PF_LD14 ( GPIO_PORTD | GPIO_OUT | GPIO_PF | 29 ) #define PD30_PF_LD15 ( GPIO_PORTD | GPIO_OUT | GPIO_PF | 30 ) #define PD31_PF_TMR2OUT ( GPIO_PORTD | GPIO_PF | 31 ) -#define PD31_BIN_SPI2_TXD ( GPIO_PORTD | GPIO_BIN | 31 ) +#define PD31_BIN_SPI2_TXD ( GPIO_GIUS | GPIO_PORTD | GPIO_BIN | 31 ) /* * PWM controller -- cgit v1.2.3 From 74f8849496b73d2ae4f9c53f61bf59e063ceed88 Mon Sep 17 00:00:00 2001 From: Nicolas Pitre Date: Tue, 4 Oct 2005 23:17:52 +0100 Subject: [ARM] 2951/1: fix wrong comment Patch from Nicolas Pitre The cmpxchg emulation syscall needs write access. Signed-off-by: Nicolas Pitre Signed-off-by: Russell King --- arch/arm/kernel/traps.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/arm/kernel/traps.c b/arch/arm/kernel/traps.c index e7d22dbcb69..f6de76e0a45 100644 --- a/arch/arm/kernel/traps.c +++ b/arch/arm/kernel/traps.c @@ -504,7 +504,7 @@ asmlinkage int arm_syscall(int no, struct pt_regs *regs) bad_access: spin_unlock(&mm->page_table_lock); - /* simulate a read access fault */ + /* simulate a write access fault */ do_DataAbort(addr, 15 + (1 << 11), regs); return -1; } -- cgit v1.2.3 From c2f480869fa7559fa3532e415e3e3ec49339f208 Mon Sep 17 00:00:00 2001 From: Nicolas Pitre Date: Tue, 4 Oct 2005 23:17:53 +0100 Subject: [ARM] 2952/1: fix a register clobber list Patch from Nicolas Pitre If gcc decides to assign lr to %0 we're screwed. Signed-off-by: Nicolas Pitre Signed-off-by: Russell King --- arch/arm/kernel/sys_arm.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/arm/kernel/sys_arm.c b/arch/arm/kernel/sys_arm.c index 42629ff84f5..ea569ba482b 100644 --- a/arch/arm/kernel/sys_arm.c +++ b/arch/arm/kernel/sys_arm.c @@ -305,7 +305,7 @@ long execve(const char *filename, char **argv, char **envp) "Ir" (THREAD_START_SP - sizeof(regs)), "r" (®s), "Ir" (sizeof(regs)) - : "r0", "r1", "r2", "r3", "ip", "memory"); + : "r0", "r1", "r2", "r3", "ip", "lr", "memory"); out: return ret; -- cgit v1.2.3 From 0835ae0f27c0bfde67613d189ef6c537e004a6de Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Tue, 4 Oct 2005 15:23:20 -0700 Subject: [SPARC64]: Replace cheetah+ code patching with variables. Instead of code patching to handle the page size fields in the context registers, just use variables from which we get the proper values. Signed-off-by: David S. Miller --- arch/sparc64/kernel/entry.S | 43 +++++++-------------------------- arch/sparc64/kernel/etrap.S | 51 ++++------------------------------------ arch/sparc64/kernel/head.S | 33 ++++---------------------- arch/sparc64/kernel/rtrap.S | 23 ++---------------- arch/sparc64/kernel/setup.c | 8 ++----- arch/sparc64/kernel/trampoline.S | 15 ++++-------- arch/sparc64/kernel/winfixup.S | 33 ++------------------------ arch/sparc64/mm/init.c | 26 +++++++++++++++----- 8 files changed, 47 insertions(+), 185 deletions(-) diff --git a/arch/sparc64/kernel/entry.S b/arch/sparc64/kernel/entry.S index 2879b107292..f685035dbdb 100644 --- a/arch/sparc64/kernel/entry.S +++ b/arch/sparc64/kernel/entry.S @@ -97,8 +97,8 @@ do_fpdis: faddd %f0, %f2, %f4 fmuld %f0, %f2, %f6 ldxa [%g3] ASI_DMMU, %g5 -cplus_fptrap_insn_1: - sethi %hi(0), %g2 + sethi %hi(sparc64_kern_sec_context), %g2 + ldx [%g2 + %lo(sparc64_kern_sec_context)], %g2 stxa %g2, [%g3] ASI_DMMU membar #Sync add %g6, TI_FPREGS + 0xc0, %g2 @@ -126,8 +126,8 @@ cplus_fptrap_insn_1: fzero %f34 ldxa [%g3] ASI_DMMU, %g5 add %g6, TI_FPREGS, %g1 -cplus_fptrap_insn_2: - sethi %hi(0), %g2 + sethi %hi(sparc64_kern_sec_context), %g2 + ldx [%g2 + %lo(sparc64_kern_sec_context)], %g2 stxa %g2, [%g3] ASI_DMMU membar #Sync add %g6, TI_FPREGS + 0x40, %g2 @@ -153,8 +153,8 @@ cplus_fptrap_insn_2: 3: mov SECONDARY_CONTEXT, %g3 add %g6, TI_FPREGS, %g1 ldxa [%g3] ASI_DMMU, %g5 -cplus_fptrap_insn_3: - sethi %hi(0), %g2 + sethi %hi(sparc64_kern_sec_context), %g2 + ldx [%g2 + %lo(sparc64_kern_sec_context)], %g2 stxa %g2, [%g3] ASI_DMMU membar #Sync mov 0x40, %g2 @@ -319,8 +319,8 @@ do_fptrap_after_fsr: stx %g3, [%g6 + TI_GSR] mov SECONDARY_CONTEXT, %g3 ldxa [%g3] ASI_DMMU, %g5 -cplus_fptrap_insn_4: - sethi %hi(0), %g2 + sethi %hi(sparc64_kern_sec_context), %g2 + ldx [%g2 + %lo(sparc64_kern_sec_context)], %g2 stxa %g2, [%g3] ASI_DMMU membar #Sync add %g6, TI_FPREGS, %g2 @@ -341,33 +341,6 @@ cplus_fptrap_insn_4: ba,pt %xcc, etrap wr %g0, 0, %fprs -cplus_fptrap_1: - sethi %hi(CTX_CHEETAH_PLUS_CTX0), %g2 - - .globl cheetah_plus_patch_fpdis -cheetah_plus_patch_fpdis: - /* We configure the dTLB512_0 for 4MB pages and the - * dTLB512_1 for 8K pages when in context zero. - */ - sethi %hi(cplus_fptrap_1), %o0 - lduw [%o0 + %lo(cplus_fptrap_1)], %o1 - - set cplus_fptrap_insn_1, %o2 - stw %o1, [%o2] - flush %o2 - set cplus_fptrap_insn_2, %o2 - stw %o1, [%o2] - flush %o2 - set cplus_fptrap_insn_3, %o2 - stw %o1, [%o2] - flush %o2 - set cplus_fptrap_insn_4, %o2 - stw %o1, [%o2] - flush %o2 - - retl - nop - /* The registers for cross calls will be: * * DATA 0: [low 32-bits] Address of function to call, jmp to this diff --git a/arch/sparc64/kernel/etrap.S b/arch/sparc64/kernel/etrap.S index 50d2af1d98a..0d8eba21111 100644 --- a/arch/sparc64/kernel/etrap.S +++ b/arch/sparc64/kernel/etrap.S @@ -68,12 +68,8 @@ etrap_irq: wrpr %g3, 0, %otherwin wrpr %g2, 0, %wstate -cplus_etrap_insn_1: - sethi %hi(0), %g3 - sllx %g3, 32, %g3 -cplus_etrap_insn_2: - sethi %hi(0), %g2 - or %g3, %g2, %g3 + sethi %hi(sparc64_kern_pri_context), %g2 + ldx [%g2 + %lo(sparc64_kern_pri_context)], %g3 stxa %g3, [%l4] ASI_DMMU flush %l6 wr %g0, ASI_AIUS, %asi @@ -215,12 +211,8 @@ scetrap: rdpr %pil, %g2 mov PRIMARY_CONTEXT, %l4 wrpr %g3, 0, %otherwin wrpr %g2, 0, %wstate -cplus_etrap_insn_3: - sethi %hi(0), %g3 - sllx %g3, 32, %g3 -cplus_etrap_insn_4: - sethi %hi(0), %g2 - or %g3, %g2, %g3 + sethi %hi(sparc64_kern_pri_context), %g2 + ldx [%g2 + %lo(sparc64_kern_pri_context)], %g3 stxa %g3, [%l4] ASI_DMMU flush %l6 @@ -264,38 +256,3 @@ cplus_etrap_insn_4: #undef TASK_REGOFF #undef ETRAP_PSTATE1 - -cplus_einsn_1: - sethi %uhi(CTX_CHEETAH_PLUS_NUC), %g3 -cplus_einsn_2: - sethi %hi(CTX_CHEETAH_PLUS_CTX0), %g2 - - .globl cheetah_plus_patch_etrap -cheetah_plus_patch_etrap: - /* We configure the dTLB512_0 for 4MB pages and the - * dTLB512_1 for 8K pages when in context zero. - */ - sethi %hi(cplus_einsn_1), %o0 - sethi %hi(cplus_etrap_insn_1), %o2 - lduw [%o0 + %lo(cplus_einsn_1)], %o1 - or %o2, %lo(cplus_etrap_insn_1), %o2 - stw %o1, [%o2] - flush %o2 - sethi %hi(cplus_etrap_insn_3), %o2 - or %o2, %lo(cplus_etrap_insn_3), %o2 - stw %o1, [%o2] - flush %o2 - - sethi %hi(cplus_einsn_2), %o0 - sethi %hi(cplus_etrap_insn_2), %o2 - lduw [%o0 + %lo(cplus_einsn_2)], %o1 - or %o2, %lo(cplus_etrap_insn_2), %o2 - stw %o1, [%o2] - flush %o2 - sethi %hi(cplus_etrap_insn_4), %o2 - or %o2, %lo(cplus_etrap_insn_4), %o2 - stw %o1, [%o2] - flush %o2 - - retl - nop diff --git a/arch/sparc64/kernel/head.S b/arch/sparc64/kernel/head.S index 89406f9649a..24340496cdd 100644 --- a/arch/sparc64/kernel/head.S +++ b/arch/sparc64/kernel/head.S @@ -325,23 +325,7 @@ cheetah_tlb_fixup: 1: sethi %hi(tlb_type), %g1 stw %g2, [%g1 + %lo(tlb_type)] - BRANCH_IF_CHEETAH_PLUS_OR_FOLLOWON(g1,g7,1f) - ba,pt %xcc, 2f - nop - -1: /* Patch context register writes to support nucleus page - * size correctly. - */ - call cheetah_plus_patch_etrap - nop - call cheetah_plus_patch_rtrap - nop - call cheetah_plus_patch_fpdis - nop - call cheetah_plus_patch_winfixup - nop - -2: /* Patch copy/page operations to cheetah optimized versions. */ + /* Patch copy/page operations to cheetah optimized versions. */ call cheetah_patch_copyops nop call cheetah_patch_copy_page @@ -484,20 +468,13 @@ spitfire_vpte_base: call prom_set_trap_table sethi %hi(sparc64_ttable_tl0), %o0 - BRANCH_IF_CHEETAH_PLUS_OR_FOLLOWON(g2,g3,1f) - ba,pt %xcc, 2f - nop - -1: /* Start using proper page size encodings in ctx register. */ - sethi %uhi(CTX_CHEETAH_PLUS_NUC), %g3 + /* Start using proper page size encodings in ctx register. */ + sethi %hi(sparc64_kern_pri_context), %g3 + ldx [%g3 + %lo(sparc64_kern_pri_context)], %g2 mov PRIMARY_CONTEXT, %g1 - sllx %g3, 32, %g3 - sethi %hi(CTX_CHEETAH_PLUS_CTX0), %g2 - or %g3, %g2, %g3 - stxa %g3, [%g1] ASI_DMMU + stxa %g2, [%g1] ASI_DMMU membar #Sync -2: rdpr %pstate, %o1 or %o1, PSTATE_IE, %o1 wrpr %o1, 0, %pstate diff --git a/arch/sparc64/kernel/rtrap.S b/arch/sparc64/kernel/rtrap.S index fafd227735f..ecfb42a69a4 100644 --- a/arch/sparc64/kernel/rtrap.S +++ b/arch/sparc64/kernel/rtrap.S @@ -256,9 +256,8 @@ rt_continue: ldx [%sp + PTREGS_OFF + PT_V9_G1], %g1 brnz,pn %l3, kern_rtt mov PRIMARY_CONTEXT, %l7 ldxa [%l7 + %l7] ASI_DMMU, %l0 -cplus_rtrap_insn_1: - sethi %hi(0), %l1 - sllx %l1, 32, %l1 + sethi %hi(sparc64_kern_pri_nuc_bits), %l1 + ldx [%l1 + %lo(sparc64_kern_pri_nuc_bits)], %l1 or %l0, %l1, %l0 stxa %l0, [%l7] ASI_DMMU flush %g6 @@ -345,21 +344,3 @@ kern_fpucheck: ldub [%g6 + TI_FPDEPTH], %l5 wr %g0, FPRS_DU, %fprs ba,pt %xcc, rt_continue stb %l5, [%g6 + TI_FPDEPTH] - -cplus_rinsn_1: - sethi %uhi(CTX_CHEETAH_PLUS_NUC), %l1 - - .globl cheetah_plus_patch_rtrap -cheetah_plus_patch_rtrap: - /* We configure the dTLB512_0 for 4MB pages and the - * dTLB512_1 for 8K pages when in context zero. - */ - sethi %hi(cplus_rinsn_1), %o0 - sethi %hi(cplus_rtrap_insn_1), %o2 - lduw [%o0 + %lo(cplus_rinsn_1)], %o1 - or %o2, %lo(cplus_rtrap_insn_1), %o2 - stw %o1, [%o2] - flush %o2 - - retl - nop diff --git a/arch/sparc64/kernel/setup.c b/arch/sparc64/kernel/setup.c index 4c9c8f24174..c1f34237cdf 100644 --- a/arch/sparc64/kernel/setup.c +++ b/arch/sparc64/kernel/setup.c @@ -187,17 +187,13 @@ int prom_callback(long *args) } if ((va >= KERNBASE) && (va < (KERNBASE + (4 * 1024 * 1024)))) { - unsigned long kernel_pctx = 0; - - if (tlb_type == cheetah_plus) - kernel_pctx |= (CTX_CHEETAH_PLUS_NUC | - CTX_CHEETAH_PLUS_CTX0); + extern unsigned long sparc64_kern_pri_context; /* Spitfire Errata #32 workaround */ __asm__ __volatile__("stxa %0, [%1] %2\n\t" "flush %%g6" : /* No outputs */ - : "r" (kernel_pctx), + : "r" (sparc64_kern_pri_context), "r" (PRIMARY_CONTEXT), "i" (ASI_DMMU)); diff --git a/arch/sparc64/kernel/trampoline.S b/arch/sparc64/kernel/trampoline.S index 89f2fcfcd66..9478551cb02 100644 --- a/arch/sparc64/kernel/trampoline.S +++ b/arch/sparc64/kernel/trampoline.S @@ -336,20 +336,13 @@ do_unlock: call init_irqwork_curcpu nop - BRANCH_IF_CHEETAH_PLUS_OR_FOLLOWON(g2,g3,1f) - ba,pt %xcc, 2f - nop - -1: /* Start using proper page size encodings in ctx register. */ - sethi %uhi(CTX_CHEETAH_PLUS_NUC), %g3 + /* Start using proper page size encodings in ctx register. */ + sethi %hi(sparc64_kern_pri_context), %g3 + ldx [%g3 + %lo(sparc64_kern_pri_context)], %g2 mov PRIMARY_CONTEXT, %g1 - sllx %g3, 32, %g3 - sethi %hi(CTX_CHEETAH_PLUS_CTX0), %g2 - or %g3, %g2, %g3 - stxa %g3, [%g1] ASI_DMMU + stxa %g2, [%g1] ASI_DMMU membar #Sync -2: rdpr %pstate, %o1 or %o1, PSTATE_IE, %o1 wrpr %o1, 0, %pstate diff --git a/arch/sparc64/kernel/winfixup.S b/arch/sparc64/kernel/winfixup.S index 99c809a1e5a..39160926267 100644 --- a/arch/sparc64/kernel/winfixup.S +++ b/arch/sparc64/kernel/winfixup.S @@ -16,23 +16,14 @@ .text set_pcontext: -cplus_winfixup_insn_1: - sethi %hi(0), %l1 + sethi %hi(sparc64_kern_pri_context), %l1 + ldx [%l1 + %lo(sparc64_kern_pri_context)], %l1 mov PRIMARY_CONTEXT, %g1 - sllx %l1, 32, %l1 -cplus_winfixup_insn_2: - sethi %hi(0), %g2 - or %l1, %g2, %l1 stxa %l1, [%g1] ASI_DMMU flush %g6 retl nop -cplus_wfinsn_1: - sethi %uhi(CTX_CHEETAH_PLUS_NUC), %l1 -cplus_wfinsn_2: - sethi %hi(CTX_CHEETAH_PLUS_CTX0), %g2 - .align 32 /* Here are the rules, pay attention. @@ -395,23 +386,3 @@ window_dax_from_user_common: add %sp, PTREGS_OFF, %o0 ba,pt %xcc, rtrap clr %l6 - - - .globl cheetah_plus_patch_winfixup -cheetah_plus_patch_winfixup: - sethi %hi(cplus_wfinsn_1), %o0 - sethi %hi(cplus_winfixup_insn_1), %o2 - lduw [%o0 + %lo(cplus_wfinsn_1)], %o1 - or %o2, %lo(cplus_winfixup_insn_1), %o2 - stw %o1, [%o2] - flush %o2 - - sethi %hi(cplus_wfinsn_2), %o0 - sethi %hi(cplus_winfixup_insn_2), %o2 - lduw [%o0 + %lo(cplus_wfinsn_2)], %o1 - or %o2, %lo(cplus_winfixup_insn_2), %o2 - stw %o1, [%o2] - flush %o2 - - retl - nop diff --git a/arch/sparc64/mm/init.c b/arch/sparc64/mm/init.c index 5db50524f20..4e2f71e0abc 100644 --- a/arch/sparc64/mm/init.c +++ b/arch/sparc64/mm/init.c @@ -133,6 +133,12 @@ extern unsigned int sparc_ramdisk_size; struct page *mem_map_zero __read_mostly; +unsigned int sparc64_highest_unlocked_tlb_ent __read_mostly; + +unsigned long sparc64_kern_pri_context __read_mostly; +unsigned long sparc64_kern_pri_nuc_bits __read_mostly; +unsigned long sparc64_kern_sec_context __read_mostly; + int bigkernel = 0; /* XXX Tune this... */ @@ -582,13 +588,21 @@ static void __init remap_kernel(void) prom_dtlb_load(tlb_ent, tte_data, tte_vaddr); prom_itlb_load(tlb_ent, tte_data, tte_vaddr); if (bigkernel) { - prom_dtlb_load(tlb_ent - 1, + tlb_ent -= 1; + prom_dtlb_load(tlb_ent, tte_data + 0x400000, tte_vaddr + 0x400000); - prom_itlb_load(tlb_ent - 1, + prom_itlb_load(tlb_ent, tte_data + 0x400000, tte_vaddr + 0x400000); } + sparc64_highest_unlocked_tlb_ent = tlb_ent - 1; + if (tlb_type == cheetah_plus) { + sparc64_kern_pri_context = (CTX_CHEETAH_PLUS_CTX0 | + CTX_CHEETAH_PLUS_NUC); + sparc64_kern_pri_nuc_bits = CTX_CHEETAH_PLUS_NUC; + sparc64_kern_sec_context = CTX_CHEETAH_PLUS_CTX0; + } } static void __init inherit_prom_mappings(void) @@ -788,8 +802,8 @@ void inherit_locked_prom_mappings(int save_p) } } if (tlb_type == spitfire) { - int high = SPITFIRE_HIGHEST_LOCKED_TLBENT - bigkernel; - for (i = 0; i < high; i++) { + int high = sparc64_highest_unlocked_tlb_ent; + for (i = 0; i <= high; i++) { unsigned long data; /* Spitfire Errata #32 workaround */ @@ -877,9 +891,9 @@ void inherit_locked_prom_mappings(int save_p) } } } else if (tlb_type == cheetah || tlb_type == cheetah_plus) { - int high = CHEETAH_HIGHEST_LOCKED_TLBENT - bigkernel; + int high = sparc64_highest_unlocked_tlb_ent; - for (i = 0; i < high; i++) { + for (i = 0; i <= high; i++) { unsigned long data; data = cheetah_get_ldtlb_data(i); -- cgit v1.2.3 From 6d2553612fa329979e6423a5f2410fd7be5aa902 Mon Sep 17 00:00:00 2001 From: Eric Dumazet Date: Tue, 4 Oct 2005 15:55:51 -0700 Subject: [INET]: Shrink struct inet_ehash_bucket on 32 bits UP No need to align struct inet_ehash_bucket on a 8 bytes boundary. On 32 bits Uniprocessor, that's a waste of 4 bytes per struct (50 %) On other platforms, the attribute is useless, natual alignement is already 8. platform | Size before | Size after patch -------------+-------------+------------------ 32 bits, UP | 8 | 4 32 bits, SMP | 8 | 8 64 bits, UP | 8 | 8 64 bits, SMP | 16 | 16 Signed-off-by: Eric Dumazet Signed-off-by: David S. Miller --- include/net/inet_hashtables.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/net/inet_hashtables.h b/include/net/inet_hashtables.h index 35f49e65e29..f50f9596834 100644 --- a/include/net/inet_hashtables.h +++ b/include/net/inet_hashtables.h @@ -40,7 +40,7 @@ struct inet_ehash_bucket { rwlock_t lock; struct hlist_head chain; -} __attribute__((__aligned__(8))); +}; /* There are a few simple rules, which allow for local port reuse by * an application. In essence: -- cgit v1.2.3 From 944d2647dded12e2b05ad8ebc020644bb1997ce1 Mon Sep 17 00:00:00 2001 From: Andi Kleen Date: Wed, 5 Oct 2005 00:21:39 +0200 Subject: [PATCH] x86_64: Drop global bit from early low mappings Drop global bit from early low mappings Suggested by Linus, originally also proposed by Suresh. This fixes a race condition with early start of udev, originally tracked down by Suresh B. Siddha. The problem was that switching to the user space VM would not clear the global low mappings for the beginning of memory, which lead to memory corruption. Drop the global bits. The kernel mapping stays global because it should stay constant. Signed-off-by: Andi Kleen Signed-off-by: Linus Torvalds --- arch/x86_64/kernel/head.S | 40 ++++++++++++++++++++-------------------- 1 file changed, 20 insertions(+), 20 deletions(-) diff --git a/arch/x86_64/kernel/head.S b/arch/x86_64/kernel/head.S index 4592bf21fca..b92e5f45ed4 100644 --- a/arch/x86_64/kernel/head.S +++ b/arch/x86_64/kernel/head.S @@ -270,26 +270,26 @@ ENTRY(level3_kernel_pgt) .org 0x4000 ENTRY(level2_ident_pgt) /* 40MB for bootup. */ - .quad 0x0000000000000183 - .quad 0x0000000000200183 - .quad 0x0000000000400183 - .quad 0x0000000000600183 - .quad 0x0000000000800183 - .quad 0x0000000000A00183 - .quad 0x0000000000C00183 - .quad 0x0000000000E00183 - .quad 0x0000000001000183 - .quad 0x0000000001200183 - .quad 0x0000000001400183 - .quad 0x0000000001600183 - .quad 0x0000000001800183 - .quad 0x0000000001A00183 - .quad 0x0000000001C00183 - .quad 0x0000000001E00183 - .quad 0x0000000002000183 - .quad 0x0000000002200183 - .quad 0x0000000002400183 - .quad 0x0000000002600183 + .quad 0x0000000000000083 + .quad 0x0000000000200083 + .quad 0x0000000000400083 + .quad 0x0000000000600083 + .quad 0x0000000000800083 + .quad 0x0000000000A00083 + .quad 0x0000000000C00083 + .quad 0x0000000000E00083 + .quad 0x0000000001000083 + .quad 0x0000000001200083 + .quad 0x0000000001400083 + .quad 0x0000000001600083 + .quad 0x0000000001800083 + .quad 0x0000000001A00083 + .quad 0x0000000001C00083 + .quad 0x0000000001E00083 + .quad 0x0000000002000083 + .quad 0x0000000002200083 + .quad 0x0000000002400083 + .quad 0x0000000002600083 /* Temporary mappings for the super early allocator in arch/x86_64/mm/init.c */ .globl temp_boot_pmds temp_boot_pmds: -- cgit v1.2.3 From a5181ab06ddca8071b4eb54ac2c314f7d24825d4 Mon Sep 17 00:00:00 2001 From: "Horst H. von Brand" Date: Tue, 4 Oct 2005 15:58:56 -0700 Subject: [NETFILTER]: Fix Kconfig typo Signed-off-by: Horst H. von Brand Signed-off-by: David S. Miller --- net/ipv4/netfilter/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/ipv4/netfilter/Kconfig b/net/ipv4/netfilter/Kconfig index 2cd7e7d1ac9..a7659728e7a 100644 --- a/net/ipv4/netfilter/Kconfig +++ b/net/ipv4/netfilter/Kconfig @@ -141,7 +141,7 @@ config IP_NF_PPTP tristate 'PPTP protocol support' help This module adds support for PPTP (Point to Point Tunnelling - Protocol, RFC2637) conncection tracking and NAT. + Protocol, RFC2637) connection tracking and NAT. If you are running PPTP sessions over a stateful firewall or NAT box, you may want to enable this feature. -- cgit v1.2.3 From ce12467d44d7394731ec9e91e032d50b04e502f6 Mon Sep 17 00:00:00 2001 From: Deepak Saxena Date: Tue, 4 Oct 2005 16:32:38 -0700 Subject: [PATCH] Fix broken IXP4xx GPIO macro Macro ended up backwards during one of cleanups. Found by Alessandro Zummo. Signed-off-by: Deepak Saxena Signed-off-by: Linus Torvalds --- include/asm-arm/arch-ixp4xx/platform.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/asm-arm/arch-ixp4xx/platform.h b/include/asm-arm/arch-ixp4xx/platform.h index d13ee7f78c7..f14ed63590c 100644 --- a/include/asm-arm/arch-ixp4xx/platform.h +++ b/include/asm-arm/arch-ixp4xx/platform.h @@ -93,7 +93,7 @@ extern struct pci_bus *ixp4xx_scan_bus(int nr, struct pci_sys_data *sys); static inline void gpio_line_config(u8 line, u32 direction) { - if (direction == IXP4XX_GPIO_OUT) + if (direction == IXP4XX_GPIO_IN) *IXP4XX_GPIO_GPOER |= (1 << line); else *IXP4XX_GPIO_GPOER &= ~(1 << line); -- cgit v1.2.3 From 9bc39bec87ee3e35897fe27441e979e7c208f624 Mon Sep 17 00:00:00 2001 From: Pavel Roskin Date: Tue, 4 Oct 2005 21:33:10 -0400 Subject: [PATCH] orinoco: Information leakage due to incorrect padding The orinoco driver can send uninitialized data exposing random pieces of the system memory. This happens because data is not padded with zeroes when its length needs to be increased. Reported by Meder Kydyraliev Signed-off-by: Pavel Roskin Signed-off-by: Jeff Garzik --- drivers/net/wireless/orinoco.c | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/drivers/net/wireless/orinoco.c b/drivers/net/wireless/orinoco.c index 6deb7cc810c..cf3daaa1b36 100644 --- a/drivers/net/wireless/orinoco.c +++ b/drivers/net/wireless/orinoco.c @@ -503,9 +503,14 @@ static int orinoco_xmit(struct sk_buff *skb, struct net_device *dev) return 0; } - /* Length of the packet body */ - /* FIXME: what if the skb is smaller than this? */ - len = max_t(int,skb->len - ETH_HLEN, ETH_ZLEN - ETH_HLEN); + /* Check packet length, pad short packets, round up odd length */ + len = max_t(int, ALIGN(skb->len, 2), ETH_ZLEN); + if (skb->len < len) { + skb = skb_padto(skb, len); + if (skb == NULL) + goto fail; + } + len -= ETH_HLEN; eh = (struct ethhdr *)skb->data; @@ -557,8 +562,7 @@ static int orinoco_xmit(struct sk_buff *skb, struct net_device *dev) p = skb->data; } - /* Round up for odd length packets */ - err = hermes_bap_pwrite(hw, USER_BAP, p, ALIGN(data_len, 2), + err = hermes_bap_pwrite(hw, USER_BAP, p, data_len, txfid, data_off); if (err) { printk(KERN_ERR "%s: Error %d writing packet to BAP\n", -- cgit v1.2.3 From 7b5b3f3d826ea87c224c66de9c95c09e7f110ecd Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Tue, 4 Oct 2005 22:38:44 -0700 Subject: [ATM]: fix sparse gfp nocast warnings Fix implicit nocast warnings in atm code: net/atm/atm_misc.c:35:44: warning: implicit cast to nocast type drivers/atm/fore200e.c:183:33: warning: implicit cast to nocast type Also use kzalloc() instead of kmalloc(). Signed-off-by: Randy Dunlap Signed-off-by: David S. Miller --- drivers/atm/fore200e.c | 10 ++++------ include/linux/atmdev.h | 2 +- net/atm/atm_misc.c | 2 +- 3 files changed, 6 insertions(+), 8 deletions(-) diff --git a/drivers/atm/fore200e.c b/drivers/atm/fore200e.c index 2bf723a7b6e..6f1a83c9d9e 100644 --- a/drivers/atm/fore200e.c +++ b/drivers/atm/fore200e.c @@ -178,14 +178,12 @@ fore200e_irq_itoa(int irq) static void* -fore200e_kmalloc(int size, int flags) +fore200e_kmalloc(int size, unsigned int __nocast flags) { - void* chunk = kmalloc(size, flags); + void *chunk = kzalloc(size, flags); - if (chunk) - memset(chunk, 0x00, size); - else - printk(FORE200E "kmalloc() failed, requested size = %d, flags = 0x%x\n", size, flags); + if (!chunk) + printk(FORE200E "kmalloc() failed, requested size = %d, flags = 0x%x\n", size, flags); return chunk; } diff --git a/include/linux/atmdev.h b/include/linux/atmdev.h index 9f374cfa1b0..f1fd849e553 100644 --- a/include/linux/atmdev.h +++ b/include/linux/atmdev.h @@ -457,7 +457,7 @@ static inline void atm_dev_put(struct atm_dev *dev) int atm_charge(struct atm_vcc *vcc,int truesize); struct sk_buff *atm_alloc_charge(struct atm_vcc *vcc,int pdu_size, - int gfp_flags); + unsigned int __nocast gfp_flags); int atm_pcr_goal(struct atm_trafprm *tp); void vcc_release_async(struct atm_vcc *vcc, int reply); diff --git a/net/atm/atm_misc.c b/net/atm/atm_misc.c index b2113c3454a..71abc99ec81 100644 --- a/net/atm/atm_misc.c +++ b/net/atm/atm_misc.c @@ -25,7 +25,7 @@ int atm_charge(struct atm_vcc *vcc,int truesize) struct sk_buff *atm_alloc_charge(struct atm_vcc *vcc,int pdu_size, - int gfp_flags) + unsigned int __nocast gfp_flags) { struct sock *sk = sk_atm(vcc); int guess = atm_guess_pdu2truesize(pdu_size); -- cgit v1.2.3 From de54f3907d2f5d8e25cfafe513811f146b250dee Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Tue, 4 Oct 2005 22:39:41 -0700 Subject: [BONDING]: fix sparse gfp nocast warnings Fix implicit nocast warnings in bonding code: drivers/net/bonding/bond_main.c:1302:49: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: David S. Miller --- drivers/net/bonding/bond_main.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/net/bonding/bond_main.c b/drivers/net/bonding/bond_main.c index fd62e43a351..f0a5b772a38 100644 --- a/drivers/net/bonding/bond_main.c +++ b/drivers/net/bonding/bond_main.c @@ -1289,12 +1289,13 @@ static void bond_mc_list_destroy(struct bonding *bond) /* * Copy all the Multicast addresses from src to the bonding device dst */ -static int bond_mc_list_copy(struct dev_mc_list *mc_list, struct bonding *bond, int gpf_flag) +static int bond_mc_list_copy(struct dev_mc_list *mc_list, struct bonding *bond, + unsigned int __nocast gfp_flag) { struct dev_mc_list *dmi, *new_dmi; for (dmi = mc_list; dmi; dmi = dmi->next) { - new_dmi = kmalloc(sizeof(struct dev_mc_list), gpf_flag); + new_dmi = kmalloc(sizeof(struct dev_mc_list), gfp_flag); if (!new_dmi) { /* FIXME: Potential memory leak !!! */ -- cgit v1.2.3 From 17b698856328a42d5874ac87640e2cd84a824eef Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Tue, 4 Oct 2005 22:41:16 -0700 Subject: [CONNECTOR]: fix sparse gfp nocast warnings Fix implicit nocast warnings in connector code: drivers/connector/connector.c:102:24: warning: implicit cast to nocast type drivers/connector/connector.c:114:45: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: David S. Miller --- drivers/connector/connector.c | 3 ++- include/linux/connector.h | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/connector/connector.c b/drivers/connector/connector.c index bb0b3a8de14..1422285d537 100644 --- a/drivers/connector/connector.c +++ b/drivers/connector/connector.c @@ -69,7 +69,8 @@ int cn_already_initialized = 0; * a new message. * */ -int cn_netlink_send(struct cn_msg *msg, u32 __group, int gfp_mask) +int cn_netlink_send(struct cn_msg *msg, u32 __group, + unsigned int __nocast gfp_mask) { struct cn_callback_entry *__cbq; unsigned int size; diff --git a/include/linux/connector.h b/include/linux/connector.h index 86d4b0a8171..96582c9911a 100644 --- a/include/linux/connector.h +++ b/include/linux/connector.h @@ -149,7 +149,7 @@ struct cn_dev { int cn_add_callback(struct cb_id *, char *, void (*callback) (void *)); void cn_del_callback(struct cb_id *); -int cn_netlink_send(struct cn_msg *, u32, int); +int cn_netlink_send(struct cn_msg *, u32, unsigned int __nocast); int cn_queue_add_callback(struct cn_queue_dev *dev, char *name, struct cb_id *id, void (*callback)(void *)); void cn_queue_del_callback(struct cn_queue_dev *dev, struct cb_id *id); -- cgit v1.2.3 From f4a19a56e38442e434b8809915d756469f1e89a2 Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Tue, 4 Oct 2005 22:41:48 -0700 Subject: [DECNET]: fix sparse gfp nocast warnings Fix implicit nocast warnings in decnet code: net/decnet/af_decnet.c:458:40: warning: implicit cast to nocast type net/decnet/dn_nsp_out.c:125:35: warning: implicit cast to nocast type net/decnet/dn_nsp_out.c:219:29: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: David S. Miller --- include/net/dn_nsp.h | 8 ++++---- include/net/dn_route.h | 2 +- net/decnet/af_decnet.c | 6 ++++-- net/decnet/dn_nsp_out.c | 23 ++++++++++++++--------- 4 files changed, 23 insertions(+), 16 deletions(-) diff --git a/include/net/dn_nsp.h b/include/net/dn_nsp.h index 6bbeafa73e8..8a0891e2e88 100644 --- a/include/net/dn_nsp.h +++ b/include/net/dn_nsp.h @@ -19,9 +19,9 @@ extern void dn_nsp_send_data_ack(struct sock *sk); extern void dn_nsp_send_oth_ack(struct sock *sk); extern void dn_nsp_delayed_ack(struct sock *sk); extern void dn_send_conn_ack(struct sock *sk); -extern void dn_send_conn_conf(struct sock *sk, int gfp); +extern void dn_send_conn_conf(struct sock *sk, unsigned int __nocast gfp); extern void dn_nsp_send_disc(struct sock *sk, unsigned char type, - unsigned short reason, int gfp); + unsigned short reason, unsigned int __nocast gfp); extern void dn_nsp_return_disc(struct sk_buff *skb, unsigned char type, unsigned short reason); extern void dn_nsp_send_link(struct sock *sk, unsigned char lsflags, char fcval); @@ -29,14 +29,14 @@ extern void dn_nsp_send_conninit(struct sock *sk, unsigned char flags); extern void dn_nsp_output(struct sock *sk); extern int dn_nsp_check_xmit_queue(struct sock *sk, struct sk_buff *skb, struct sk_buff_head *q, unsigned short acknum); -extern void dn_nsp_queue_xmit(struct sock *sk, struct sk_buff *skb, int gfp, int oob); +extern void dn_nsp_queue_xmit(struct sock *sk, struct sk_buff *skb, unsigned int __nocast gfp, int oob); extern unsigned long dn_nsp_persist(struct sock *sk); extern int dn_nsp_xmit_timeout(struct sock *sk); extern int dn_nsp_rx(struct sk_buff *); extern int dn_nsp_backlog_rcv(struct sock *sk, struct sk_buff *skb); -extern struct sk_buff *dn_alloc_skb(struct sock *sk, int size, int pri); +extern struct sk_buff *dn_alloc_skb(struct sock *sk, int size, unsigned int __nocast pri); extern struct sk_buff *dn_alloc_send_skb(struct sock *sk, size_t *size, int noblock, long timeo, int *err); #define NSP_REASON_OK 0 /* No error */ diff --git a/include/net/dn_route.h b/include/net/dn_route.h index d084721db19..11fe973cf38 100644 --- a/include/net/dn_route.h +++ b/include/net/dn_route.h @@ -15,7 +15,7 @@ GNU General Public License for more details. *******************************************************************************/ -extern struct sk_buff *dn_alloc_skb(struct sock *sk, int size, int pri); +extern struct sk_buff *dn_alloc_skb(struct sock *sk, int size, unsigned int __nocast pri); extern int dn_route_output_sock(struct dst_entry **pprt, struct flowi *, struct sock *sk, int flags); extern int dn_cache_dump(struct sk_buff *skb, struct netlink_callback *cb); extern int dn_cache_getroute(struct sk_buff *skb, struct nlmsghdr *nlh, void *arg); diff --git a/net/decnet/af_decnet.c b/net/decnet/af_decnet.c index 348f36b529f..34d4128d56d 100644 --- a/net/decnet/af_decnet.c +++ b/net/decnet/af_decnet.c @@ -452,7 +452,8 @@ static struct proto dn_proto = { .obj_size = sizeof(struct dn_sock), }; -static struct sock *dn_alloc_sock(struct socket *sock, int gfp) +static struct sock *dn_alloc_sock(struct socket *sock, + unsigned int __nocast gfp) { struct dn_scp *scp; struct sock *sk = sk_alloc(PF_DECnet, gfp, &dn_proto, 1); @@ -804,7 +805,8 @@ static int dn_auto_bind(struct socket *sock) return rv; } -static int dn_confirm_accept(struct sock *sk, long *timeo, int allocation) +static int dn_confirm_accept(struct sock *sk, long *timeo, + unsigned int __nocast allocation) { struct dn_scp *scp = DN_SK(sk); DEFINE_WAIT(wait); diff --git a/net/decnet/dn_nsp_out.c b/net/decnet/dn_nsp_out.c index 53633d35286..cd08244aa10 100644 --- a/net/decnet/dn_nsp_out.c +++ b/net/decnet/dn_nsp_out.c @@ -117,7 +117,8 @@ try_again: * The eventual aim is for each socket to have a cached header size * for its outgoing packets, and to set hdr from this when sk != NULL. */ -struct sk_buff *dn_alloc_skb(struct sock *sk, int size, int pri) +struct sk_buff *dn_alloc_skb(struct sock *sk, int size, + unsigned int __nocast pri) { struct sk_buff *skb; int hdr = 64; @@ -210,7 +211,8 @@ static void dn_nsp_rtt(struct sock *sk, long rtt) * * Returns: The number of times the packet has been sent previously */ -static inline unsigned dn_nsp_clone_and_send(struct sk_buff *skb, int gfp) +static inline unsigned dn_nsp_clone_and_send(struct sk_buff *skb, + unsigned int __nocast gfp) { struct dn_skb_cb *cb = DN_SKB_CB(skb); struct sk_buff *skb2; @@ -350,7 +352,8 @@ static unsigned short *dn_nsp_mk_data_header(struct sock *sk, struct sk_buff *sk return ptr; } -void dn_nsp_queue_xmit(struct sock *sk, struct sk_buff *skb, int gfp, int oth) +void dn_nsp_queue_xmit(struct sock *sk, struct sk_buff *skb, + unsigned int __nocast gfp, int oth) { struct dn_scp *scp = DN_SK(sk); struct dn_skb_cb *cb = DN_SKB_CB(skb); @@ -517,7 +520,7 @@ static int dn_nsp_retrans_conn_conf(struct sock *sk) return 0; } -void dn_send_conn_conf(struct sock *sk, int gfp) +void dn_send_conn_conf(struct sock *sk, unsigned int __nocast gfp) { struct dn_scp *scp = DN_SK(sk); struct sk_buff *skb = NULL; @@ -549,7 +552,8 @@ void dn_send_conn_conf(struct sock *sk, int gfp) static __inline__ void dn_nsp_do_disc(struct sock *sk, unsigned char msgflg, - unsigned short reason, int gfp, struct dst_entry *dst, + unsigned short reason, unsigned int __nocast gfp, + struct dst_entry *dst, int ddl, unsigned char *dd, __u16 rem, __u16 loc) { struct sk_buff *skb = NULL; @@ -591,7 +595,7 @@ static __inline__ void dn_nsp_do_disc(struct sock *sk, unsigned char msgflg, void dn_nsp_send_disc(struct sock *sk, unsigned char msgflg, - unsigned short reason, int gfp) + unsigned short reason, unsigned int __nocast gfp) { struct dn_scp *scp = DN_SK(sk); int ddl = 0; @@ -612,7 +616,7 @@ void dn_nsp_return_disc(struct sk_buff *skb, unsigned char msgflg, { struct dn_skb_cb *cb = DN_SKB_CB(skb); int ddl = 0; - int gfp = GFP_ATOMIC; + unsigned int __nocast gfp = GFP_ATOMIC; dn_nsp_do_disc(NULL, msgflg, reason, gfp, skb->dst, ddl, NULL, cb->src_port, cb->dst_port); @@ -624,7 +628,7 @@ void dn_nsp_send_link(struct sock *sk, unsigned char lsflags, char fcval) struct dn_scp *scp = DN_SK(sk); struct sk_buff *skb; unsigned char *ptr; - int gfp = GFP_ATOMIC; + unsigned int __nocast gfp = GFP_ATOMIC; if ((skb = dn_alloc_skb(sk, DN_MAX_NSP_DATA_HEADER + 2, gfp)) == NULL) return; @@ -659,7 +663,8 @@ void dn_nsp_send_conninit(struct sock *sk, unsigned char msgflg) unsigned char menuver; struct dn_skb_cb *cb; unsigned char type = 1; - int allocation = (msgflg == NSP_CI) ? sk->sk_allocation : GFP_ATOMIC; + unsigned int __nocast allocation = + (msgflg == NSP_CI) ? sk->sk_allocation : GFP_ATOMIC; struct sk_buff *skb = dn_alloc_skb(sk, 200, allocation); if (!skb) -- cgit v1.2.3 From 8eea00a44d9f493869f8d30b72e3ed18475be556 Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Tue, 4 Oct 2005 22:42:15 -0700 Subject: [IPVS]: fix sparse gfp nocast warnings From: Randy Dunlap Fix implicit nocast warnings in ip_vs code: net/ipv4/ipvs/ip_vs_app.c:631:54: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: David S. Miller --- include/net/ip_vs.h | 2 +- net/ipv4/ipvs/ip_vs_app.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/include/net/ip_vs.h b/include/net/ip_vs.h index 06b4235aa01..ecb2b061f59 100644 --- a/include/net/ip_vs.h +++ b/include/net/ip_vs.h @@ -832,7 +832,7 @@ extern void ip_vs_app_inc_put(struct ip_vs_app *inc); extern int ip_vs_app_pkt_out(struct ip_vs_conn *, struct sk_buff **pskb); extern int ip_vs_app_pkt_in(struct ip_vs_conn *, struct sk_buff **pskb); -extern int ip_vs_skb_replace(struct sk_buff *skb, int pri, +extern int ip_vs_skb_replace(struct sk_buff *skb, unsigned int __nocast pri, char *o_buf, int o_len, char *n_buf, int n_len); extern int ip_vs_app_init(void); extern void ip_vs_app_cleanup(void); diff --git a/net/ipv4/ipvs/ip_vs_app.c b/net/ipv4/ipvs/ip_vs_app.c index 6e092dadb38..b942ff3c886 100644 --- a/net/ipv4/ipvs/ip_vs_app.c +++ b/net/ipv4/ipvs/ip_vs_app.c @@ -604,7 +604,7 @@ static struct file_operations ip_vs_app_fops = { /* * Replace a segment of data with a new segment */ -int ip_vs_skb_replace(struct sk_buff *skb, int pri, +int ip_vs_skb_replace(struct sk_buff *skb, unsigned int __nocast pri, char *o_buf, int o_len, char *n_buf, int n_len) { struct iphdr *iph; -- cgit v1.2.3 From c6f4fafccfa66f0530587ac3c11bb8fd0b8fe8ab Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Tue, 4 Oct 2005 22:42:42 -0700 Subject: [NETFILTER]: fix sparse gfp nocast warnings Fix implicit nocast warnings in nfnetlink code: net/netfilter/nfnetlink.c:204:43: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: David S. Miller --- net/netfilter/nfnetlink.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/net/netfilter/nfnetlink.c b/net/netfilter/nfnetlink.c index 49a3900e3d3..34d671974a4 100644 --- a/net/netfilter/nfnetlink.c +++ b/net/netfilter/nfnetlink.c @@ -195,7 +195,8 @@ nfnetlink_check_attributes(struct nfnetlink_subsystem *subsys, int nfnetlink_send(struct sk_buff *skb, u32 pid, unsigned group, int echo) { - int allocation = in_interrupt() ? GFP_ATOMIC : GFP_KERNEL; + unsigned int __nocast allocation = + in_interrupt() ? GFP_ATOMIC : GFP_KERNEL; int err = 0; NETLINK_CB(skb).dst_group = group; -- cgit v1.2.3 From 00fa02334540ec795934737cd6e6ef8db2560731 Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Tue, 4 Oct 2005 22:43:04 -0700 Subject: [AF_KEY]: fix sparse gfp nocast warnings Fix implicit nocast warnings in net/key code: net/key/af_key.c:195:27: warning: implicit cast to nocast type net/key/af_key.c:1439:28: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: David S. Miller --- net/key/af_key.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/net/key/af_key.c b/net/key/af_key.c index 4879743b945..50d0a31c3ba 100644 --- a/net/key/af_key.c +++ b/net/key/af_key.c @@ -185,7 +185,7 @@ static int pfkey_release(struct socket *sock) } static int pfkey_broadcast_one(struct sk_buff *skb, struct sk_buff **skb2, - int allocation, struct sock *sk) + unsigned int __nocast allocation, struct sock *sk) { int err = -ENOBUFS; @@ -217,7 +217,7 @@ static int pfkey_broadcast_one(struct sk_buff *skb, struct sk_buff **skb2, #define BROADCAST_ONE 1 #define BROADCAST_REGISTERED 2 #define BROADCAST_PROMISC_ONLY 4 -static int pfkey_broadcast(struct sk_buff *skb, int allocation, +static int pfkey_broadcast(struct sk_buff *skb, unsigned int __nocast allocation, int broadcast_flags, struct sock *one_sk) { struct sock *sk; @@ -1416,7 +1416,8 @@ static int pfkey_get(struct sock *sk, struct sk_buff *skb, struct sadb_msg *hdr, return 0; } -static struct sk_buff *compose_sadb_supported(struct sadb_msg *orig, int allocation) +static struct sk_buff *compose_sadb_supported(struct sadb_msg *orig, + unsigned int __nocast allocation) { struct sk_buff *skb; struct sadb_msg *hdr; -- cgit v1.2.3 From dd13a285b79ba77416b96ee10f49097f4aaf48c5 Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Tue, 4 Oct 2005 22:44:45 -0700 Subject: [RPC]: fix sparse gfp nocast warnings Fix nocast sparse warnings: net/rxrpc/call.c:2013:25: warning: implicit cast to nocast type net/rxrpc/connection.c:538:46: warning: implicit cast to nocast type net/sunrpc/sched.c:730:36: warning: implicit cast to nocast type net/sunrpc/sched.c:734:56: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: David S. Miller --- include/rxrpc/call.h | 2 +- include/rxrpc/message.h | 2 +- net/rxrpc/call.c | 2 +- net/rxrpc/connection.c | 2 +- net/sunrpc/sched.c | 2 +- 5 files changed, 5 insertions(+), 5 deletions(-) diff --git a/include/rxrpc/call.h b/include/rxrpc/call.h index f48f27e9e0a..8118731e7d9 100644 --- a/include/rxrpc/call.h +++ b/include/rxrpc/call.h @@ -203,7 +203,7 @@ extern int rxrpc_call_write_data(struct rxrpc_call *call, size_t sioc, struct kvec *siov, uint8_t rxhdr_flags, - int alloc_flags, + unsigned int __nocast alloc_flags, int dup_data, size_t *size_sent); diff --git a/include/rxrpc/message.h b/include/rxrpc/message.h index 3a59df6870b..983d9f9eee1 100644 --- a/include/rxrpc/message.h +++ b/include/rxrpc/message.h @@ -63,7 +63,7 @@ extern int rxrpc_conn_newmsg(struct rxrpc_connection *conn, uint8_t type, int count, struct kvec *diov, - int alloc_flags, + unsigned int __nocast alloc_flags, struct rxrpc_message **_msg); extern int rxrpc_conn_sendmsg(struct rxrpc_connection *conn, struct rxrpc_message *msg); diff --git a/net/rxrpc/call.c b/net/rxrpc/call.c index 5cfd4cadee4..86f77705263 100644 --- a/net/rxrpc/call.c +++ b/net/rxrpc/call.c @@ -1923,7 +1923,7 @@ int rxrpc_call_write_data(struct rxrpc_call *call, size_t sioc, struct kvec *siov, u8 rxhdr_flags, - int alloc_flags, + unsigned int __nocast alloc_flags, int dup_data, size_t *size_sent) { diff --git a/net/rxrpc/connection.c b/net/rxrpc/connection.c index 61463c74f8c..be4b2be5895 100644 --- a/net/rxrpc/connection.c +++ b/net/rxrpc/connection.c @@ -522,7 +522,7 @@ int rxrpc_conn_newmsg(struct rxrpc_connection *conn, uint8_t type, int dcount, struct kvec diov[], - int alloc_flags, + unsigned int __nocast alloc_flags, struct rxrpc_message **_msg) { struct rxrpc_message *msg; diff --git a/net/sunrpc/sched.c b/net/sunrpc/sched.c index f3104035e35..ade730eaf40 100644 --- a/net/sunrpc/sched.c +++ b/net/sunrpc/sched.c @@ -719,7 +719,7 @@ static void rpc_async_schedule(void *arg) void * rpc_malloc(struct rpc_task *task, size_t size) { - int gfp; + unsigned int __nocast gfp; if (task->tk_flags & RPC_TASK_SWAPPER) gfp = GFP_ATOMIC; -- cgit v1.2.3 From 3d2aef668920e8d93b77f145f8f647f62abe75db Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Tue, 4 Oct 2005 22:45:14 -0700 Subject: [TEXTSEARCH]: fix sparse gfp nocast warnings Fix nocast sparse warnings: include/linux/textsearch.h:165:57: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: David S. Miller --- include/linux/textsearch.h | 3 ++- lib/ts_bm.c | 2 +- lib/ts_fsm.c | 2 +- lib/ts_kmp.c | 2 +- 4 files changed, 5 insertions(+), 4 deletions(-) diff --git a/include/linux/textsearch.h b/include/linux/textsearch.h index 941f45ac117..1a4990e448e 100644 --- a/include/linux/textsearch.h +++ b/include/linux/textsearch.h @@ -158,7 +158,8 @@ extern unsigned int textsearch_find_continuous(struct ts_config *, #define TS_PRIV_ALIGNTO 8 #define TS_PRIV_ALIGN(len) (((len) + TS_PRIV_ALIGNTO-1) & ~(TS_PRIV_ALIGNTO-1)) -static inline struct ts_config *alloc_ts_config(size_t payload, int gfp_mask) +static inline struct ts_config *alloc_ts_config(size_t payload, + unsigned int __nocast gfp_mask) { struct ts_config *conf; diff --git a/lib/ts_bm.c b/lib/ts_bm.c index 2cc79112ecc..1b61fceef77 100644 --- a/lib/ts_bm.c +++ b/lib/ts_bm.c @@ -127,7 +127,7 @@ static void compute_prefix_tbl(struct ts_bm *bm, const u8 *pattern, } static struct ts_config *bm_init(const void *pattern, unsigned int len, - int gfp_mask) + unsigned int __nocast gfp_mask) { struct ts_config *conf; struct ts_bm *bm; diff --git a/lib/ts_fsm.c b/lib/ts_fsm.c index d27c0a07294..ef9779e0050 100644 --- a/lib/ts_fsm.c +++ b/lib/ts_fsm.c @@ -258,7 +258,7 @@ found_match: } static struct ts_config *fsm_init(const void *pattern, unsigned int len, - int gfp_mask) + unsigned int __nocast gfp_mask) { int i, err = -EINVAL; struct ts_config *conf; diff --git a/lib/ts_kmp.c b/lib/ts_kmp.c index 73266b97558..e45f0f0c237 100644 --- a/lib/ts_kmp.c +++ b/lib/ts_kmp.c @@ -87,7 +87,7 @@ static inline void compute_prefix_tbl(const u8 *pattern, unsigned int len, } static struct ts_config *kmp_init(const void *pattern, unsigned int len, - int gfp_mask) + unsigned int __nocast gfp_mask) { struct ts_config *conf; struct ts_kmp *kmp; -- cgit v1.2.3 From 83fa3400ebcba307a60909824a251be984eb9567 Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Tue, 4 Oct 2005 22:45:35 -0700 Subject: [XFRM]: fix sparse gfp nocast warnings Fix implicit nocast warnings in xfrm code: net/xfrm/xfrm_policy.c:232:47: warning: implicit cast to nocast type Signed-off-by: Randy Dunlap Signed-off-by: David S. Miller --- include/net/xfrm.h | 2 +- net/xfrm/xfrm_policy.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/include/net/xfrm.h b/include/net/xfrm.h index a9d0d8c5dfb..7564b2ce449 100644 --- a/include/net/xfrm.h +++ b/include/net/xfrm.h @@ -875,7 +875,7 @@ static inline int xfrm_dst_lookup(struct xfrm_dst **dst, struct flowi *fl, unsig } #endif -struct xfrm_policy *xfrm_policy_alloc(int gfp); +struct xfrm_policy *xfrm_policy_alloc(unsigned int __nocast gfp); extern int xfrm_policy_walk(int (*func)(struct xfrm_policy *, int, int, void*), void *); int xfrm_policy_insert(int dir, struct xfrm_policy *policy, int excl); struct xfrm_policy *xfrm_policy_bysel(int dir, struct xfrm_selector *sel, diff --git a/net/xfrm/xfrm_policy.c b/net/xfrm/xfrm_policy.c index fda737d77ed..c6a0d34fc29 100644 --- a/net/xfrm/xfrm_policy.c +++ b/net/xfrm/xfrm_policy.c @@ -225,7 +225,7 @@ expired: * SPD calls. */ -struct xfrm_policy *xfrm_policy_alloc(int gfp) +struct xfrm_policy *xfrm_policy_alloc(unsigned int __nocast gfp) { struct xfrm_policy *policy; -- cgit v1.2.3 From 329d4dd72e5c3393a0c7aeebf3e62df77b196d71 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Wed, 5 Oct 2005 08:36:02 +0100 Subject: [PATCH] fix the breakage in sparc headers If we switch extern inline to static inline, we'd better switch the pre-declarations we use to say that these puppies have __attribute_const__ on them. Otherwise we get extern declaration followed by static inline one. Which makes gcc unhappy, and for a good reason... Signed-off-by: Al Viro Signed-off-by: David S. Miller Signed-off-by: Linus Torvalds --- include/asm-sparc/btfixup.h | 12 ++++++------ include/asm-sparc/pgtable.h | 16 ++++++++-------- 2 files changed, 14 insertions(+), 14 deletions(-) diff --git a/include/asm-sparc/btfixup.h b/include/asm-sparc/btfixup.h index 6b29503256f..c2868d0f60b 100644 --- a/include/asm-sparc/btfixup.h +++ b/include/asm-sparc/btfixup.h @@ -49,7 +49,7 @@ extern unsigned int ___illegal_use_of_BTFIXUP_INT_in_module(void); /* Put bottom 13bits into some register variable */ #define BTFIXUPDEF_SIMM13(__name) \ - extern unsigned int ___sf_##__name(void) __attribute_const__; \ + static inline unsigned int ___sf_##__name(void) __attribute_const__; \ extern unsigned ___ss_##__name[2]; \ static inline unsigned int ___sf_##__name(void) { \ unsigned int ret; \ @@ -57,7 +57,7 @@ extern unsigned int ___illegal_use_of_BTFIXUP_INT_in_module(void); return ret; \ } #define BTFIXUPDEF_SIMM13_INIT(__name,__val) \ - extern unsigned int ___sf_##__name(void) __attribute_const__; \ + static inline unsigned int ___sf_##__name(void) __attribute_const__; \ extern unsigned ___ss_##__name[2]; \ static inline unsigned int ___sf_##__name(void) { \ unsigned int ret; \ @@ -71,7 +71,7 @@ extern unsigned int ___illegal_use_of_BTFIXUP_INT_in_module(void); */ #define BTFIXUPDEF_HALF(__name) \ - extern unsigned int ___af_##__name(void) __attribute_const__; \ + static inline unsigned int ___af_##__name(void) __attribute_const__; \ extern unsigned ___as_##__name[2]; \ static inline unsigned int ___af_##__name(void) { \ unsigned int ret; \ @@ -79,7 +79,7 @@ extern unsigned int ___illegal_use_of_BTFIXUP_INT_in_module(void); return ret; \ } #define BTFIXUPDEF_HALF_INIT(__name,__val) \ - extern unsigned int ___af_##__name(void) __attribute_const__; \ + static inline unsigned int ___af_##__name(void) __attribute_const__; \ extern unsigned ___as_##__name[2]; \ static inline unsigned int ___af_##__name(void) { \ unsigned int ret; \ @@ -90,7 +90,7 @@ extern unsigned int ___illegal_use_of_BTFIXUP_INT_in_module(void); /* Put upper 22 bits into some register variable */ #define BTFIXUPDEF_SETHI(__name) \ - extern unsigned int ___hf_##__name(void) __attribute_const__; \ + static inline unsigned int ___hf_##__name(void) __attribute_const__; \ extern unsigned ___hs_##__name[2]; \ static inline unsigned int ___hf_##__name(void) { \ unsigned int ret; \ @@ -98,7 +98,7 @@ extern unsigned int ___illegal_use_of_BTFIXUP_INT_in_module(void); return ret; \ } #define BTFIXUPDEF_SETHI_INIT(__name,__val) \ - extern unsigned int ___hf_##__name(void) __attribute_const__; \ + static inline unsigned int ___hf_##__name(void) __attribute_const__; \ extern unsigned ___hs_##__name[2]; \ static inline unsigned int ___hf_##__name(void) { \ unsigned int ret; \ diff --git a/include/asm-sparc/pgtable.h b/include/asm-sparc/pgtable.h index ae883f295f1..a14e9867750 100644 --- a/include/asm-sparc/pgtable.h +++ b/include/asm-sparc/pgtable.h @@ -194,19 +194,19 @@ BTFIXUPDEF_HALF(pte_writei) BTFIXUPDEF_HALF(pte_dirtyi) BTFIXUPDEF_HALF(pte_youngi) -extern int pte_write(pte_t pte) __attribute_const__; +static int pte_write(pte_t pte) __attribute_const__; static inline int pte_write(pte_t pte) { return pte_val(pte) & BTFIXUP_HALF(pte_writei); } -extern int pte_dirty(pte_t pte) __attribute_const__; +static int pte_dirty(pte_t pte) __attribute_const__; static inline int pte_dirty(pte_t pte) { return pte_val(pte) & BTFIXUP_HALF(pte_dirtyi); } -extern int pte_young(pte_t pte) __attribute_const__; +static int pte_young(pte_t pte) __attribute_const__; static inline int pte_young(pte_t pte) { return pte_val(pte) & BTFIXUP_HALF(pte_youngi); @@ -217,7 +217,7 @@ static inline int pte_young(pte_t pte) */ BTFIXUPDEF_HALF(pte_filei) -extern int pte_file(pte_t pte) __attribute_const__; +static int pte_file(pte_t pte) __attribute_const__; static inline int pte_file(pte_t pte) { return pte_val(pte) & BTFIXUP_HALF(pte_filei); @@ -229,19 +229,19 @@ BTFIXUPDEF_HALF(pte_wrprotecti) BTFIXUPDEF_HALF(pte_mkcleani) BTFIXUPDEF_HALF(pte_mkoldi) -extern pte_t pte_wrprotect(pte_t pte) __attribute_const__; +static pte_t pte_wrprotect(pte_t pte) __attribute_const__; static inline pte_t pte_wrprotect(pte_t pte) { return __pte(pte_val(pte) & ~BTFIXUP_HALF(pte_wrprotecti)); } -extern pte_t pte_mkclean(pte_t pte) __attribute_const__; +static pte_t pte_mkclean(pte_t pte) __attribute_const__; static inline pte_t pte_mkclean(pte_t pte) { return __pte(pte_val(pte) & ~BTFIXUP_HALF(pte_mkcleani)); } -extern pte_t pte_mkold(pte_t pte) __attribute_const__; +static pte_t pte_mkold(pte_t pte) __attribute_const__; static inline pte_t pte_mkold(pte_t pte) { return __pte(pte_val(pte) & ~BTFIXUP_HALF(pte_mkoldi)); @@ -278,7 +278,7 @@ BTFIXUPDEF_CALL_CONST(pte_t, mk_pte_io, unsigned long, pgprot_t, int) BTFIXUPDEF_INT(pte_modify_mask) -extern pte_t pte_modify(pte_t pte, pgprot_t newprot) __attribute_const__; +static pte_t pte_modify(pte_t pte, pgprot_t newprot) __attribute_const__; static inline pte_t pte_modify(pte_t pte, pgprot_t newprot) { return __pte((pte_val(pte) & BTFIXUP_INT(pte_modify_mask)) | -- cgit v1.2.3 From 23cb8c297eb939b25e5a628dc9e8a71b17f1c44e Mon Sep 17 00:00:00 2001 From: Benjamin Herrenschmidt Date: Wed, 5 Oct 2005 17:43:40 +1000 Subject: [PATCH] ppc: Fix timekeeping with HZ=250 on some Mac models Older Macs which uses the VIA chip timers to calibrate the timebase used some code that wouldn't work if HZ wasn't divisible by 100... This fixes it at least for 250. Not totally perfect but should be enough for now (so it at least works with the default value which is now 250). There is still a potential issue with the core using CLOCK_TICK_RATE to maintain xtime and CLOCK_TICK_RATE value on ppc32 is pure crap, but that is a different problem, this patch at least brings us back to our previous situation. Signed-off-by: Benjamin Herrenschmidt Signed-off-by: Linus Torvalds --- arch/ppc/platforms/pmac_time.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/ppc/platforms/pmac_time.c b/arch/ppc/platforms/pmac_time.c index 778ce4fec36..efb819f9490 100644 --- a/arch/ppc/platforms/pmac_time.c +++ b/arch/ppc/platforms/pmac_time.c @@ -195,7 +195,7 @@ via_calibrate_decr(void) ; dend = get_dec(); - tb_ticks_per_jiffy = (dstart - dend) / (6 * (HZ/100)); + tb_ticks_per_jiffy = (dstart - dend) / ((6 * HZ)/100); tb_to_us = mulhwu_scale_factor(dstart - dend, 60000); printk(KERN_INFO "via_calibrate_decr: ticks per jiffy = %u (%u ticks)\n", -- cgit v1.2.3 From c0758146adbe39514e75ac860ce7e49f865c2297 Mon Sep 17 00:00:00 2001 From: Dave Jones Date: Mon, 3 Oct 2005 15:02:20 -0400 Subject: [PATCH] Fix drm 'debug' sysfs permissions Just enables some extra printk's, but still.. Only the sysadmin should be able to do that. Signed-off-by: Linus Torvalds --- drivers/char/drm/drm_stub.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/char/drm/drm_stub.c b/drivers/char/drm/drm_stub.c index 95a976c96eb..70458cb061c 100644 --- a/drivers/char/drm/drm_stub.c +++ b/drivers/char/drm/drm_stub.c @@ -47,7 +47,7 @@ MODULE_PARM_DESC(cards_limit, "Maximum number of graphics cards"); MODULE_PARM_DESC(debug, "Enable debug output"); module_param_named(cards_limit, drm_cards_limit, int, 0444); -module_param_named(debug, drm_debug, int, 0666); +module_param_named(debug, drm_debug, int, 0600); drm_head_t **drm_heads; struct drm_sysfs_class *drm_class; -- cgit v1.2.3 From fab10fe37ad8dc4388fc444c89ef5aefe906354f Mon Sep 17 00:00:00 2001 From: Yan Zheng Date: Wed, 5 Oct 2005 12:08:13 -0700 Subject: [MCAST] ipv6: Fix address size in grec_size Signed-Off-By: Yan Zheng Acked-by: YOSHIFUJI Hideaki Acked-by: David L Stevens Signed-off-by: David S. Miller --- net/ipv6/mcast.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/ipv6/mcast.c b/net/ipv6/mcast.c index 519899fb11d..39a96c76810 100644 --- a/net/ipv6/mcast.c +++ b/net/ipv6/mcast.c @@ -1393,7 +1393,7 @@ static void mld_sendpack(struct sk_buff *skb) static int grec_size(struct ifmcaddr6 *pmc, int type, int gdel, int sdel) { - return sizeof(struct mld2_grec) + 4*mld_scount(pmc,type,gdel,sdel); + return sizeof(struct mld2_grec) + 16 * mld_scount(pmc,type,gdel,sdel); } static struct sk_buff *add_grhead(struct sk_buff *skb, struct ifmcaddr6 *pmc, -- cgit v1.2.3 From 42a39450f830c57432fd4e5644fa81f41ce7156d Mon Sep 17 00:00:00 2001 From: Stephen Hemminger Date: Wed, 5 Oct 2005 12:09:31 -0700 Subject: [TCP]: BIC coding bug in Linux 2.6.13 Missing parenthesis in causes BIC to be slow in increasing congestion window. Spotted by Injong Rhee. Signed-off-by: Stephen Hemminger Signed-off-by: David S. Miller --- net/ipv4/tcp_bic.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/ipv4/tcp_bic.c b/net/ipv4/tcp_bic.c index b940346de4e..6d80e063c18 100644 --- a/net/ipv4/tcp_bic.c +++ b/net/ipv4/tcp_bic.c @@ -136,7 +136,7 @@ static inline void bictcp_update(struct bictcp *ca, u32 cwnd) else if (cwnd < ca->last_max_cwnd + max_increment*(BICTCP_B-1)) /* slow start */ ca->cnt = (cwnd * (BICTCP_B-1)) - / cwnd-ca->last_max_cwnd; + / (cwnd - ca->last_max_cwnd); else /* linear increase */ ca->cnt = cwnd / max_increment; -- cgit v1.2.3 From 140e26fcd559f6988e5a9056385eecade19d9b49 Mon Sep 17 00:00:00 2001 From: YOSHIFUJI Hideaki Date: Wed, 5 Oct 2005 12:11:41 -0700 Subject: [IPV6]: Fix NS handing for proxy/anycast address Timer set up by pneigh_enqueue() ended up calling ndisc_rcv() via pndisc_redo(), which clears LOCALLY_ENQUEUED flag in NEIGH_CB(skb) and NS was queued again. Let's call ndisc_recv_ns() directly to avoid the loop. Signed-off-by: YOSHIFUJI Hideaki Signed-off-by: David S. Miller --- net/ipv6/ndisc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/ipv6/ndisc.c b/net/ipv6/ndisc.c index 555a31347ed..305d9ee6d7d 100644 --- a/net/ipv6/ndisc.c +++ b/net/ipv6/ndisc.c @@ -1450,7 +1450,7 @@ void ndisc_send_redirect(struct sk_buff *skb, struct neighbour *neigh, static void pndisc_redo(struct sk_buff *skb) { - ndisc_rcv(skb); + ndisc_recv_ns(skb); kfree_skb(skb); } -- cgit v1.2.3 From 77d8d7a6848c81084f413e1ec4982123a56e2ccb Mon Sep 17 00:00:00 2001 From: Herbert Xu Date: Wed, 5 Oct 2005 12:15:12 -0700 Subject: [IPSEC]: Document that policy direction is derived from the index. Here is a patch that adds a helper called xfrm_policy_id2dir to document the fact that the policy direction can be and is derived from the index. This is based on a patch by YOSHIFUJI Hideaki and 210313105@suda.edu.cn. Signed-off-by: Herbert Xu Signed-off-by: David S. Miller --- include/net/xfrm.h | 5 +++++ net/key/af_key.c | 11 ++++++++--- net/xfrm/xfrm_policy.c | 4 ++-- 3 files changed, 15 insertions(+), 5 deletions(-) diff --git a/include/net/xfrm.h b/include/net/xfrm.h index 7564b2ce449..b6e72f890c6 100644 --- a/include/net/xfrm.h +++ b/include/net/xfrm.h @@ -931,4 +931,9 @@ static inline int xfrm_addr_cmp(xfrm_address_t *a, xfrm_address_t *b, } } +static inline int xfrm_policy_id2dir(u32 index) +{ + return index & 7; +} + #endif /* _NET_XFRM_H */ diff --git a/net/key/af_key.c b/net/key/af_key.c index 50d0a31c3ba..bbf0f69181b 100644 --- a/net/key/af_key.c +++ b/net/key/af_key.c @@ -2154,6 +2154,7 @@ out: static int pfkey_spdget(struct sock *sk, struct sk_buff *skb, struct sadb_msg *hdr, void **ext_hdrs) { + unsigned int dir; int err; struct sadb_x_policy *pol; struct xfrm_policy *xp; @@ -2162,7 +2163,11 @@ static int pfkey_spdget(struct sock *sk, struct sk_buff *skb, struct sadb_msg *h if ((pol = ext_hdrs[SADB_X_EXT_POLICY-1]) == NULL) return -EINVAL; - xp = xfrm_policy_byid(0, pol->sadb_x_policy_id, + dir = xfrm_policy_id2dir(pol->sadb_x_policy_id); + if (dir >= XFRM_POLICY_MAX) + return -EINVAL; + + xp = xfrm_policy_byid(dir, pol->sadb_x_policy_id, hdr->sadb_msg_type == SADB_X_SPDDELETE2); if (xp == NULL) return -ENOENT; @@ -2174,9 +2179,9 @@ static int pfkey_spdget(struct sock *sk, struct sk_buff *skb, struct sadb_msg *h if (hdr->sadb_msg_type == SADB_X_SPDDELETE2) { c.data.byid = 1; c.event = XFRM_MSG_DELPOLICY; - km_policy_notify(xp, pol->sadb_x_policy_dir-1, &c); + km_policy_notify(xp, dir, &c); } else { - err = key_pol_get_resp(sk, xp, hdr, pol->sadb_x_policy_dir-1); + err = key_pol_get_resp(sk, xp, hdr, dir); } xfrm_pol_put(xp); diff --git a/net/xfrm/xfrm_policy.c b/net/xfrm/xfrm_policy.c index c6a0d34fc29..061b44cc245 100644 --- a/net/xfrm/xfrm_policy.c +++ b/net/xfrm/xfrm_policy.c @@ -163,7 +163,7 @@ static void xfrm_policy_timer(unsigned long data) if (xp->dead) goto out; - dir = xp->index & 7; + dir = xfrm_policy_id2dir(xp->index); if (xp->lft.hard_add_expires_seconds) { long tmo = xp->lft.hard_add_expires_seconds + @@ -417,7 +417,7 @@ struct xfrm_policy *xfrm_policy_byid(int dir, u32 id, int delete) struct xfrm_policy *pol, **p; write_lock_bh(&xfrm_policy_lock); - for (p = &xfrm_policy_list[id & 7]; (pol=*p)!=NULL; p = &pol->next) { + for (p = &xfrm_policy_list[dir]; (pol=*p)!=NULL; p = &pol->next) { if (pol->index == id) { xfrm_pol_hold(pol); if (delete) -- cgit v1.2.3 From 3a867b36c3234673e61f883ebc11ad18f80a176f Mon Sep 17 00:00:00 2001 From: Ralf Baechle Date: Wed, 5 Oct 2005 12:16:04 -0700 Subject: [AX.25]: Fix packet socket crash Since changeset 98a82febb6340466824c3a453738d4fbd05db81a AX.25 is passing received IP and ARP packets to the stack through netif_rx() but we don't set the skb->mac.raw to right value which may result in a crash with applications that use a packet socket. Signed-off-by: Ralf Baechle DL5RB Signed-off-by: David S. Miller --- net/ax25/ax25_in.c | 2 +- net/netrom/nr_dev.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/net/ax25/ax25_in.c b/net/ax25/ax25_in.c index 810c9c76c2e..73cfc3411c4 100644 --- a/net/ax25/ax25_in.c +++ b/net/ax25/ax25_in.c @@ -123,7 +123,7 @@ int ax25_rx_iframe(ax25_cb *ax25, struct sk_buff *skb) } skb_pull(skb, 1); /* Remove PID */ - skb->h.raw = skb->data; + skb->mac.raw = skb->nh.raw; skb->nh.raw = skb->data; skb->dev = ax25->ax25_dev->dev; skb->pkt_type = PACKET_HOST; diff --git a/net/netrom/nr_dev.c b/net/netrom/nr_dev.c index 4e66eef9a03..509afddae56 100644 --- a/net/netrom/nr_dev.c +++ b/net/netrom/nr_dev.c @@ -58,7 +58,7 @@ int nr_rx_ip(struct sk_buff *skb, struct net_device *dev) /* Spoof incoming device */ skb->dev = dev; - skb->h.raw = skb->data; + skb->mac.raw = skb->nh.raw; skb->nh.raw = skb->data; skb->pkt_type = PACKET_HOST; -- cgit v1.2.3 From 782c3fd470abddf2525e34cf3131215a8f95e834 Mon Sep 17 00:00:00 2001 From: Martin Habets Date: Wed, 5 Oct 2005 12:21:36 -0700 Subject: [SPARC]: Remove some duplicated sparc32 config items Remove some duplicated items due to the inclusion of the general drivers/Kconfig file. These are now taken from drivers/char/Kconfig, and can be turned off there as well (which is desirable sometimes). Signed-off-by: Martin Habets Signed-off-by: David S. Miller --- arch/sparc/Kconfig | 56 ------------------------------------------------------ 1 file changed, 56 deletions(-) diff --git a/arch/sparc/Kconfig b/arch/sparc/Kconfig index aba05394d30..6537445dac0 100644 --- a/arch/sparc/Kconfig +++ b/arch/sparc/Kconfig @@ -25,62 +25,6 @@ source "init/Kconfig" menu "General machine setup" -config VT - bool - select INPUT - default y - ---help--- - If you say Y here, you will get support for terminal devices with - display and keyboard devices. These are called "virtual" because you - can run several virtual terminals (also called virtual consoles) on - one physical terminal. This is rather useful, for example one - virtual terminal can collect system messages and warnings, another - one can be used for a text-mode user session, and a third could run - an X session, all in parallel. Switching between virtual terminals - is done with certain key combinations, usually Alt-. - - The setterm command ("man setterm") can be used to change the - properties (such as colors or beeping) of a virtual terminal. The - man page console_codes(4) ("man console_codes") contains the special - character sequences that can be used to change those properties - directly. The fonts used on virtual terminals can be changed with - the setfont ("man setfont") command and the key bindings are defined - with the loadkeys ("man loadkeys") command. - - You need at least one virtual terminal device in order to make use - of your keyboard and monitor. Therefore, only people configuring an - embedded system would want to say N here in order to save some - memory; the only way to log into such a system is then via a serial - or network connection. - - If unsure, say Y, or else you won't be able to do much with your new - shiny Linux system :-) - -config VT_CONSOLE - bool - default y - ---help--- - The system console is the device which receives all kernel messages - and warnings and which allows logins in single user mode. If you - answer Y here, a virtual terminal (the device used to interact with - a physical terminal) can be used as system console. This is the most - common mode of operations, so you should say Y here unless you want - the kernel messages be output only to a serial port (in which case - you should say Y to "Console on serial port", below). - - If you do say Y here, by default the currently visible virtual - terminal (/dev/tty0) will be used as system console. You can change - that with a kernel command line option such as "console=tty3" which - would use the third virtual terminal as system console. (Try "man - bootparam" or see the documentation of your boot loader (lilo or - loadlin) about how to pass options to the kernel at boot time.) - - If unsure, say Y. - -config HW_CONSOLE - bool - default y - config SMP bool "Symmetric multi-processing support (does not work on sun4/sun4c)" depends on BROKEN -- cgit v1.2.3 From e03eb5272b670e5002463c95fdc023410ba18484 Mon Sep 17 00:00:00 2001 From: Catalin Marinas Date: Wed, 5 Oct 2005 23:06:36 +0100 Subject: [ARM] 2954/1: Allow D and I cache and branch prediction disabling for ARMv6 Patch from Catalin Marinas There is no reason to not allow these config options. They are useful when the hardware has problems. Signed-off-by: Catalin Marinas Signed-off-by: Russell King --- arch/arm/mm/Kconfig | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/arch/arm/mm/Kconfig b/arch/arm/mm/Kconfig index db5e47dfc30..c54e04c995e 100644 --- a/arch/arm/mm/Kconfig +++ b/arch/arm/mm/Kconfig @@ -370,21 +370,21 @@ config CPU_BIG_ENDIAN config CPU_ICACHE_DISABLE bool "Disable I-Cache" - depends on CPU_ARM920T || CPU_ARM922T || CPU_ARM925T || CPU_ARM926T || CPU_ARM1020 + depends on CPU_ARM920T || CPU_ARM922T || CPU_ARM925T || CPU_ARM926T || CPU_ARM1020 || CPU_V6 help Say Y here to disable the processor instruction cache. Unless you have a reason not to or are unsure, say N. config CPU_DCACHE_DISABLE bool "Disable D-Cache" - depends on CPU_ARM920T || CPU_ARM922T || CPU_ARM925T || CPU_ARM926T || CPU_ARM1020 + depends on CPU_ARM920T || CPU_ARM922T || CPU_ARM925T || CPU_ARM926T || CPU_ARM1020 || CPU_V6 help Say Y here to disable the processor data cache. Unless you have a reason not to or are unsure, say N. config CPU_DCACHE_WRITETHROUGH bool "Force write through D-cache" - depends on (CPU_ARM920T || CPU_ARM922T || CPU_ARM925T || CPU_ARM926T || CPU_ARM1020) && !CPU_DCACHE_DISABLE + depends on (CPU_ARM920T || CPU_ARM922T || CPU_ARM925T || CPU_ARM926T || CPU_ARM1020 || CPU_V6) && !CPU_DCACHE_DISABLE default y if CPU_ARM925T help Say Y here to use the data cache in writethrough mode. Unless you @@ -399,7 +399,7 @@ config CPU_CACHE_ROUND_ROBIN config CPU_BPREDICT_DISABLE bool "Disable branch prediction" - depends on CPU_ARM1020 + depends on CPU_ARM1020 || CPU_V6 help Say Y here to disable branch prediction. If unsure, say N. -- cgit v1.2.3 From 9ad98c5b4461e7dfa3754963200993a68825eab4 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Wed, 5 Oct 2005 15:12:00 -0700 Subject: [SPARC64]: Fix initrd when net booting. By allocating early memory for the firmware page tables, we can write over the beginning of the initrd image. So what we do now is: 1) Read in firmware translations table while still on the firmware's trap table. 2) Switch to Linux trap table. 3) Init bootmem. 4) Build firmware page tables using __alloc_bootmem(). And this keeps the initrd from being clobbered. Signed-off-by: David S. Miller --- arch/sparc64/mm/init.c | 156 ++++++++++++++++++------------------------------- 1 file changed, 56 insertions(+), 100 deletions(-) diff --git a/arch/sparc64/mm/init.c b/arch/sparc64/mm/init.c index 4e2f71e0abc..0d2e967c720 100644 --- a/arch/sparc64/mm/init.c +++ b/arch/sparc64/mm/init.c @@ -368,6 +368,7 @@ struct linux_prom_translation { unsigned long data; }; static struct linux_prom_translation prom_trans[512] __initdata; +static unsigned int prom_trans_ents __initdata; extern unsigned long prom_boot_page; extern void prom_remap(unsigned long physpage, unsigned long virtpage, int mmu_ihandle); @@ -381,57 +382,7 @@ unsigned long kern_locked_tte_data; unsigned long prom_pmd_phys __read_mostly; unsigned int swapper_pgd_zero __read_mostly; -/* Allocate power-of-2 aligned chunks from the end of the - * kernel image. Return physical address. - */ -static inline unsigned long early_alloc_phys(unsigned long size) -{ - unsigned long base; - - BUILD_BUG_ON(size & (size - 1)); - - kern_size = (kern_size + (size - 1)) & ~(size - 1); - base = kern_base + kern_size; - kern_size += size; - - return base; -} - -static inline unsigned long load_phys32(unsigned long pa) -{ - unsigned long val; - - __asm__ __volatile__("lduwa [%1] %2, %0" - : "=&r" (val) - : "r" (pa), "i" (ASI_PHYS_USE_EC)); - - return val; -} - -static inline unsigned long load_phys64(unsigned long pa) -{ - unsigned long val; - - __asm__ __volatile__("ldxa [%1] %2, %0" - : "=&r" (val) - : "r" (pa), "i" (ASI_PHYS_USE_EC)); - - return val; -} - -static inline void store_phys32(unsigned long pa, unsigned long val) -{ - __asm__ __volatile__("stwa %0, [%1] %2" - : /* no outputs */ - : "r" (val), "r" (pa), "i" (ASI_PHYS_USE_EC)); -} - -static inline void store_phys64(unsigned long pa, unsigned long val) -{ - __asm__ __volatile__("stxa %0, [%1] %2" - : /* no outputs */ - : "r" (val), "r" (pa), "i" (ASI_PHYS_USE_EC)); -} +static pmd_t *prompmd __read_mostly; #define BASE_PAGE_SIZE 8192 @@ -441,34 +392,28 @@ static inline void store_phys64(unsigned long pa, unsigned long val) */ unsigned long prom_virt_to_phys(unsigned long promva, int *error) { - unsigned long pmd_phys = (prom_pmd_phys + - ((promva >> 23) & 0x7ff) * sizeof(pmd_t)); - unsigned long pte_phys; - pmd_t pmd_ent; - pte_t pte_ent; + pmd_t *pmdp = prompmd + ((promva >> 23) & 0x7ff); + pte_t *ptep; unsigned long base; - pmd_val(pmd_ent) = load_phys32(pmd_phys); - if (pmd_none(pmd_ent)) { + if (pmd_none(*pmdp)) { if (error) *error = 1; return 0; } - - pte_phys = (unsigned long)pmd_val(pmd_ent) << 11UL; - pte_phys += ((promva >> 13) & 0x3ff) * sizeof(pte_t); - pte_val(pte_ent) = load_phys64(pte_phys); - if (!pte_present(pte_ent)) { + ptep = (pte_t *)__pmd_page(*pmdp) + ((promva >> 13) & 0x3ff); + if (!pte_present(*ptep)) { if (error) *error = 1; return 0; } if (error) { *error = 0; - return pte_val(pte_ent); + return pte_val(*ptep); } - base = pte_val(pte_ent) & _PAGE_PADDR; - return (base + (promva & (BASE_PAGE_SIZE - 1))); + base = pte_val(*ptep) & _PAGE_PADDR; + + return base + (promva & (BASE_PAGE_SIZE - 1)); } /* The obp translations are saved based on 8k pagesize, since obp can @@ -481,25 +426,20 @@ static void __init build_obp_range(unsigned long start, unsigned long end, unsig unsigned long vaddr; for (vaddr = start; vaddr < end; vaddr += BASE_PAGE_SIZE) { - unsigned long val, pte_phys, pmd_phys; - pmd_t pmd_ent; - int i; - - pmd_phys = (prom_pmd_phys + - (((vaddr >> 23) & 0x7ff) * sizeof(pmd_t))); - pmd_val(pmd_ent) = load_phys32(pmd_phys); - if (pmd_none(pmd_ent)) { - pte_phys = early_alloc_phys(BASE_PAGE_SIZE); - - for (i = 0; i < BASE_PAGE_SIZE / sizeof(pte_t); i++) - store_phys64(pte_phys+i*sizeof(pte_t),0); + unsigned long val; + pmd_t *pmd; + pte_t *pte; - pmd_val(pmd_ent) = pte_phys >> 11UL; - store_phys32(pmd_phys, pmd_val(pmd_ent)); + pmd = prompmd + ((vaddr >> 23) & 0x7ff); + if (pmd_none(*pmd)) { + pte = __alloc_bootmem(BASE_PAGE_SIZE, BASE_PAGE_SIZE, + PAGE_SIZE); + if (!pte) + prom_halt(); + memset(pte, 0, BASE_PAGE_SIZE); + pmd_set(pmd, pte); } - - pte_phys = (unsigned long)pmd_val(pmd_ent) << 11UL; - pte_phys += (((vaddr >> 13) & 0x3ff) * sizeof(pte_t)); + pte = (pte_t *) __pmd_page(*pmd) + ((vaddr >> 13) & 0x3ff); val = data; @@ -507,7 +447,8 @@ static void __init build_obp_range(unsigned long start, unsigned long end, unsig if (tlb_type == spitfire) val &= ~0x0003fe0000000000UL; - store_phys64(pte_phys, val | _PAGE_MODIFIED); + set_pte_at(&init_mm, vaddr, pte, + __pte(val | _PAGE_MODIFIED)); data += BASE_PAGE_SIZE; } @@ -520,13 +461,17 @@ static inline int in_obp_range(unsigned long vaddr) } #define OBP_PMD_SIZE 2048 -static void __init build_obp_pgtable(int prom_trans_ents) +static void __init build_obp_pgtable(void) { unsigned long i; - prom_pmd_phys = early_alloc_phys(OBP_PMD_SIZE); - for (i = 0; i < OBP_PMD_SIZE; i += 4) - store_phys32(prom_pmd_phys + i, 0); + prompmd = __alloc_bootmem(OBP_PMD_SIZE, OBP_PMD_SIZE, PAGE_SIZE); + if (!prompmd) + prom_halt(); + + memset(prompmd, 0, OBP_PMD_SIZE); + + prom_pmd_phys = __pa(prompmd); for (i = 0; i < prom_trans_ents; i++) { unsigned long start, end; @@ -546,7 +491,7 @@ static void __init build_obp_pgtable(int prom_trans_ents) /* Read OBP translations property into 'prom_trans[]'. * Return the number of entries. */ -static int __init read_obp_translations(void) +static void __init read_obp_translations(void) { int n, node; @@ -567,8 +512,10 @@ static int __init read_obp_translations(void) prom_printf("prom_mappings: Couldn't get property.\n"); prom_halt(); } + n = n / sizeof(struct linux_prom_translation); - return n; + + prom_trans_ents = n; } static void __init remap_kernel(void) @@ -605,19 +552,21 @@ static void __init remap_kernel(void) } } -static void __init inherit_prom_mappings(void) -{ - int n; - n = read_obp_translations(); - build_obp_pgtable(n); +static void __init inherit_prom_mappings_pre(void) +{ + read_obp_translations(); /* Now fixup OBP's idea about where we really are mapped. */ prom_printf("Remapping the kernel... "); remap_kernel(); prom_printf("done.\n"); +} +static void __init inherit_prom_mappings_post(void) +{ + build_obp_pgtable(); register_prom_callbacks(); } @@ -1570,8 +1519,7 @@ void __init paging_init(void) swapper_pgd_zero = pgd_val(swapper_pg_dir[0]); - /* Inherit non-locked OBP mappings. */ - inherit_prom_mappings(); + inherit_prom_mappings_pre(); /* Ok, we can use our TLB miss and window trap handlers safely. * We need to do a quick peek here to see if we are on StarFire @@ -1582,15 +1530,23 @@ void __init paging_init(void) extern void setup_tba(int); setup_tba(this_is_starfire); } - - inherit_locked_prom_mappings(1); - __flush_tlb_all(); + /* Everything from this point forward, until we are done with + * inherit_prom_mappings_post(), must complete successfully + * without calling into the firmware. The firwmare page tables + * have not been built, but we are running on the Linux kernel's + * trap table. + */ + /* Setup bootmem... */ pages_avail = 0; last_valid_pfn = end_pfn = bootmem_init(&pages_avail); + inherit_prom_mappings_post(); + + inherit_locked_prom_mappings(1); + #ifdef CONFIG_DEBUG_PAGEALLOC kernel_physical_mapping_init(); #endif -- cgit v1.2.3 From a448a28589a6640736b8af1f2f57616c10bb37d5 Mon Sep 17 00:00:00 2001 From: Russell King Date: Thu, 6 Oct 2005 13:09:42 +0100 Subject: [MFD] Fix gcc4 build errors in ucb1x00-core.c drivers/mfd/ucb1x00-core.c:555: error: static declaration of 'ucb1x00_class' follows non-static declaration drivers/mfd/ucb1x00.h:109: error: previous declaration of 'ucb1x00_class' was here Since ucb1x00_class isn't used by anything, remove the extern declaration and the symbol export. Signed-off-by: Russell King --- drivers/mfd/ucb1x00-core.c | 2 -- drivers/mfd/ucb1x00.h | 2 -- 2 files changed, 4 deletions(-) diff --git a/drivers/mfd/ucb1x00-core.c b/drivers/mfd/ucb1x00-core.c index 10f6ce1bc0a..612564ac6f7 100644 --- a/drivers/mfd/ucb1x00-core.c +++ b/drivers/mfd/ucb1x00-core.c @@ -642,8 +642,6 @@ static void __exit ucb1x00_exit(void) module_init(ucb1x00_init); module_exit(ucb1x00_exit); -EXPORT_SYMBOL(ucb1x00_class); - EXPORT_SYMBOL(ucb1x00_io_set_dir); EXPORT_SYMBOL(ucb1x00_io_write); EXPORT_SYMBOL(ucb1x00_io_read); diff --git a/drivers/mfd/ucb1x00.h b/drivers/mfd/ucb1x00.h index 6b632644f59..9c9a647d8b7 100644 --- a/drivers/mfd/ucb1x00.h +++ b/drivers/mfd/ucb1x00.h @@ -106,8 +106,6 @@ struct ucb1x00_irq { void (*fn)(int, void *); }; -extern struct class ucb1x00_class; - struct ucb1x00 { spinlock_t lock; struct mcp *mcp; -- cgit v1.2.3 From 76e677e25dd3d8af77d0b3810eacaacaf2f93f2f Mon Sep 17 00:00:00 2001 From: Bryan Sutula Date: Wed, 5 Oct 2005 11:02:06 -0600 Subject: [IA64] Avoid kernel hang during CMC interrupt storm I've noticed a kernel hang during a storm of CMC interrupts, which was tracked down to the continual execution of the interrupt handler. There's code in the CMC handler that's supposed to disable CMC interrupts and switch to polling mode when it sees a bunch of CMCs. Because disabling CMCs across all CPUs isn't safe in interrupt context, the disable is done with a schedule_work(). But with continual CMC interrupts, the schedule_work() never gets executed. The following patch immediately disables CMC interrupts for the current CPU. This then allows (at least) one CPU to ignore CMC interrupts, execute the schedule_work() code, and disable CMC interrupts on the rest of the CPUs. Acked-by: Keith Owens Signed-off-by: Bryan Sutula Signed-off-by: Tony Luck --- arch/ia64/kernel/mca.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/arch/ia64/kernel/mca.c b/arch/ia64/kernel/mca.c index 6dc726ad713..d0a5106fba2 100644 --- a/arch/ia64/kernel/mca.c +++ b/arch/ia64/kernel/mca.c @@ -1016,6 +1016,11 @@ ia64_mca_cmc_int_handler(int cmc_irq, void *arg, struct pt_regs *ptregs) cmc_polling_enabled = 1; spin_unlock(&cmc_history_lock); + /* If we're being hit with CMC interrupts, we won't + * ever execute the schedule_work() below. Need to + * disable CMC interrupts on this processor now. + */ + ia64_mca_cmc_vector_disable(NULL); schedule_work(&cmc_disable_work); /* -- cgit v1.2.3 From 2256c13b992b09f1f9563c26457aa048da2865df Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Thu, 6 Oct 2005 20:43:54 -0700 Subject: [SPARC64]: Probe for power device on ISA bus too. Signed-off-by: David S. Miller --- arch/sparc64/kernel/power.c | 64 ++++++++++++++++++++++++++++++++++++--------- 1 file changed, 51 insertions(+), 13 deletions(-) diff --git a/arch/sparc64/kernel/power.c b/arch/sparc64/kernel/power.c index 946cee0257e..9e8362ea310 100644 --- a/arch/sparc64/kernel/power.c +++ b/arch/sparc64/kernel/power.c @@ -17,6 +17,7 @@ #include #include +#include #include #include @@ -100,46 +101,83 @@ again: return 0; } -static int __init has_button_interrupt(struct linux_ebus_device *edev) +static int __init has_button_interrupt(unsigned int irq, int prom_node) { - if (edev->irqs[0] == PCI_IRQ_NONE) + if (irq == PCI_IRQ_NONE) return 0; - if (!prom_node_has_property(edev->prom_node, "button")) + if (!prom_node_has_property(prom_node, "button")) return 0; return 1; } -void __init power_init(void) +static int __init power_probe_ebus(struct resource **resp, unsigned int *irq_p, int *prom_node_p) { struct linux_ebus *ebus; struct linux_ebus_device *edev; + + for_each_ebus(ebus) { + for_each_ebusdev(edev, ebus) { + if (!strcmp(edev->prom_name, "power")) { + *resp = &edev->resource[0]; + *irq_p = edev->irqs[0]; + *prom_node_p = edev->prom_node; + return 0; + } + } + } + return -ENODEV; +} + +static int __init power_probe_isa(struct resource **resp, unsigned int *irq_p, int *prom_node_p) +{ + struct sparc_isa_bridge *isa_bus; + struct sparc_isa_device *isa_dev; + + for_each_isa(isa_bus) { + for_each_isadev(isa_dev, isa_bus) { + if (!strcmp(isa_dev->prom_name, "power")) { + *resp = &isa_dev->resource; + *irq_p = isa_dev->irq; + *prom_node_p = isa_dev->prom_node; + return 0; + } + } + } + return -ENODEV; +} + +void __init power_init(void) +{ + struct resource *res = NULL; + unsigned int irq; + int prom_node; static int invoked; if (invoked) return; invoked = 1; - for_each_ebus(ebus) { - for_each_ebusdev(edev, ebus) { - if (!strcmp(edev->prom_name, "power")) - goto found; - } - } + if (!power_probe_ebus(&res, &irq, &prom_node)) + goto found; + + if (!power_probe_isa(&res, &irq, &prom_node)) + goto found; + return; found: - power_reg = ioremap(edev->resource[0].start, 0x4); + power_reg = ioremap(res->start, 0x4); printk("power: Control reg at %p ... ", power_reg); poweroff_method = machine_halt; /* able to use the standard halt */ - if (has_button_interrupt(edev)) { + if (has_button_interrupt(irq, prom_node)) { if (kernel_thread(powerd, NULL, CLONE_FS) < 0) { printk("Failed to start power daemon.\n"); return; } printk("powerd running.\n"); - if (request_irq(edev->irqs[0], + if (request_irq(irq, power_handler, SA_SHIRQ, "power", NULL) < 0) printk("power: Error, cannot register IRQ handler.\n"); } else { -- cgit v1.2.3 From 5fe467ee9787007dd9b263eb42dde3742deb743b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ivan=20Skytte=20J=F8rgensen?= Date: Thu, 6 Oct 2005 21:36:17 -0700 Subject: [SCTP] Fix sctp_get{pl}addrs() API to work with 32-bit apps on 64-bit kernels. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The old socket options are marked with a _OLD suffix so that the existing 32-bit apps on 32-bit kernels do not break. Signed-off-by: Ivan Skytte Jørgensen Signed-off-by: Sridhar Samudrala Signed-off-by: David S. Miller --- include/net/sctp/user.h | 23 +++-- net/sctp/socket.c | 252 +++++++++++++++++++++++++++++++++++++++++++----- 2 files changed, 243 insertions(+), 32 deletions(-) diff --git a/include/net/sctp/user.h b/include/net/sctp/user.h index f6328aeddcc..e81ab52755f 100644 --- a/include/net/sctp/user.h +++ b/include/net/sctp/user.h @@ -103,16 +103,20 @@ enum sctp_optname { #define SCTP_SOCKOPT_BINDX_REM SCTP_SOCKOPT_BINDX_REM SCTP_SOCKOPT_PEELOFF, /* peel off association. */ #define SCTP_SOCKOPT_PEELOFF SCTP_SOCKOPT_PEELOFF - SCTP_GET_PEER_ADDRS_NUM, /* Get number of peer addresss. */ -#define SCTP_GET_PEER_ADDRS_NUM SCTP_GET_PEER_ADDRS_NUM + SCTP_GET_PEER_ADDRS_NUM_OLD, /* Get number of peer addresss. */ +#define SCTP_GET_PEER_ADDRS_NUM_OLD SCTP_GET_PEER_ADDRS_NUM_OLD + SCTP_GET_PEER_ADDRS_OLD, /* Get all peer addresss. */ +#define SCTP_GET_PEER_ADDRS_OLD SCTP_GET_PEER_ADDRS_OLD + SCTP_GET_LOCAL_ADDRS_NUM_OLD, /* Get number of local addresss. */ +#define SCTP_GET_LOCAL_ADDRS_NUM_OLD SCTP_GET_LOCAL_ADDRS_NUM_OLD + SCTP_GET_LOCAL_ADDRS_OLD, /* Get all local addresss. */ +#define SCTP_GET_LOCAL_ADDRS_OLD SCTP_GET_LOCAL_ADDRS_OLD + SCTP_SOCKOPT_CONNECTX, /* CONNECTX requests. */ +#define SCTP_SOCKOPT_CONNECTX SCTP_SOCKOPT_CONNECTX SCTP_GET_PEER_ADDRS, /* Get all peer addresss. */ #define SCTP_GET_PEER_ADDRS SCTP_GET_PEER_ADDRS - SCTP_GET_LOCAL_ADDRS_NUM, /* Get number of local addresss. */ -#define SCTP_GET_LOCAL_ADDRS_NUM SCTP_GET_LOCAL_ADDRS_NUM SCTP_GET_LOCAL_ADDRS, /* Get all local addresss. */ #define SCTP_GET_LOCAL_ADDRS SCTP_GET_LOCAL_ADDRS - SCTP_SOCKOPT_CONNECTX, /* CONNECTX requests. */ -#define SCTP_SOCKOPT_CONNECTX SCTP_SOCKOPT_CONNECTX }; /* @@ -559,11 +563,16 @@ struct sctp_status { * SCTP_GET_LOCAL_ADDRS socket options used internally to implement * sctp_getpaddrs() and sctp_getladdrs() API. */ -struct sctp_getaddrs { +struct sctp_getaddrs_old { sctp_assoc_t assoc_id; int addr_num; struct sockaddr __user *addrs; }; +struct sctp_getaddrs { + sctp_assoc_t assoc_id; /*input*/ + __u32 addr_num; /*output*/ + __u8 addrs[0]; /*output, variable size*/ +}; /* These are bit fields for msghdr->msg_flags. See section 5.1. */ /* On user space Linux, these live in as an enum. */ diff --git a/net/sctp/socket.c b/net/sctp/socket.c index 91ec8c93691..02e068d3450 100644 --- a/net/sctp/socket.c +++ b/net/sctp/socket.c @@ -3159,8 +3159,9 @@ static int sctp_getsockopt_initmsg(struct sock *sk, int len, char __user *optval return 0; } -static int sctp_getsockopt_peer_addrs_num(struct sock *sk, int len, - char __user *optval, int __user *optlen) +static int sctp_getsockopt_peer_addrs_num_old(struct sock *sk, int len, + char __user *optval, + int __user *optlen) { sctp_assoc_t id; struct sctp_association *asoc; @@ -3185,23 +3186,28 @@ static int sctp_getsockopt_peer_addrs_num(struct sock *sk, int len, return cnt; } -static int sctp_getsockopt_peer_addrs(struct sock *sk, int len, - char __user *optval, int __user *optlen) +/* + * Old API for getting list of peer addresses. Does not work for 32-bit + * programs running on a 64-bit kernel + */ +static int sctp_getsockopt_peer_addrs_old(struct sock *sk, int len, + char __user *optval, + int __user *optlen) { struct sctp_association *asoc; struct list_head *pos; int cnt = 0; - struct sctp_getaddrs getaddrs; + struct sctp_getaddrs_old getaddrs; struct sctp_transport *from; void __user *to; union sctp_addr temp; struct sctp_sock *sp = sctp_sk(sk); int addrlen; - if (len != sizeof(struct sctp_getaddrs)) + if (len != sizeof(struct sctp_getaddrs_old)) return -EINVAL; - if (copy_from_user(&getaddrs, optval, sizeof(struct sctp_getaddrs))) + if (copy_from_user(&getaddrs, optval, sizeof(struct sctp_getaddrs_old))) return -EFAULT; if (getaddrs.addr_num <= 0) return -EINVAL; @@ -3225,15 +3231,69 @@ static int sctp_getsockopt_peer_addrs(struct sock *sk, int len, if (cnt >= getaddrs.addr_num) break; } getaddrs.addr_num = cnt; - if (copy_to_user(optval, &getaddrs, sizeof(struct sctp_getaddrs))) + if (copy_to_user(optval, &getaddrs, sizeof(struct sctp_getaddrs_old))) + return -EFAULT; + + return 0; +} + +static int sctp_getsockopt_peer_addrs(struct sock *sk, int len, + char __user *optval, int __user *optlen) +{ + struct sctp_association *asoc; + struct list_head *pos; + int cnt = 0; + struct sctp_getaddrs getaddrs; + struct sctp_transport *from; + void __user *to; + union sctp_addr temp; + struct sctp_sock *sp = sctp_sk(sk); + int addrlen; + size_t space_left; + int bytes_copied; + + if (len < sizeof(struct sctp_getaddrs)) + return -EINVAL; + + if (copy_from_user(&getaddrs, optval, sizeof(struct sctp_getaddrs))) + return -EFAULT; + + /* For UDP-style sockets, id specifies the association to query. */ + asoc = sctp_id2assoc(sk, getaddrs.assoc_id); + if (!asoc) + return -EINVAL; + + to = optval + offsetof(struct sctp_getaddrs,addrs); + space_left = len - sizeof(struct sctp_getaddrs) - + offsetof(struct sctp_getaddrs,addrs); + + list_for_each(pos, &asoc->peer.transport_addr_list) { + from = list_entry(pos, struct sctp_transport, transports); + memcpy(&temp, &from->ipaddr, sizeof(temp)); + sctp_get_pf_specific(sk->sk_family)->addr_v4map(sp, &temp); + addrlen = sctp_get_af_specific(sk->sk_family)->sockaddr_len; + if(space_left < addrlen) + return -ENOMEM; + temp.v4.sin_port = htons(temp.v4.sin_port); + if (copy_to_user(to, &temp, addrlen)) + return -EFAULT; + to += addrlen; + cnt++; + space_left -= addrlen; + } + + if (put_user(cnt, &((struct sctp_getaddrs __user *)optval)->addr_num)) + return -EFAULT; + bytes_copied = ((char __user *)to) - optval; + if (put_user(bytes_copied, optlen)) return -EFAULT; return 0; } -static int sctp_getsockopt_local_addrs_num(struct sock *sk, int len, - char __user *optval, - int __user *optlen) +static int sctp_getsockopt_local_addrs_num_old(struct sock *sk, int len, + char __user *optval, + int __user *optlen) { sctp_assoc_t id; struct sctp_bind_addr *bp; @@ -3306,8 +3366,8 @@ done: /* Helper function that copies local addresses to user and returns the number * of addresses copied. */ -static int sctp_copy_laddrs_to_user(struct sock *sk, __u16 port, int max_addrs, - void __user *to) +static int sctp_copy_laddrs_to_user_old(struct sock *sk, __u16 port, int max_addrs, + void __user *to) { struct list_head *pos; struct sctp_sockaddr_entry *addr; @@ -3341,14 +3401,54 @@ static int sctp_copy_laddrs_to_user(struct sock *sk, __u16 port, int max_addrs, return cnt; } -static int sctp_getsockopt_local_addrs(struct sock *sk, int len, - char __user *optval, int __user *optlen) +static int sctp_copy_laddrs_to_user(struct sock *sk, __u16 port, + void * __user *to, size_t space_left) +{ + struct list_head *pos; + struct sctp_sockaddr_entry *addr; + unsigned long flags; + union sctp_addr temp; + int cnt = 0; + int addrlen; + + sctp_spin_lock_irqsave(&sctp_local_addr_lock, flags); + list_for_each(pos, &sctp_local_addr_list) { + addr = list_entry(pos, struct sctp_sockaddr_entry, list); + if ((PF_INET == sk->sk_family) && + (AF_INET6 == addr->a.sa.sa_family)) + continue; + memcpy(&temp, &addr->a, sizeof(temp)); + sctp_get_pf_specific(sk->sk_family)->addr_v4map(sctp_sk(sk), + &temp); + addrlen = sctp_get_af_specific(temp.sa.sa_family)->sockaddr_len; + if(space_leftaddress_list.next, struct sctp_sockaddr_entry, list); if (sctp_is_any(&addr->a)) { - cnt = sctp_copy_laddrs_to_user(sk, bp->port, - getaddrs.addr_num, to); + cnt = sctp_copy_laddrs_to_user_old(sk, bp->port, + getaddrs.addr_num, + to); if (cnt < 0) { err = cnt; goto unlock; @@ -3419,7 +3520,7 @@ static int sctp_getsockopt_local_addrs(struct sock *sk, int len, copy_getaddrs: getaddrs.addr_num = cnt; - if (copy_to_user(optval, &getaddrs, sizeof(struct sctp_getaddrs))) + if (copy_to_user(optval, &getaddrs, sizeof(struct sctp_getaddrs_old))) err = -EFAULT; unlock: @@ -3427,6 +3528,99 @@ unlock: return err; } +static int sctp_getsockopt_local_addrs(struct sock *sk, int len, + char __user *optval, int __user *optlen) +{ + struct sctp_bind_addr *bp; + struct sctp_association *asoc; + struct list_head *pos; + int cnt = 0; + struct sctp_getaddrs getaddrs; + struct sctp_sockaddr_entry *addr; + void __user *to; + union sctp_addr temp; + struct sctp_sock *sp = sctp_sk(sk); + int addrlen; + rwlock_t *addr_lock; + int err = 0; + size_t space_left; + int bytes_copied; + + if (len <= sizeof(struct sctp_getaddrs)) + return -EINVAL; + + if (copy_from_user(&getaddrs, optval, sizeof(struct sctp_getaddrs))) + return -EFAULT; + + /* + * For UDP-style sockets, id specifies the association to query. + * If the id field is set to the value '0' then the locally bound + * addresses are returned without regard to any particular + * association. + */ + if (0 == getaddrs.assoc_id) { + bp = &sctp_sk(sk)->ep->base.bind_addr; + addr_lock = &sctp_sk(sk)->ep->base.addr_lock; + } else { + asoc = sctp_id2assoc(sk, getaddrs.assoc_id); + if (!asoc) + return -EINVAL; + bp = &asoc->base.bind_addr; + addr_lock = &asoc->base.addr_lock; + } + + to = optval + offsetof(struct sctp_getaddrs,addrs); + space_left = len - sizeof(struct sctp_getaddrs) - + offsetof(struct sctp_getaddrs,addrs); + + sctp_read_lock(addr_lock); + + /* If the endpoint is bound to 0.0.0.0 or ::0, get the valid + * addresses from the global local address list. + */ + if (sctp_list_single_entry(&bp->address_list)) { + addr = list_entry(bp->address_list.next, + struct sctp_sockaddr_entry, list); + if (sctp_is_any(&addr->a)) { + cnt = sctp_copy_laddrs_to_user(sk, bp->port, + &to, space_left); + if (cnt < 0) { + err = cnt; + goto unlock; + } + goto copy_getaddrs; + } + } + + list_for_each(pos, &bp->address_list) { + addr = list_entry(pos, struct sctp_sockaddr_entry, list); + memcpy(&temp, &addr->a, sizeof(temp)); + sctp_get_pf_specific(sk->sk_family)->addr_v4map(sp, &temp); + addrlen = sctp_get_af_specific(temp.sa.sa_family)->sockaddr_len; + if(space_left < addrlen) + return -ENOMEM; /*fixme: right error?*/ + temp.v4.sin_port = htons(temp.v4.sin_port); + if (copy_to_user(to, &temp, addrlen)) { + err = -EFAULT; + goto unlock; + } + to += addrlen; + cnt ++; + space_left -= addrlen; + } + +copy_getaddrs: + if (put_user(cnt, &((struct sctp_getaddrs __user *)optval)->addr_num)) + return -EFAULT; + bytes_copied = ((char __user *)to) - optval; + if (put_user(bytes_copied, optlen)) + return -EFAULT; + +unlock: + sctp_read_unlock(addr_lock); + return err; +} + /* 7.1.10 Set Primary Address (SCTP_PRIMARY_ADDR) * * Requests that the local SCTP stack use the enclosed peer address as @@ -3807,12 +4001,20 @@ SCTP_STATIC int sctp_getsockopt(struct sock *sk, int level, int optname, case SCTP_INITMSG: retval = sctp_getsockopt_initmsg(sk, len, optval, optlen); break; - case SCTP_GET_PEER_ADDRS_NUM: - retval = sctp_getsockopt_peer_addrs_num(sk, len, optval, + case SCTP_GET_PEER_ADDRS_NUM_OLD: + retval = sctp_getsockopt_peer_addrs_num_old(sk, len, optval, + optlen); + break; + case SCTP_GET_LOCAL_ADDRS_NUM_OLD: + retval = sctp_getsockopt_local_addrs_num_old(sk, len, optval, + optlen); + break; + case SCTP_GET_PEER_ADDRS_OLD: + retval = sctp_getsockopt_peer_addrs_old(sk, len, optval, optlen); break; - case SCTP_GET_LOCAL_ADDRS_NUM: - retval = sctp_getsockopt_local_addrs_num(sk, len, optval, + case SCTP_GET_LOCAL_ADDRS_OLD: + retval = sctp_getsockopt_local_addrs_old(sk, len, optval, optlen); break; case SCTP_GET_PEER_ADDRS: -- cgit v1.2.3 From 20c9c825b12fcb8526a29cf20a17a5a3fc581726 Mon Sep 17 00:00:00 2001 From: Sridhar Samudrala Date: Thu, 6 Oct 2005 21:37:01 -0700 Subject: [SCTP] Fix SCTP socket options to work with 32-bit apps on 64-bit kernels. Adds alignment attribute to a few structures used with SCTP socket options so that the sizes and offsets remain the same when built using either 32 or 64 bit tools. Signed-off-by: Sridhar Samudrala Signed-off-by: David S. Miller --- include/net/sctp/user.h | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/include/net/sctp/user.h b/include/net/sctp/user.h index e81ab52755f..1c5f19f995a 100644 --- a/include/net/sctp/user.h +++ b/include/net/sctp/user.h @@ -243,7 +243,7 @@ struct sctp_paddr_change { int spc_state; int spc_error; sctp_assoc_t spc_assoc_id; -}; +} __attribute__((packed, aligned(4))); /* * spc_state: 32 bits (signed integer) @@ -468,7 +468,7 @@ struct sctp_assocparams { struct sctp_setpeerprim { sctp_assoc_t sspp_assoc_id; struct sockaddr_storage sspp_addr; -}; +} __attribute__((packed, aligned(4))); /* * 7.1.10 Set Primary Address (SCTP_PRIMARY_ADDR) @@ -481,7 +481,7 @@ struct sctp_setpeerprim { struct sctp_prim { sctp_assoc_t ssp_assoc_id; struct sockaddr_storage ssp_addr; -}; +} __attribute__((packed, aligned(4))); /* * 7.1.11 Set Adaption Layer Indicator (SCTP_ADAPTION_LAYER) @@ -508,7 +508,7 @@ struct sctp_paddrparams { struct sockaddr_storage spp_address; __u32 spp_hbinterval; __u16 spp_pathmaxrxt; -}; +} __attribute__((packed, aligned(4))); /* * 7.2.2 Peer Address Information @@ -527,7 +527,7 @@ struct sctp_paddrinfo { __u32 spinfo_srtt; __u32 spinfo_rto; __u32 spinfo_mtu; -}; +} __attribute__((packed, aligned(4))); /* Peer addresses's state. */ enum sctp_spinfo_state { -- cgit v1.2.3 From 829841146878e082613a49581ae252c071057c23 Mon Sep 17 00:00:00 2001 From: Linus Torvalds Date: Thu, 6 Oct 2005 21:54:21 -0700 Subject: Avoid 'names_cache' memory leak with CONFIG_AUDITSYSCALL The nameidata "last.name" is always allocated with "__getname()", and should always be free'd with "__putname()". Using "putname()" without the underscores will leak memory, because the allocation will have been hidden from the AUDITSYSCALL code. Arguably the real bug is that the AUDITSYSCALL code is really broken, but in the meantime this fixes the problem people see. Reported by Robert Derr, patch by Rick Lindsley. Acked-by: Al Viro Signed-off-by: Linus Torvalds --- fs/namei.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/fs/namei.c b/fs/namei.c index 043d587216b..aa62dbda93a 100644 --- a/fs/namei.c +++ b/fs/namei.c @@ -1551,19 +1551,19 @@ do_link: if (nd->last_type != LAST_NORM) goto exit; if (nd->last.name[nd->last.len]) { - putname(nd->last.name); + __putname(nd->last.name); goto exit; } error = -ELOOP; if (count++==32) { - putname(nd->last.name); + __putname(nd->last.name); goto exit; } dir = nd->dentry; down(&dir->d_inode->i_sem); path.dentry = __lookup_hash(&nd->last, nd->dentry, nd); path.mnt = nd->mnt; - putname(nd->last.name); + __putname(nd->last.name); goto do_last; } -- cgit v1.2.3 From eb98129eec7fa605f0407dfd92d40ee8ddf5cd9a Mon Sep 17 00:00:00 2001 From: Tom 'spot' Callaway Date: Thu, 6 Oct 2005 22:14:59 -0700 Subject: [SPARC32]: Enable generic IOMAP. This helps some PCI stuff build. Signed-off-by: Tom 'spot' Callaway Signed-off-by: David S. Miller --- arch/sparc/Kconfig | 4 ++++ arch/sparc/defconfig | 1 + 2 files changed, 5 insertions(+) diff --git a/arch/sparc/Kconfig b/arch/sparc/Kconfig index 6537445dac0..f7c51b86904 100644 --- a/arch/sparc/Kconfig +++ b/arch/sparc/Kconfig @@ -21,6 +21,10 @@ config GENERIC_ISA_DMA bool default y +config GENERIC_IOMAP + bool + default y + source "init/Kconfig" menu "General machine setup" diff --git a/arch/sparc/defconfig b/arch/sparc/defconfig index a6985626300..8a3aef1e22f 100644 --- a/arch/sparc/defconfig +++ b/arch/sparc/defconfig @@ -5,6 +5,7 @@ CONFIG_MMU=y CONFIG_UID16=y CONFIG_HIGHMEM=y CONFIG_GENERIC_ISA_DMA=y +CONFIG_GENERIC_IOMAP=y # # Code maturity level options -- cgit v1.2.3 From 0f21ba7cc3320d33459ecb3f538f1a42040c29cd Mon Sep 17 00:00:00 2001 From: Eric Kinzie Date: Thu, 6 Oct 2005 22:19:28 -0700 Subject: [ATM]: add support for LECS addresses learned from network From: Eric Kinzie Signed-off-by: Chas Williams Signed-off-by: David S. Miller --- include/linux/atmdev.h | 10 ++++++++++ net/atm/addr.c | 51 +++++++++++++++++++++++++++++++++++++------------- net/atm/addr.h | 12 +++++++----- net/atm/resources.c | 20 +++++++++++++++----- 4 files changed, 70 insertions(+), 23 deletions(-) diff --git a/include/linux/atmdev.h b/include/linux/atmdev.h index f1fd849e553..aca9b344bd3 100644 --- a/include/linux/atmdev.h +++ b/include/linux/atmdev.h @@ -76,6 +76,13 @@ struct atm_dev_stats { /* set interface ESI */ #define ATM_SETESIF _IOW('a',ATMIOC_ITF+13,struct atmif_sioc) /* force interface ESI */ +#define ATM_ADDLECSADDR _IOW('a', ATMIOC_ITF+14, struct atmif_sioc) + /* register a LECS address */ +#define ATM_DELLECSADDR _IOW('a', ATMIOC_ITF+15, struct atmif_sioc) + /* unregister a LECS address */ +#define ATM_GETLECSADDR _IOW('a', ATMIOC_ITF+16, struct atmif_sioc) + /* retrieve LECS address(es) */ + #define ATM_GETSTAT _IOW('a',ATMIOC_SARCOM+0,struct atmif_sioc) /* get AAL layer statistics */ #define ATM_GETSTATZ _IOW('a',ATMIOC_SARCOM+1,struct atmif_sioc) @@ -328,6 +335,8 @@ struct atm_dev_addr { struct list_head entry; /* next address */ }; +enum atm_addr_type_t { ATM_ADDR_LOCAL, ATM_ADDR_LECS }; + struct atm_dev { const struct atmdev_ops *ops; /* device operations; NULL if unused */ const struct atmphy_ops *phy; /* PHY operations, may be undefined */ @@ -338,6 +347,7 @@ struct atm_dev { void *phy_data; /* private PHY date */ unsigned long flags; /* device flags (ATM_DF_*) */ struct list_head local; /* local ATM addresses */ + struct list_head lecs; /* LECS ATM addresses learned via ILMI */ unsigned char esi[ESI_LEN]; /* ESI ("MAC" addr) */ struct atm_cirange ci_range; /* VPI/VCI range */ struct k_atm_dev_stats stats; /* statistics */ diff --git a/net/atm/addr.c b/net/atm/addr.c index a30d0bf4806..3060fd0ba4b 100644 --- a/net/atm/addr.c +++ b/net/atm/addr.c @@ -44,31 +44,43 @@ static void notify_sigd(struct atm_dev *dev) sigd_enq(NULL, as_itf_notify, NULL, &pvc, NULL); } -void atm_reset_addr(struct atm_dev *dev) +void atm_reset_addr(struct atm_dev *dev, enum atm_addr_type_t atype) { unsigned long flags; struct atm_dev_addr *this, *p; + struct list_head *head; spin_lock_irqsave(&dev->lock, flags); - list_for_each_entry_safe(this, p, &dev->local, entry) { + if (atype == ATM_ADDR_LECS) + head = &dev->lecs; + else + head = &dev->local; + list_for_each_entry_safe(this, p, head, entry) { list_del(&this->entry); kfree(this); } spin_unlock_irqrestore(&dev->lock, flags); - notify_sigd(dev); + if (head == &dev->local) + notify_sigd(dev); } -int atm_add_addr(struct atm_dev *dev, struct sockaddr_atmsvc *addr) +int atm_add_addr(struct atm_dev *dev, struct sockaddr_atmsvc *addr, + enum atm_addr_type_t atype) { unsigned long flags; struct atm_dev_addr *this; + struct list_head *head; int error; error = check_addr(addr); if (error) return error; spin_lock_irqsave(&dev->lock, flags); - list_for_each_entry(this, &dev->local, entry) { + if (atype == ATM_ADDR_LECS) + head = &dev->lecs; + else + head = &dev->local; + list_for_each_entry(this, head, entry) { if (identical(&this->addr, addr)) { spin_unlock_irqrestore(&dev->lock, flags); return -EEXIST; @@ -80,28 +92,36 @@ int atm_add_addr(struct atm_dev *dev, struct sockaddr_atmsvc *addr) return -ENOMEM; } this->addr = *addr; - list_add(&this->entry, &dev->local); + list_add(&this->entry, head); spin_unlock_irqrestore(&dev->lock, flags); - notify_sigd(dev); + if (head == &dev->local) + notify_sigd(dev); return 0; } -int atm_del_addr(struct atm_dev *dev, struct sockaddr_atmsvc *addr) +int atm_del_addr(struct atm_dev *dev, struct sockaddr_atmsvc *addr, + enum atm_addr_type_t atype) { unsigned long flags; struct atm_dev_addr *this; + struct list_head *head; int error; error = check_addr(addr); if (error) return error; spin_lock_irqsave(&dev->lock, flags); - list_for_each_entry(this, &dev->local, entry) { + if (atype == ATM_ADDR_LECS) + head = &dev->lecs; + else + head = &dev->local; + list_for_each_entry(this, head, entry) { if (identical(&this->addr, addr)) { list_del(&this->entry); spin_unlock_irqrestore(&dev->lock, flags); kfree(this); - notify_sigd(dev); + if (head == &dev->local) + notify_sigd(dev); return 0; } } @@ -110,22 +130,27 @@ int atm_del_addr(struct atm_dev *dev, struct sockaddr_atmsvc *addr) } int atm_get_addr(struct atm_dev *dev, struct sockaddr_atmsvc __user * buf, - size_t size) + size_t size, enum atm_addr_type_t atype) { unsigned long flags; struct atm_dev_addr *this; + struct list_head *head; int total = 0, error; struct sockaddr_atmsvc *tmp_buf, *tmp_bufp; spin_lock_irqsave(&dev->lock, flags); - list_for_each_entry(this, &dev->local, entry) + if (atype == ATM_ADDR_LECS) + head = &dev->lecs; + else + head = &dev->local; + list_for_each_entry(this, head, entry) total += sizeof(struct sockaddr_atmsvc); tmp_buf = tmp_bufp = kmalloc(total, GFP_ATOMIC); if (!tmp_buf) { spin_unlock_irqrestore(&dev->lock, flags); return -ENOMEM; } - list_for_each_entry(this, &dev->local, entry) + list_for_each_entry(this, head, entry) memcpy(tmp_bufp++, &this->addr, sizeof(struct sockaddr_atmsvc)); spin_unlock_irqrestore(&dev->lock, flags); error = total > size ? -E2BIG : total; diff --git a/net/atm/addr.h b/net/atm/addr.h index 3099d21feea..f39433ad45d 100644 --- a/net/atm/addr.h +++ b/net/atm/addr.h @@ -9,10 +9,12 @@ #include #include - -void atm_reset_addr(struct atm_dev *dev); -int atm_add_addr(struct atm_dev *dev,struct sockaddr_atmsvc *addr); -int atm_del_addr(struct atm_dev *dev,struct sockaddr_atmsvc *addr); -int atm_get_addr(struct atm_dev *dev,struct sockaddr_atmsvc __user *buf,size_t size); +void atm_reset_addr(struct atm_dev *dev, enum atm_addr_type_t type); +int atm_add_addr(struct atm_dev *dev, struct sockaddr_atmsvc *addr, + enum atm_addr_type_t type); +int atm_del_addr(struct atm_dev *dev, struct sockaddr_atmsvc *addr, + enum atm_addr_type_t type); +int atm_get_addr(struct atm_dev *dev, struct sockaddr_atmsvc __user *buf, + size_t size, enum atm_addr_type_t type); #endif diff --git a/net/atm/resources.c b/net/atm/resources.c index a57a9268bd2..415d2615d47 100644 --- a/net/atm/resources.c +++ b/net/atm/resources.c @@ -40,6 +40,7 @@ static struct atm_dev *__alloc_atm_dev(const char *type) dev->link_rate = ATM_OC3_PCR; spin_lock_init(&dev->lock); INIT_LIST_HEAD(&dev->local); + INIT_LIST_HEAD(&dev->lecs); return dev; } @@ -320,10 +321,12 @@ int atm_dev_ioctl(unsigned int cmd, void __user *arg) error = -EPERM; goto done; } - atm_reset_addr(dev); + atm_reset_addr(dev, ATM_ADDR_LOCAL); break; case ATM_ADDADDR: case ATM_DELADDR: + case ATM_ADDLECSADDR: + case ATM_DELLECSADDR: if (!capable(CAP_NET_ADMIN)) { error = -EPERM; goto done; @@ -335,14 +338,21 @@ int atm_dev_ioctl(unsigned int cmd, void __user *arg) error = -EFAULT; goto done; } - if (cmd == ATM_ADDADDR) - error = atm_add_addr(dev, &addr); + if (cmd == ATM_ADDADDR || cmd == ATM_ADDLECSADDR) + error = atm_add_addr(dev, &addr, + (cmd == ATM_ADDADDR ? + ATM_ADDR_LOCAL : ATM_ADDR_LECS)); else - error = atm_del_addr(dev, &addr); + error = atm_del_addr(dev, &addr, + (cmd == ATM_DELADDR ? + ATM_ADDR_LOCAL : ATM_ADDR_LECS)); goto done; } case ATM_GETADDR: - error = atm_get_addr(dev, buf, len); + case ATM_GETLECSADDR: + error = atm_get_addr(dev, buf, len, + (cmd == ATM_GETADDR ? + ATM_ADDR_LOCAL : ATM_ADDR_LECS)); if (error < 0) goto done; size = error; -- cgit v1.2.3 From 06f619ccb3319759c2acf91c7ca02b6b1d9ed343 Mon Sep 17 00:00:00 2001 From: Daniel Ritz Date: Mon, 12 Sep 2005 11:47:04 +0200 Subject: [ALSA] snd_opl3sa2: add missing pnp_unregister_driver() calls OPL3SA2 driver Signed-off-by: Daniel Ritz Signed-off-by: Takashi Iwai --- sound/isa/opl3sa2.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/sound/isa/opl3sa2.c b/sound/isa/opl3sa2.c index e2d2babcd20..4ba268f251e 100644 --- a/sound/isa/opl3sa2.c +++ b/sound/isa/opl3sa2.c @@ -914,6 +914,7 @@ static int __init alsa_card_opl3sa2_init(void) #endif #ifdef CONFIG_PNP pnp_unregister_card_driver(&opl3sa2_pnpc_driver); + pnp_unregister_driver(&opl3sa2_pnp_driver); #endif return -ENODEV; } @@ -927,6 +928,7 @@ static void __exit alsa_card_opl3sa2_exit(void) #ifdef CONFIG_PNP /* PnP cards first */ pnp_unregister_card_driver(&opl3sa2_pnpc_driver); + pnp_unregister_driver(&opl3sa2_pnp_driver); #endif for (idx = 0; idx < SNDRV_CARDS; idx++) snd_card_free(snd_opl3sa2_legacy[idx]); -- cgit v1.2.3 From 0444e2aca9ac89f571f0bb7781d12818719e4baf Mon Sep 17 00:00:00 2001 From: Sasha Khapyorsky Date: Tue, 13 Sep 2005 11:21:30 +0200 Subject: [ALSA] no templated index for mc97 controls AC97 Codec No index is templated for mdoem controls. Signed-off-by: Sasha Khapyorsky Signed-off-by: Takashi Iwai --- sound/pci/ac97/ac97_codec.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sound/pci/ac97/ac97_codec.c b/sound/pci/ac97/ac97_codec.c index e64cb07a39c..f221eba5c32 100644 --- a/sound/pci/ac97/ac97_codec.c +++ b/sound/pci/ac97/ac97_codec.c @@ -1557,7 +1557,7 @@ static int snd_ac97_modem_build(snd_card_t * card, ac97_t * ac97) /* build modem switches */ for (idx = 0; idx < ARRAY_SIZE(snd_ac97_controls_modem_switches); idx++) - if ((err = snd_ctl_add(card, snd_ac97_cnew(&snd_ac97_controls_modem_switches[idx], ac97))) < 0) + if ((err = snd_ctl_add(card, snd_ctl_new1(&snd_ac97_controls_modem_switches[idx], ac97))) < 0) return err; /* build chip specific controls */ -- cgit v1.2.3 From 27bcaa693c866b9bccf94ee5b60eaf705e90c341 Mon Sep 17 00:00:00 2001 From: Sasha Khapyorsky Date: Tue, 13 Sep 2005 11:23:13 +0200 Subject: [ALSA] no templated index for si3036 modem controls AC97 Codec No index is templated for si3036 modem controls. Signed-off-by: Sasha Khapyorsky Signed-off-by: Takashi Iwai --- sound/pci/ac97/ac97_patch.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/sound/pci/ac97/ac97_patch.c b/sound/pci/ac97/ac97_patch.c index 045ddc743ed..0238cc65d32 100644 --- a/sound/pci/ac97/ac97_patch.c +++ b/sound/pci/ac97/ac97_patch.c @@ -2752,7 +2752,11 @@ AC97_DOUBLE("Modem Speaker Volume", 0x5c, 14, 12, 3, 1) static int patch_si3036_specific(ac97_t * ac97) { - return patch_build_controls(ac97, snd_ac97_controls_si3036, ARRAY_SIZE(snd_ac97_controls_si3036)); + int idx, err; + for (idx = 0; idx < ARRAY_SIZE(snd_ac97_controls_si3036); idx++) + if ((err = snd_ctl_add(ac97->bus->card, snd_ctl_new1(&snd_ac97_controls_si3036[idx], ac97))) < 0) + return err; + return 0; } static struct snd_ac97_build_ops patch_si3036_ops = { -- cgit v1.2.3 From 84802f0df3425ae0f9987af0d35ea19910479ec0 Mon Sep 17 00:00:00 2001 From: Sasha Khapyorsky Date: Tue, 13 Sep 2005 11:25:54 +0200 Subject: [ALSA] hda-codec - 'empty' generic mfg-only codec HDA generic driver This creates 'empty' hda generic for unknown MFG-only codecs. Signed-off-by: Sasha Khapyorsky Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_generic.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/sound/pci/hda/hda_generic.c b/sound/pci/hda/hda_generic.c index 5b829a1a4c6..d0eb9f2250a 100644 --- a/sound/pci/hda/hda_generic.c +++ b/sound/pci/hda/hda_generic.c @@ -881,10 +881,8 @@ int snd_hda_parse_generic_codec(struct hda_codec *codec) struct hda_gspec *spec; int err; - if(!codec->afg) { - snd_printdd("hda_generic: no generic modem yet\n"); - return -ENODEV; - } + if(!codec->afg) + return 0; spec = kzalloc(sizeof(*spec), GFP_KERNEL); if (spec == NULL) { -- cgit v1.2.3 From e8dede5a136bd7ef36d1779ea173cfd504dff0cb Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Tue, 13 Sep 2005 11:28:53 +0200 Subject: [ALSA] hda-intel - Disable DMA position auto-correction HDA Intel driver Disable the auto-correction of DMA position temporarily. It doesn't work as expected yet... Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_intel.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/sound/pci/hda/hda_intel.c b/sound/pci/hda/hda_intel.c index 9590ece2099..6fe696e53ea 100644 --- a/sound/pci/hda/hda_intel.c +++ b/sound/pci/hda/hda_intel.c @@ -1137,6 +1137,7 @@ static snd_pcm_uframes_t azx_pcm_pointer(snd_pcm_substream_t *substream) pos = azx_sd_readl(azx_dev, SD_LPIB); if (chip->position_fix == POS_FIX_FIFO) pos += azx_dev->fifo_size; +#if 0 /* disabled temprarily, auto-correction doesn't work well... */ else if (chip->position_fix == POS_FIX_AUTO && azx_dev->period_updating) { /* check the validity of DMA position */ unsigned int diff = 0; @@ -1157,6 +1158,10 @@ static snd_pcm_uframes_t azx_pcm_pointer(snd_pcm_substream_t *substream) } azx_dev->period_updating = 0; } +#else + else if (chip->position_fix == POS_FIX_AUTO) + pos += azx_dev->fifo_size; +#endif } if (pos >= azx_dev->bufsize) pos = 0; -- cgit v1.2.3 From 1dcee12591320d79e4fc5bcdc4aa8a2522b7afdb Mon Sep 17 00:00:00 2001 From: Dirk Opfer Date: Wed, 14 Sep 2005 20:52:25 +0200 Subject: [ALSA] Fix pm_message_t in PXA2XX-AC97 driver ARM PXA2XX driver Fix pm_message_t in PXA2XX-AC97 driver. Signed-off-by: Takashi Iwai --- sound/arm/pxa2xx-ac97.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sound/arm/pxa2xx-ac97.c b/sound/arm/pxa2xx-ac97.c index 29450befb5d..38b20efc9c0 100644 --- a/sound/arm/pxa2xx-ac97.c +++ b/sound/arm/pxa2xx-ac97.c @@ -245,7 +245,7 @@ static pxa2xx_pcm_client_t pxa2xx_ac97_pcm_client = { #ifdef CONFIG_PM -static int pxa2xx_ac97_do_suspend(snd_card_t *card, unsigned int state) +static int pxa2xx_ac97_do_suspend(snd_card_t *card, pm_message_t state) { if (card->power_state != SNDRV_CTL_POWER_D3cold) { pxa2xx_audio_ops_t *platform_ops = card->dev->platform_data; -- cgit v1.2.3 From 460dc98afc6db255344a06c8da1196e2a2744758 Mon Sep 17 00:00:00 2001 From: Clemens Ladisch Date: Fri, 16 Sep 2005 16:56:01 +0200 Subject: [ALSA] usb-audio: ignore Hercules DJ Console mixer errors USB generic driver Add a quirk entry for the Hercules DJ Console to ignore timeouts on some mixer control transfers. Signed-off-by: Clemens Ladisch --- sound/usb/usbmixer_maps.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/sound/usb/usbmixer_maps.c b/sound/usb/usbmixer_maps.c index f05500b05ec..13199ff36d4 100644 --- a/sound/usb/usbmixer_maps.c +++ b/sound/usb/usbmixer_maps.c @@ -237,6 +237,11 @@ static struct usbmix_ctl_map usbmix_ctl_maps[] = { .map = audigy2nx_map, .selector_map = audigy2nx_selectors, }, + { + /* Hercules DJ Console */ + .id = USB_ID(0x06f8, 0xd002), + .ignore_ctl_error = 1, + }, { .id = USB_ID(0x08bb, 0x2702), .map = linex_map, -- cgit v1.2.3 From 3a91e95969b84a56c7fef15ba25a5f6a17dd94b2 Mon Sep 17 00:00:00 2001 From: Nicolas Pitre Date: Fri, 16 Sep 2005 18:46:36 +0200 Subject: [ALSA] remove bogus match method for ac97_bus AC97 Codec The bus_id is initialized with a generic identifier string which is not really useful for proper driver matching. Let the driver decide what it needs via its probe method instead. Signed-off-by: Nicolas Pitre Signed-off-by: Takashi Iwai --- sound/pci/ac97/ac97_bus.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/sound/pci/ac97/ac97_bus.c b/sound/pci/ac97/ac97_bus.c index 227f8b9f67c..6f0e4bd83aa 100644 --- a/sound/pci/ac97/ac97_bus.c +++ b/sound/pci/ac97/ac97_bus.c @@ -17,12 +17,13 @@ #include /* - * Codec families have names seperated by commas, so we search for an - * individual codec name within the family string. + * Let drivers decide whether they want to support given codec from their + * probe method. Drivers have direct access to the ac97_t structure and may + * decide based on the id field amongst other things. */ static int ac97_bus_match(struct device *dev, struct device_driver *drv) { - return (strstr(dev->bus_id, drv->name) != NULL); + return 1; } static int ac97_bus_suspend(struct device *dev, pm_message_t state) -- cgit v1.2.3 From 72e75de2df9a7116d0afbcd5810b2a8fd4bf7559 Mon Sep 17 00:00:00 2001 From: Nicolas Pitre Date: Fri, 16 Sep 2005 18:49:22 +0200 Subject: [ALSA] remove redundent assignment to the ac97 device structure AC97 Codec Don't use dev.platform_data to store a reference to the containing ac97_t structure. Such assignment is redundent since we can deduce the ac97_t structure location from the contained device structure. This sets platform_data free for other purposes. Signed-off-by: Nicolas Pitre Signed-off-by: Takashi Iwai --- include/sound/ac97_codec.h | 2 ++ sound/pci/ac97/ac97_codec.c | 1 - 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/include/sound/ac97_codec.h b/include/sound/ac97_codec.h index 2857cf0472d..d11f34832a9 100644 --- a/include/sound/ac97_codec.h +++ b/include/sound/ac97_codec.h @@ -527,6 +527,8 @@ struct _snd_ac97 { struct device dev; }; +#define to_ac97_t(d) container_of(d, struct _snd_ac97, dev) + /* conditions */ static inline int ac97_is_audio(ac97_t * ac97) { diff --git a/sound/pci/ac97/ac97_codec.c b/sound/pci/ac97/ac97_codec.c index f221eba5c32..41fc290149e 100644 --- a/sound/pci/ac97/ac97_codec.c +++ b/sound/pci/ac97/ac97_codec.c @@ -1828,7 +1828,6 @@ static int snd_ac97_dev_register(snd_device_t *device) ac97->dev.bus = &ac97_bus_type; ac97->dev.parent = ac97->bus->card->dev; - ac97->dev.platform_data = ac97; ac97->dev.release = ac97_device_release; snprintf(ac97->dev.bus_id, BUS_ID_SIZE, "card%d-%d", ac97->bus->card->number, ac97->num); if ((err = device_register(&ac97->dev)) < 0) { -- cgit v1.2.3 From 90b66e833261618e11d71a35f2488a7d664a4566 Mon Sep 17 00:00:00 2001 From: Nicolas Pitre Date: Fri, 16 Sep 2005 18:50:53 +0200 Subject: [ALSA] clean suspend/resume calls for ac97_bus_type AC97 Codec A single call to the driver suspend/resume method for each device is enough. The level and SUSPEND_*/RESUME_* arguments are deprecated and said to be removed eventually anyway (no other subsystem are using them anymore except platform devices). Signed-off-by: Nicolas Pitre Signed-off-by: Takashi Iwai --- sound/pci/ac97/ac97_bus.c | 16 +++------------- 1 file changed, 3 insertions(+), 13 deletions(-) diff --git a/sound/pci/ac97/ac97_bus.c b/sound/pci/ac97/ac97_bus.c index 6f0e4bd83aa..becbc420ba4 100644 --- a/sound/pci/ac97/ac97_bus.c +++ b/sound/pci/ac97/ac97_bus.c @@ -30,13 +30,8 @@ static int ac97_bus_suspend(struct device *dev, pm_message_t state) { int ret = 0; - if (dev->driver && dev->driver->suspend) { - ret = dev->driver->suspend(dev, state, SUSPEND_DISABLE); - if (ret == 0) - ret = dev->driver->suspend(dev, state, SUSPEND_SAVE_STATE); - if (ret == 0) - ret = dev->driver->suspend(dev, state, SUSPEND_POWER_DOWN); - } + if (dev->driver && dev->driver->suspend) + ret = dev->driver->suspend(dev, state, SUSPEND_POWER_DOWN); return ret; } @@ -44,13 +39,8 @@ static int ac97_bus_resume(struct device *dev) { int ret = 0; - if (dev->driver && dev->driver->resume) { + if (dev->driver && dev->driver->resume) ret = dev->driver->resume(dev, RESUME_POWER_ON); - if (ret == 0) - ret = dev->driver->resume(dev, RESUME_RESTORE_STATE); - if (ret == 0) - ret = dev->driver->resume(dev, RESUME_ENABLE); - } return ret; } -- cgit v1.2.3 From db99055f8d8eb54d9da55293a11b82e9d53ca80d Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Fri, 16 Sep 2005 19:07:52 +0200 Subject: [ALSA] via82xx - Add a dxs whitelist entry VIA82xx driver Added a dxs whitelist entry for an ECS mobo. Signed-off-by: Takashi Iwai --- sound/pci/via82xx.c | 1 + 1 file changed, 1 insertion(+) diff --git a/sound/pci/via82xx.c b/sound/pci/via82xx.c index 6db7de6b971..964113ffa60 100644 --- a/sound/pci/via82xx.c +++ b/sound/pci/via82xx.c @@ -2147,6 +2147,7 @@ static int __devinit check_dxs_list(struct pci_dev *pci) { .subvendor = 0x1019, .subdevice = 0x0996, .action = VIA_DXS_48K }, { .subvendor = 0x1019, .subdevice = 0x0a81, .action = VIA_DXS_NO_VRA }, /* ECS K7VTA3 v8.0 */ { .subvendor = 0x1019, .subdevice = 0x0a85, .action = VIA_DXS_NO_VRA }, /* ECS L7VMM2 */ + { .subvendor = 0x1019, .subdevice = 0xa101, .action = VIA_DXS_SRC }, { .subvendor = 0x1025, .subdevice = 0x0033, .action = VIA_DXS_NO_VRA }, /* Acer Inspire 1353LM */ { .subvendor = 0x1025, .subdevice = 0x0046, .action = VIA_DXS_SRC }, /* Acer Aspire 1524 WLMi */ { .subvendor = 0x1043, .subdevice = 0x8095, .action = VIA_DXS_NO_VRA }, /* ASUS A7V8X (FIXME: possibly VIA_DXS_ENABLE?)*/ -- cgit v1.2.3 From 5a2a68f5a1dab785d60a4575f48af5b15ab6328d Mon Sep 17 00:00:00 2001 From: Clemens Ladisch Date: Mon, 19 Sep 2005 12:24:00 +0200 Subject: [ALSA] usb-audio: add Roland RD-700SX support USB generic driver Add a quirk entry for the Roland RD-700SX. This should work for the RD-300SX, too. Signed-off-by: Clemens Ladisch --- sound/usb/usbquirks.h | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/sound/usb/usbquirks.h b/sound/usb/usbquirks.h index f74e652a1e5..36f9a3b8694 100644 --- a/sound/usb/usbquirks.h +++ b/sound/usb/usbquirks.h @@ -1010,6 +1010,19 @@ YAMAHA_DEVICE(0x7010, "UB99"), } } }, +{ + USB_DEVICE_VENDOR_SPEC(0x0582, 0x007a), + .driver_info = (unsigned long) & (const snd_usb_audio_quirk_t) { + .vendor_name = "Roland", + /* RD-700SX, RD-300SX */ + .ifnum = 0, + .type = QUIRK_MIDI_FIXED_ENDPOINT, + .data = & (const snd_usb_midi_endpoint_info_t) { + .out_cables = 0x0003, + .in_cables = 0x0003 + } + } +}, /* Midiman/M-Audio devices */ { -- cgit v1.2.3 From 1e8bdcaf82268ac713cbbaffc14801147be42ae7 Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Mon, 19 Sep 2005 15:21:17 +0200 Subject: [ALSA] Add iBook 1.33GHz support PPC PMAC driver Added the support of iBook 1.33GHz. Signed-off-by: Takashi Iwai --- sound/ppc/pmac.c | 1 + 1 file changed, 1 insertion(+) diff --git a/sound/ppc/pmac.c b/sound/ppc/pmac.c index e35b48d29c4..392b2abd9f1 100644 --- a/sound/ppc/pmac.c +++ b/sound/ppc/pmac.c @@ -988,6 +988,7 @@ static int __init snd_pmac_detect(pmac_t *chip) case 0x33: case 0x29: case 0x24: + case 0x50: case 0x5c: chip->num_freqs = ARRAY_SIZE(tumbler_freqs); chip->model = PMAC_SNAPPER; -- cgit v1.2.3 From f542fda8f8cd0cc0e4bffef42b27c7dc59cd07d3 Mon Sep 17 00:00:00 2001 From: Clemens Ladisch Date: Tue, 20 Sep 2005 09:06:36 +0200 Subject: [ALSA] usb-audio: add more Yamaha USB MIDI devices USB generic driver Add quirk entries for four unknown Yamaha USB MIDI devices. Signed-off-by: Clemens Ladisch --- sound/usb/usbquirks.h | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/sound/usb/usbquirks.h b/sound/usb/usbquirks.h index 36f9a3b8694..5c6b3da93e3 100644 --- a/sound/usb/usbquirks.h +++ b/sound/usb/usbquirks.h @@ -117,6 +117,10 @@ YAMAHA_DEVICE(0x103a, NULL), YAMAHA_DEVICE(0x103b, NULL), YAMAHA_DEVICE(0x103c, NULL), YAMAHA_DEVICE(0x103d, NULL), +YAMAHA_DEVICE(0x103e, NULL), +YAMAHA_DEVICE(0x103f, NULL), +YAMAHA_DEVICE(0x1040, NULL), +YAMAHA_DEVICE(0x1041, NULL), YAMAHA_DEVICE(0x2000, "DGP-7"), YAMAHA_DEVICE(0x2001, "DGP-5"), YAMAHA_DEVICE(0x2002, NULL), -- cgit v1.2.3 From 31ab9523ed3773d5de7c07b3b6c4c00ddb06045e Mon Sep 17 00:00:00 2001 From: Clemens Ladisch Date: Mon, 26 Sep 2005 08:55:01 +0200 Subject: [ALSA] usb-audio: add another ID for the TerraTec PHASE26 USB generic driver There is another revision of the PHASE26 with a different product ID; add a quirk entry for that, too. Signed-off-by: Clemens Ladisch --- sound/usb/usbquirks.h | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/sound/usb/usbquirks.h b/sound/usb/usbquirks.h index 5c6b3da93e3..370f0e3c6e2 100644 --- a/sound/usb/usbquirks.h +++ b/sound/usb/usbquirks.h @@ -1356,10 +1356,20 @@ YAMAHA_DEVICE(0x7010, "UB99"), } }, +/* TerraTec devices */ +{ + USB_DEVICE_VENDOR_SPEC(0x0ccd, 0x0012), + .driver_info = (unsigned long) & (const snd_usb_audio_quirk_t) { + .vendor_name = "TerraTec", + .product_name = "PHASE 26", + .ifnum = 3, + .type = QUIRK_MIDI_STANDARD_INTERFACE + } +}, { USB_DEVICE_VENDOR_SPEC(0x0ccd, 0x0013), .driver_info = (unsigned long) & (const snd_usb_audio_quirk_t) { - .vendor_name = "Terratec", + .vendor_name = "TerraTec", .product_name = "PHASE 26", .ifnum = 3, .type = QUIRK_MIDI_STANDARD_INTERFACE -- cgit v1.2.3 From d31cbbfd80a84696847913b7486a998481038663 Mon Sep 17 00:00:00 2001 From: Clemens Ladisch Date: Mon, 26 Sep 2005 09:59:57 +0200 Subject: [ALSA] usb-audio: increase max buffer size USB generic driver Increase the maximum PCM buffer size to 1 MB. The USB driver doesn't have any inherent buffer size limit, and big multichannel interfaces may benefit from this. Signed-off-by: Clemens Ladisch --- sound/usb/usbaudio.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/sound/usb/usbaudio.c b/sound/usb/usbaudio.c index d5ae2055b89..2ead878bcb8 100644 --- a/sound/usb/usbaudio.c +++ b/sound/usb/usbaudio.c @@ -1444,9 +1444,9 @@ static snd_pcm_hardware_t snd_usb_playback = SNDRV_PCM_INFO_BATCH | SNDRV_PCM_INFO_INTERLEAVED | SNDRV_PCM_INFO_BLOCK_TRANSFER, - .buffer_bytes_max = (256*1024), + .buffer_bytes_max = 1024 * 1024, .period_bytes_min = 64, - .period_bytes_max = (128*1024), + .period_bytes_max = 512 * 1024, .periods_min = 2, .periods_max = 1024, }; @@ -1458,9 +1458,9 @@ static snd_pcm_hardware_t snd_usb_capture = SNDRV_PCM_INFO_BATCH | SNDRV_PCM_INFO_INTERLEAVED | SNDRV_PCM_INFO_BLOCK_TRANSFER, - .buffer_bytes_max = (256*1024), + .buffer_bytes_max = 1024 * 1024, .period_bytes_min = 64, - .period_bytes_max = (128*1024), + .period_bytes_max = 512 * 1024, .periods_min = 2, .periods_max = 1024, }; -- cgit v1.2.3 From a7175aab3f5cffe3c79575e56dfcfe87a41a74c7 Mon Sep 17 00:00:00 2001 From: "John W. Linville" Date: Thu, 29 Sep 2005 13:13:38 +0200 Subject: [ALSA] fix HD audio ALC260 mono (un)mute HDA Codec driver The ALC260 'Mono Playback Switch' is marked as an output in patch_realtek.c. It actually does not work unless it is marked as an input. Go figure... This was tested and confirmed on an HP xw4300. Signed-off-by: John W. Linville Signed-off-by: Takashi Iwai --- sound/pci/hda/patch_realtek.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index 849b5b50c92..9aca9b4e813 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -2243,7 +2243,7 @@ static snd_kcontrol_new_t alc260_base_mixer[] = { HDA_CODEC_VOLUME("Headphone Playback Volume", 0x09, 0x0, HDA_OUTPUT), ALC_BIND_MUTE("Headphone Playback Switch", 0x09, 2, HDA_INPUT), HDA_CODEC_VOLUME_MONO("Mono Playback Volume", 0x0a, 1, 0x0, HDA_OUTPUT), - ALC_BIND_MUTE_MONO("Mono Playback Switch", 0x0a, 1, 2, HDA_OUTPUT), + ALC_BIND_MUTE_MONO("Mono Playback Switch", 0x0a, 1, 2, HDA_INPUT), HDA_CODEC_VOLUME("Capture Volume", 0x04, 0x0, HDA_INPUT), HDA_CODEC_MUTE("Capture Switch", 0x04, 0x0, HDA_INPUT), { @@ -2270,7 +2270,7 @@ static snd_kcontrol_new_t alc260_hp_mixer[] = { HDA_CODEC_VOLUME("Headphone Playback Volume", 0x09, 0x0, HDA_OUTPUT), ALC_BIND_MUTE("Headphone Playback Switch", 0x09, 2, HDA_INPUT), HDA_CODEC_VOLUME_MONO("Mono Playback Volume", 0x0a, 1, 0x0, HDA_OUTPUT), - ALC_BIND_MUTE_MONO("Mono Playback Switch", 0x0a, 1, 2, HDA_OUTPUT), + ALC_BIND_MUTE_MONO("Mono Playback Switch", 0x0a, 1, 2, HDA_INPUT), HDA_CODEC_VOLUME("Capture Volume", 0x05, 0x0, HDA_INPUT), HDA_CODEC_MUTE("Capture Switch", 0x05, 0x0, HDA_INPUT), { -- cgit v1.2.3 From 1c1fa8b69e6d538bcc1e58791938b31a2354ee65 Mon Sep 17 00:00:00 2001 From: "John W. Linville" Date: Thu, 29 Sep 2005 13:18:41 +0200 Subject: [ALSA] fix alc880_test_mixer typo HDA Codec driver Fix a typo (cut & paste) in the alc880_test_mixer structure. Signed-off-by: John W. Linville Signed-off-by: Takashi Iwai --- sound/pci/hda/patch_realtek.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index 9aca9b4e813..f62597e576d 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -1385,8 +1385,8 @@ static snd_kcontrol_new_t alc880_test_mixer[] = { HDA_CODEC_VOLUME("Side Playback Volume", 0x0f, 0x0, HDA_OUTPUT), ALC_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT), ALC_BIND_MUTE("Surround Playback Switch", 0x0d, 2, HDA_INPUT), - ALC_BIND_MUTE("CLFE Playback Volume", 0x0e, 2, HDA_INPUT), - ALC_BIND_MUTE("Side Playback Volume", 0x0f, 2, HDA_INPUT), + ALC_BIND_MUTE("CLFE Playback Switch", 0x0e, 2, HDA_INPUT), + ALC_BIND_MUTE("Side Playback Switch", 0x0f, 2, HDA_INPUT), PIN_CTL_TEST("Front Pin Mode", 0x14), PIN_CTL_TEST("Surround Pin Mode", 0x15), PIN_CTL_TEST("CLFE Pin Mode", 0x16), -- cgit v1.2.3 From 92447f3f1a1c1af418eb1dfee85a7685d9b9a3ef Mon Sep 17 00:00:00 2001 From: "John W. Linville" Date: Thu, 29 Sep 2005 13:20:45 +0200 Subject: [ALSA] fix HD audio ALC882 lfe (un)mute HDA Codec driver Mark the ALC882 'LFE Playback Switch' as an input, like the other playback switch settings. Signed-off-by: John W. Linville Signed-off-by: Takashi Iwai --- sound/pci/hda/patch_realtek.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index f62597e576d..429e4786f7c 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -2501,7 +2501,7 @@ static snd_kcontrol_new_t alc882_base_mixer[] = { HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x0e, 1, 0x0, HDA_OUTPUT), HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x0e, 2, 0x0, HDA_OUTPUT), ALC_BIND_MUTE_MONO("Center Playback Switch", 0x0e, 1, 2, HDA_INPUT), - ALC_BIND_MUTE_MONO("LFE Playback Switch", 0x0e, 2, 2, HDA_OUTPUT), + ALC_BIND_MUTE_MONO("LFE Playback Switch", 0x0e, 2, 2, HDA_INPUT), HDA_CODEC_VOLUME("Side Playback Volume", 0x0f, 0x0, HDA_OUTPUT), ALC_BIND_MUTE("Side Playback Switch", 0x0f, 2, HDA_INPUT), HDA_CODEC_MUTE("Headphone Playback Switch", 0x1b, 0x0, HDA_OUTPUT), -- cgit v1.2.3 From 35451088f445955fe460a38b25b97c263ff35033 Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Thu, 29 Sep 2005 13:25:14 +0200 Subject: [ALSA] Fix confliction of capture controls on ALC880 test model HDA Codec driver Fixed the confliction of capture controls on ALC880 'test' model. Signed-off-by: Takashi Iwai --- sound/pci/hda/patch_realtek.c | 12 ------------ 1 file changed, 12 deletions(-) diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index 429e4786f7c..7327deb6df9 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -1409,18 +1409,6 @@ static snd_kcontrol_new_t alc880_test_mixer[] = { HDA_CODEC_MUTE("In-4 Playback Switch", 0x0b, 0x3, HDA_INPUT), HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x4, HDA_INPUT), HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x4, HDA_INPUT), - HDA_CODEC_VOLUME("Capture Volume", 0x08, 0x0, HDA_INPUT), - HDA_CODEC_MUTE("Capture Switch", 0x08, 0x0, HDA_INPUT), - HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x09, 0x0, HDA_INPUT), - HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x09, 0x0, HDA_INPUT), - { - .iface = SNDRV_CTL_ELEM_IFACE_MIXER, - .name = "Input Source", - .count = 2, - .info = alc_mux_enum_info, - .get = alc_mux_enum_get, - .put = alc_mux_enum_put, - }, { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = "Channel Mode", -- cgit v1.2.3 From c66186e1c966e7e115a86af55597c05c5512014b Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Thu, 29 Sep 2005 13:49:44 +0200 Subject: [ALSA] via82xx - dxs_support entry for an ASUS mobo VIA82xx driver Addded a dxs_support entry for an ASUS mobo. Signed-off-by: Takashi Iwai --- sound/pci/via82xx.c | 1 + 1 file changed, 1 insertion(+) diff --git a/sound/pci/via82xx.c b/sound/pci/via82xx.c index 964113ffa60..3c0205b91e1 100644 --- a/sound/pci/via82xx.c +++ b/sound/pci/via82xx.c @@ -2153,6 +2153,7 @@ static int __devinit check_dxs_list(struct pci_dev *pci) { .subvendor = 0x1043, .subdevice = 0x8095, .action = VIA_DXS_NO_VRA }, /* ASUS A7V8X (FIXME: possibly VIA_DXS_ENABLE?)*/ { .subvendor = 0x1043, .subdevice = 0x80a1, .action = VIA_DXS_NO_VRA }, /* ASUS A7V8-X */ { .subvendor = 0x1043, .subdevice = 0x80b0, .action = VIA_DXS_NO_VRA }, /* ASUS A7V600 & K8V*/ + { .subvendor = 0x1043, .subdevice = 0x810d, .action = VIA_DXS_SRC }, /* ASUS */ { .subvendor = 0x1043, .subdevice = 0x812a, .action = VIA_DXS_SRC }, /* ASUS A8V Deluxe */ { .subvendor = 0x1071, .subdevice = 0x8375, .action = VIA_DXS_NO_VRA }, /* Vobis/Yakumo/Mitac notebook */ { .subvendor = 0x1071, .subdevice = 0x8399, .action = VIA_DXS_NO_VRA }, /* Umax AB 595T (VIA K8N800A - VT8237) */ -- cgit v1.2.3 From f12aa40c9d76af5add413731d30565327219c41f Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Fri, 30 Sep 2005 16:56:59 +0200 Subject: [ALSA] emu10k1 - Fix loading of SBLive Game board EMU10K1/EMU10K2 driver Fixed the error at loading SBLive Game board (and possible other models). The PCI SSIDs of this board conflicts with SB Live 5.1 Platinum, which has no AC97 chip. Signed-off-by: Takashi Iwai --- include/sound/emu10k1.h | 2 +- sound/pci/emu10k1/emu10k1_main.c | 5 ++++- sound/pci/emu10k1/emumixer.c | 10 ++++++++-- 3 files changed, 13 insertions(+), 4 deletions(-) diff --git a/include/sound/emu10k1.h b/include/sound/emu10k1.h index 67bf3f18e96..14cb2718cb7 100644 --- a/include/sound/emu10k1.h +++ b/include/sound/emu10k1.h @@ -1059,7 +1059,7 @@ typedef struct { unsigned char spk71; /* Has 7.1 speakers */ unsigned char sblive51; /* SBLive! 5.1 - extout 0x11 -> center, 0x12 -> lfe */ unsigned char spdif_bug; /* Has Spdif phasing bug */ - unsigned char ac97_chip; /* Has an AC97 chip */ + unsigned char ac97_chip; /* Has an AC97 chip: 1 = mandatory, 2 = optional */ unsigned char ecard; /* APS EEPROM */ const char *driver; const char *name; diff --git a/sound/pci/emu10k1/emu10k1_main.c b/sound/pci/emu10k1/emu10k1_main.c index e87e8427f25..e9cd8e054f2 100644 --- a/sound/pci/emu10k1/emu10k1_main.c +++ b/sound/pci/emu10k1/emu10k1_main.c @@ -756,9 +756,12 @@ static emu_chip_details_t emu_chip_details[] = { .sblive51 = 1} , /* Tested by alsa bugtrack user "hus" bug #1297 12th Aug 2005 */ {.vendor = 0x1102, .device = 0x0002, .subsystem = 0x80611102, - .driver = "EMU10K1", .name = "SBLive! Platinum 5.1 [SB0060]", + .driver = "EMU10K1", .name = "SBLive 5.1 [SB0060]", .id = "Live", .emu10k1_chip = 1, + .ac97_chip = 2, /* ac97 is optional; both SBLive 5.1 and platinum + * share the same IDs! + */ .sblive51 = 1} , {.vendor = 0x1102, .device = 0x0002, .subsystem = 0x80511102, .driver = "EMU10K1", .name = "SBLive! Value [CT4850]", diff --git a/sound/pci/emu10k1/emumixer.c b/sound/pci/emu10k1/emumixer.c index d71a72e84bc..6994f90bb83 100644 --- a/sound/pci/emu10k1/emumixer.c +++ b/sound/pci/emu10k1/emumixer.c @@ -802,8 +802,13 @@ int __devinit snd_emu10k1_mixer(emu10k1_t *emu, .read = snd_emu10k1_ac97_read, }; - if ((err = snd_ac97_bus(emu->card, 0, &ops, NULL, &pbus)) < 0) - return err; + if ((err = snd_ac97_bus(emu->card, 0, &ops, NULL, &pbus)) < 0) { + if (emu->card_capabilities->ac97_chip == 1) + return err; + snd_printd(KERN_INFO "emu10k1: AC97 is optional on this board\n"); + snd_printd(KERN_INFO" Proceeding without ac97 mixers...\n"); + goto no_ac97; /* FIXME: get rid of ugly gotos.. */ + } pbus->no_vra = 1; /* we don't need VRA */ memset(&ac97, 0, sizeof(ac97)); @@ -836,6 +841,7 @@ int __devinit snd_emu10k1_mixer(emu10k1_t *emu, for (; *c; c++) remove_ctl(card, *c); } else { + no_ac97: if (emu->card_capabilities->ecard) strcpy(emu->card->mixername, "EMU APS"); else if (emu->audigy) -- cgit v1.2.3 From 315e3bd717068624ce888f3d045a168acefc6ce8 Mon Sep 17 00:00:00 2001 From: Clemens Ladisch Date: Tue, 4 Oct 2005 08:42:10 +0200 Subject: [ALSA] korg1212: fix typo KORG1212 driver Add a missing comma that made the stateName array one entry too short. Signed-off-by: Clemens Ladisch --- sound/pci/korg1212/korg1212.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sound/pci/korg1212/korg1212.c b/sound/pci/korg1212/korg1212.c index 09f9cbe116a..5561fd4091e 100644 --- a/sound/pci/korg1212/korg1212.c +++ b/sound/pci/korg1212/korg1212.c @@ -442,7 +442,7 @@ static char* stateName[] = { "Setup for play", "Playing", "Monitor mode on", - "Calibrating" + "Calibrating", "Invalid" }; -- cgit v1.2.3 From b150869369adafb7cc0cf65ea500f9f3c4bbf857 Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Tue, 4 Oct 2005 13:49:32 +0200 Subject: [ALSA] emu10k1 - Fix handling of ac97_chip=2 EMU10K1/EMU10K2 driver Fixed the handling of ac97_chip=2 capability type. The error occurs in snd_ac97_mixer(), not in snd_ac97_bus(). Also, release the unnecessary ac97_bus object in the error path. Signed-off-by: Takashi Iwai --- sound/pci/emu10k1/emumixer.c | 19 ++++++++++--------- 1 file changed, 10 insertions(+), 9 deletions(-) diff --git a/sound/pci/emu10k1/emumixer.c b/sound/pci/emu10k1/emumixer.c index 6994f90bb83..7cc831ccd0c 100644 --- a/sound/pci/emu10k1/emumixer.c +++ b/sound/pci/emu10k1/emumixer.c @@ -802,21 +802,22 @@ int __devinit snd_emu10k1_mixer(emu10k1_t *emu, .read = snd_emu10k1_ac97_read, }; - if ((err = snd_ac97_bus(emu->card, 0, &ops, NULL, &pbus)) < 0) { - if (emu->card_capabilities->ac97_chip == 1) - return err; - snd_printd(KERN_INFO "emu10k1: AC97 is optional on this board\n"); - snd_printd(KERN_INFO" Proceeding without ac97 mixers...\n"); - goto no_ac97; /* FIXME: get rid of ugly gotos.. */ - } + if ((err = snd_ac97_bus(emu->card, 0, &ops, NULL, &pbus)) < 0) + return err; pbus->no_vra = 1; /* we don't need VRA */ memset(&ac97, 0, sizeof(ac97)); ac97.private_data = emu; ac97.private_free = snd_emu10k1_mixer_free_ac97; ac97.scaps = AC97_SCAP_NO_SPDIF; - if ((err = snd_ac97_mixer(pbus, &ac97, &emu->ac97)) < 0) - return err; + if ((err = snd_ac97_mixer(pbus, &ac97, &emu->ac97)) < 0) { + if (emu->card_capabilities->ac97_chip == 1) + return err; + snd_printd(KERN_INFO "emu10k1: AC97 is optional on this board\n"); + snd_printd(KERN_INFO" Proceeding without ac97 mixers...\n"); + snd_device_free(emu->card, pbus); + goto no_ac97; /* FIXME: get rid of ugly gotos.. */ + } if (emu->audigy) { /* set master volume to 0 dB */ snd_ac97_write(emu->ac97, AC97_MASTER, 0x0000); -- cgit v1.2.3 From 4d060fd16946d767ee903804c6769a26d7da7ab2 Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Tue, 4 Oct 2005 13:50:44 +0200 Subject: [ALSA] ali5451 - Don't build non-existing modem PCM ALI5451 driver Don't build the modem PCM if the corresponding codec isn't detected. Signed-off-by: Takashi Iwai --- sound/pci/ali5451/ali5451.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/sound/pci/ali5451/ali5451.c b/sound/pci/ali5451/ali5451.c index d683f7736a6..f35b558c29b 100644 --- a/sound/pci/ali5451/ali5451.c +++ b/sound/pci/ali5451/ali5451.c @@ -1993,8 +1993,10 @@ static int __devinit snd_ali_mixer(ali_t * codec) if ((err = snd_ac97_mixer(codec->ac97_bus, &ac97, &codec->ac97[i])) < 0) { snd_printk("ali mixer %d creating error.\n", i); if(i == 0) - return err; - } + return err; + codec->num_of_codecs = 1; + break; + } } if (codec->spdif_support) { -- cgit v1.2.3 From 9c9565f709f28c12dadfe74b31f2c86ffd75f71e Mon Sep 17 00:00:00 2001 From: Clemens Ladisch Date: Wed, 5 Oct 2005 13:02:38 +0200 Subject: [ALSA] usb-audio: add another ID for Hercules DJ Console USB generic driver Add a mixer quirk entry for the Hercules DJ Console (Windows Edition) that uses a different USB product ID. Signed-off-by: Clemens Ladisch --- sound/usb/usbmixer_maps.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/sound/usb/usbmixer_maps.c b/sound/usb/usbmixer_maps.c index 13199ff36d4..c1264434e50 100644 --- a/sound/usb/usbmixer_maps.c +++ b/sound/usb/usbmixer_maps.c @@ -238,7 +238,12 @@ static struct usbmix_ctl_map usbmix_ctl_maps[] = { .selector_map = audigy2nx_selectors, }, { - /* Hercules DJ Console */ + /* Hercules DJ Console (Windows Edition) */ + .id = USB_ID(0x06f8, 0xb000), + .ignore_ctl_error = 1, + }, + { + /* Hercules DJ Console (Macintosh Edition) */ .id = USB_ID(0x06f8, 0xd002), .ignore_ctl_error = 1, }, -- cgit v1.2.3 From a25f175c2f6962c38cdbacfc4b66b297f4fb54b2 Mon Sep 17 00:00:00 2001 From: Clemens Ladisch Date: Wed, 5 Oct 2005 13:23:19 +0200 Subject: [ALSA] usb-audio: add MIDI quirk for Hercules DJ Console USB generic driver Add a quirk entry for the external MIDI ports of the Windows Edition of the Hercules DJ Console. Signed-off-by: Clemens Ladisch --- sound/usb/usbquirks.h | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/sound/usb/usbquirks.h b/sound/usb/usbquirks.h index 370f0e3c6e2..948759da656 100644 --- a/sound/usb/usbquirks.h +++ b/sound/usb/usbquirks.h @@ -1028,6 +1028,27 @@ YAMAHA_DEVICE(0x7010, "UB99"), } }, +/* Guillemot devices */ +{ + /* + * This is for the "Windows Edition" where the external MIDI ports are + * the only MIDI ports; the control data is reported through HID + * interfaces. The "Macintosh Edition" has ID 0xd002 and uses standard + * compliant USB MIDI ports for external MIDI and controls. + */ + USB_DEVICE_VENDOR_SPEC(0x06f8, 0xb000), + .driver_info = (unsigned long) & (const snd_usb_audio_quirk_t) { + .vendor_name = "Hercules", + .product_name = "DJ Console (WE)", + .ifnum = 4, + .type = QUIRK_MIDI_FIXED_ENDPOINT, + .data = & (const snd_usb_midi_endpoint_info_t) { + .out_cables = 0x0001, + .in_cables = 0x0001 + } + } +}, + /* Midiman/M-Audio devices */ { USB_DEVICE_VENDOR_SPEC(0x0763, 0x1002), -- cgit v1.2.3 From d85c3553df5e24cb3117385f0a17e1cc0436d148 Mon Sep 17 00:00:00 2001 From: Tom 'spot' Callaway Date: Fri, 7 Oct 2005 13:05:56 -0700 Subject: [SPARC]: Fix p9100 framebuffer in 2.6 The attached patch fixes the p9100 framebuffer so that text is viewable (not black on black, like it was before the patch). The linux logo displays for a very short period of time, then is replaced by a grey box. This leads me to believe that this framebuffer would have problems in X, but since there hasn't been a weitek driver for X in several millennia, this isn't something that I can confirm or deny. But this patch does get color console working on my SPARCbook 3TX. Signed-off-by: Tom 'spot' Callaway Signed-off-by: David S. Miller --- drivers/video/p9100.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/video/p9100.c b/drivers/video/p9100.c index 7808a01493a..b76a5a9a125 100644 --- a/drivers/video/p9100.c +++ b/drivers/video/p9100.c @@ -288,6 +288,9 @@ static void p9100_init_one(struct sbus_dev *sdev) all->par.physbase = sdev->reg_addrs[2].phys_addr; sbusfb_fill_var(&all->info.var, sdev->prom_node, 8); + all->info.var.red.length = 8; + all->info.var.green.length = 8; + all->info.var.blue.length = 8; linebytes = prom_getintdefault(sdev->prom_node, "linebytes", all->info.var.xres); @@ -323,6 +326,7 @@ static void p9100_init_one(struct sbus_dev *sdev) kfree(all); return; } + fb_set_cmap(&all->info.cmap, &all->info); list_add(&all->list, &p9100_list); -- cgit v1.2.3 From ba6399334dd8a75bd295de26496196c720abae0a Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Fri, 7 Oct 2005 13:30:49 -0700 Subject: [SPARC64]: Fix userland FPU state corruption. We need to use stricter memory barriers around the block load and store instructions we use to save and restore the FPU register file. Signed-off-by: David S. Miller --- arch/sparc64/kernel/entry.S | 39 +++++++++++++++++++++------------------ arch/sparc64/kernel/rtrap.S | 7 ++++--- arch/sparc64/lib/VISsave.S | 8 +++++--- 3 files changed, 30 insertions(+), 24 deletions(-) diff --git a/arch/sparc64/kernel/entry.S b/arch/sparc64/kernel/entry.S index f685035dbdb..11a848402fb 100644 --- a/arch/sparc64/kernel/entry.S +++ b/arch/sparc64/kernel/entry.S @@ -33,7 +33,7 @@ /* This is trivial with the new code... */ .globl do_fpdis do_fpdis: - sethi %hi(TSTATE_PEF), %g4 ! IEU0 + sethi %hi(TSTATE_PEF), %g4 rdpr %tstate, %g5 andcc %g5, %g4, %g0 be,pt %xcc, 1f @@ -50,18 +50,18 @@ do_fpdis: add %g0, %g0, %g0 ba,a,pt %xcc, rtrap_clr_l6 -1: ldub [%g6 + TI_FPSAVED], %g5 ! Load Group - wr %g0, FPRS_FEF, %fprs ! LSU Group+4bubbles - andcc %g5, FPRS_FEF, %g0 ! IEU1 Group - be,a,pt %icc, 1f ! CTI - clr %g7 ! IEU0 - ldx [%g6 + TI_GSR], %g7 ! Load Group -1: andcc %g5, FPRS_DL, %g0 ! IEU1 - bne,pn %icc, 2f ! CTI - fzero %f0 ! FPA - andcc %g5, FPRS_DU, %g0 ! IEU1 Group - bne,pn %icc, 1f ! CTI - fzero %f2 ! FPA +1: ldub [%g6 + TI_FPSAVED], %g5 + wr %g0, FPRS_FEF, %fprs + andcc %g5, FPRS_FEF, %g0 + be,a,pt %icc, 1f + clr %g7 + ldx [%g6 + TI_GSR], %g7 +1: andcc %g5, FPRS_DL, %g0 + bne,pn %icc, 2f + fzero %f0 + andcc %g5, FPRS_DU, %g0 + bne,pn %icc, 1f + fzero %f2 faddd %f0, %f2, %f4 fmuld %f0, %f2, %f6 faddd %f0, %f2, %f8 @@ -104,8 +104,10 @@ do_fpdis: add %g6, TI_FPREGS + 0xc0, %g2 faddd %f0, %f2, %f8 fmuld %f0, %f2, %f10 - ldda [%g1] ASI_BLK_S, %f32 ! grrr, where is ASI_BLK_NUCLEUS 8-( + membar #Sync + ldda [%g1] ASI_BLK_S, %f32 ldda [%g2] ASI_BLK_S, %f48 + membar #Sync faddd %f0, %f2, %f12 fmuld %f0, %f2, %f14 faddd %f0, %f2, %f16 @@ -116,7 +118,6 @@ do_fpdis: fmuld %f0, %f2, %f26 faddd %f0, %f2, %f28 fmuld %f0, %f2, %f30 - membar #Sync b,pt %xcc, fpdis_exit nop 2: andcc %g5, FPRS_DU, %g0 @@ -133,8 +134,10 @@ do_fpdis: add %g6, TI_FPREGS + 0x40, %g2 faddd %f32, %f34, %f36 fmuld %f32, %f34, %f38 - ldda [%g1] ASI_BLK_S, %f0 ! grrr, where is ASI_BLK_NUCLEUS 8-( + membar #Sync + ldda [%g1] ASI_BLK_S, %f0 ldda [%g2] ASI_BLK_S, %f16 + membar #Sync faddd %f32, %f34, %f40 fmuld %f32, %f34, %f42 faddd %f32, %f34, %f44 @@ -147,7 +150,6 @@ do_fpdis: fmuld %f32, %f34, %f58 faddd %f32, %f34, %f60 fmuld %f32, %f34, %f62 - membar #Sync ba,pt %xcc, fpdis_exit nop 3: mov SECONDARY_CONTEXT, %g3 @@ -158,7 +160,8 @@ do_fpdis: stxa %g2, [%g3] ASI_DMMU membar #Sync mov 0x40, %g2 - ldda [%g1] ASI_BLK_S, %f0 ! grrr, where is ASI_BLK_NUCLEUS 8-( + membar #Sync + ldda [%g1] ASI_BLK_S, %f0 ldda [%g1 + %g2] ASI_BLK_S, %f16 add %g1, 0x80, %g1 ldda [%g1] ASI_BLK_S, %f32 diff --git a/arch/sparc64/kernel/rtrap.S b/arch/sparc64/kernel/rtrap.S index ecfb42a69a4..090dcca00d2 100644 --- a/arch/sparc64/kernel/rtrap.S +++ b/arch/sparc64/kernel/rtrap.S @@ -312,32 +312,33 @@ kern_fpucheck: ldub [%g6 + TI_FPDEPTH], %l5 wr %g1, FPRS_FEF, %fprs ldx [%o1 + %o5], %g1 add %g6, TI_XFSR, %o1 - membar #StoreLoad | #LoadLoad sll %o0, 8, %o2 add %g6, TI_FPREGS, %o3 brz,pn %l6, 1f add %g6, TI_FPREGS+0x40, %o4 + membar #Sync ldda [%o3 + %o2] ASI_BLK_P, %f0 ldda [%o4 + %o2] ASI_BLK_P, %f16 + membar #Sync 1: andcc %l2, FPRS_DU, %g0 be,pn %icc, 1f wr %g1, 0, %gsr add %o2, 0x80, %o2 + membar #Sync ldda [%o3 + %o2] ASI_BLK_P, %f32 ldda [%o4 + %o2] ASI_BLK_P, %f48 - 1: membar #Sync ldx [%o1 + %o5], %fsr 2: stb %l5, [%g6 + TI_FPDEPTH] ba,pt %xcc, rt_continue nop 5: wr %g0, FPRS_FEF, %fprs - membar #StoreLoad | #LoadLoad sll %o0, 8, %o2 add %g6, TI_FPREGS+0x80, %o3 add %g6, TI_FPREGS+0xc0, %o4 + membar #Sync ldda [%o3 + %o2] ASI_BLK_P, %f32 ldda [%o4 + %o2] ASI_BLK_P, %f48 membar #Sync diff --git a/arch/sparc64/lib/VISsave.S b/arch/sparc64/lib/VISsave.S index 4e18989bd60..a0ded5c5aa5 100644 --- a/arch/sparc64/lib/VISsave.S +++ b/arch/sparc64/lib/VISsave.S @@ -59,15 +59,17 @@ vis1: ldub [%g6 + TI_FPSAVED], %g3 be,pn %icc, 9b add %g6, TI_FPREGS, %g2 andcc %o5, FPRS_DL, %g0 - membar #StoreStore | #LoadStore be,pn %icc, 4f add %g6, TI_FPREGS+0x40, %g3 + membar #Sync stda %f0, [%g2 + %g1] ASI_BLK_P stda %f16, [%g3 + %g1] ASI_BLK_P + membar #Sync andcc %o5, FPRS_DU, %g0 be,pn %icc, 5f 4: add %g1, 128, %g1 + membar #Sync stda %f32, [%g2 + %g1] ASI_BLK_P stda %f48, [%g3 + %g1] ASI_BLK_P @@ -87,7 +89,7 @@ vis1: ldub [%g6 + TI_FPSAVED], %g3 sll %g1, 5, %g1 add %g6, TI_FPREGS+0xc0, %g3 wr %g0, FPRS_FEF, %fprs - membar #StoreStore | #LoadStore + membar #Sync stda %f32, [%g2 + %g1] ASI_BLK_P stda %f48, [%g3 + %g1] ASI_BLK_P membar #Sync @@ -128,8 +130,8 @@ VISenterhalf: be,pn %icc, 4f add %g6, TI_FPREGS, %g2 - membar #StoreStore | #LoadStore add %g6, TI_FPREGS+0x40, %g3 + membar #Sync stda %f0, [%g2 + %g1] ASI_BLK_P stda %f16, [%g3 + %g1] ASI_BLK_P membar #Sync -- cgit v1.2.3 From 4f55cd105c38af4aa157804729d694f864fbc78a Mon Sep 17 00:00:00 2001 From: Jean-Denis Boyer Date: Fri, 7 Oct 2005 13:44:35 -0700 Subject: [ATM]: [br2684] if we free the skb, we should return 0 From: "Jean-Denis Boyer" Signed-off-by: Chas Williams Signed-off-by: David S. Miller --- net/atm/br2684.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/atm/br2684.c b/net/atm/br2684.c index 289956c4dd3..72f3f7b8de8 100644 --- a/net/atm/br2684.c +++ b/net/atm/br2684.c @@ -220,7 +220,7 @@ static int br2684_start_xmit(struct sk_buff *skb, struct net_device *dev) /* netif_stop_queue(dev); */ dev_kfree_skb(skb); read_unlock(&devs_lock); - return -EUNATCH; + return 0; } if (!br2684_xmit_vcc(skb, brdev, brvcc)) { /* -- cgit v1.2.3 From 788e05a67c343fa22f2ae1d3ca264e7f15c25eaf Mon Sep 17 00:00:00 2001 From: Oleg Nesterov Date: Fri, 7 Oct 2005 17:46:19 +0400 Subject: [PATCH] fix do_coredump() vs SIGSTOP race Let's suppose we have 2 threads in thread group: A - does coredump B - has pending SIGSTOP thread A thread B do_coredump: get_signal_to_deliver: lock(->sighand) ->signal->flags = SIGNAL_GROUP_EXIT unlock(->sighand) lock(->sighand) signr = dequeue_signal() ->signal->flags |= SIGNAL_STOP_DEQUEUED return SIGSTOP; do_signal_stop: unlock(->sighand) coredump_wait: zap_threads: lock(tasklist_lock) send SIGKILL to B // signal_wake_up() does nothing unlock(tasklist_lock) lock(tasklist_lock) lock(->sighand) re-check sig->flags & SIGNAL_STOP_DEQUEUED, yes set_current_state(TASK_STOPPED); finish_stop: schedule(); // ->state == TASK_STOPPED wait_for_completion(&startup_done) // waits for complete() from B, // ->state == TASK_UNINTERRUPTIBLE We can't wake up 'B' in any way: SIGCONT will be ignored because handle_stop_signal() sees ->signal->flags & SIGNAL_GROUP_EXIT. sys_kill(SIGKILL)->__group_complete_signal() will choose uninterruptible 'A', so it can't help. sys_tkill(B, SIGKILL) will be ignored by specific_send_sig_info() because B already has pending SIGKILL. This scenario is not possbile if 'A' does do_group_exit(), because it sets sig->flags = SIGNAL_GROUP_EXIT and delivers SIGKILL to subthreads atomically, holding both tasklist_lock and sighand->lock. That means that do_signal_stop() will notice !SIGNAL_STOP_DEQUEUED after re-locking ->sighand. And it is not possible to any other thread to re-add SIGNAL_STOP_DEQUEUED later, because dequeue_signal() can only return SIGKILL. I think it is better to change do_coredump() to do sigaddset(SIGKILL) and signal_wake_up() under sighand->lock, but this patch is much simpler. Signed-off-by: Oleg Nesterov Signed-off-by: Linus Torvalds --- kernel/signal.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/kernel/signal.c b/kernel/signal.c index 619b027e92b..c135f5aa2c2 100644 --- a/kernel/signal.c +++ b/kernel/signal.c @@ -578,7 +578,8 @@ int dequeue_signal(struct task_struct *tsk, sigset_t *mask, siginfo_t *info) * is to alert stop-signal processing code when another * processor has come along and cleared the flag. */ - tsk->signal->flags |= SIGNAL_STOP_DEQUEUED; + if (!(tsk->signal->flags & SIGNAL_GROUP_EXIT)) + tsk->signal->flags |= SIGNAL_STOP_DEQUEUED; } if ( signr && ((info->si_code & __SI_MASK) == __SI_TIMER) && -- cgit v1.2.3 From c2059b2e0b209a0674c21f78337bb158d3ccb22b Mon Sep 17 00:00:00 2001 From: David Vrabel Date: Fri, 7 Oct 2005 14:43:22 +0100 Subject: [PATCH] yenta: fix build if YENTA && !CARDBUS (struct pcmcia_socket).tune_bridge only exists if CONFIG_CARDBUS is set but building yenta_socket without CardBus is valid. Signed-off-by: David Vrabel Signed-off-by: Linus Torvalds --- drivers/pcmcia/ti113x.h | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/drivers/pcmcia/ti113x.h b/drivers/pcmcia/ti113x.h index da0b404561c..539b5cd1a59 100644 --- a/drivers/pcmcia/ti113x.h +++ b/drivers/pcmcia/ti113x.h @@ -873,6 +873,7 @@ static int ti1250_override(struct yenta_socket *socket) * Some fixup code to make everybody happy (TM). */ +#ifdef CONFIG_CARDBUS /** * set/clear various test bits: * Defaults to clear the bit. @@ -927,7 +928,6 @@ static void ene_tune_bridge(struct pcmcia_socket *sock, struct pci_bus *bus) config_writeb(socket, ENE_TEST_C9, test_c9); } - static int ene_override(struct yenta_socket *socket) { /* install tune_bridge() function */ @@ -935,6 +935,9 @@ static int ene_override(struct yenta_socket *socket) return ti1250_override(socket); } +#else +# define ene_override ti1250_override +#endif #endif /* _LINUX_TI113X_H */ -- cgit v1.2.3 From 74fd92c511bd4a0771ac0faaaef38bb1be3a29f6 Mon Sep 17 00:00:00 2001 From: David Howells Date: Fri, 7 Oct 2005 15:01:09 +0100 Subject: [PATCH] key: plug request_key_auth memleak Plug request_key_auth memleak. This can be triggered by unprivileged users, so is local DoS. Signed-off-by: Chris Wright Signed-Off-By: David Howells Signed-off-by: Linus Torvalds --- security/keys/request_key_auth.c | 1 + 1 file changed, 1 insertion(+) diff --git a/security/keys/request_key_auth.c b/security/keys/request_key_auth.c index 1ecd3d3fa9f..f80a501e27f 100644 --- a/security/keys/request_key_auth.c +++ b/security/keys/request_key_auth.c @@ -96,6 +96,7 @@ static void request_key_auth_destroy(struct key *key) kenter("{%d}", key->serial); key_put(rka->target_key); + kfree(rka); } /* end request_key_auth_destroy() */ -- cgit v1.2.3 From f1a9badcf6ecad9975240d94514721cb93932151 Mon Sep 17 00:00:00 2001 From: David Howells Date: Fri, 7 Oct 2005 15:04:52 +0100 Subject: [PATCH] Keys: Add request-key process documentation The attached patch adds documentation for the process by which request-key works, including how it permits helper processes to gain access to the requestor's keyrings. Signed-Off-By: David Howells Signed-off-by: Linus Torvalds --- Documentation/keys-request-key.txt | 161 +++++++++++++++++++++++++++++++++++++ Documentation/keys.txt | 18 +++-- security/keys/request_key.c | 2 + security/keys/request_key_auth.c | 2 + 4 files changed, 176 insertions(+), 7 deletions(-) create mode 100644 Documentation/keys-request-key.txt diff --git a/Documentation/keys-request-key.txt b/Documentation/keys-request-key.txt new file mode 100644 index 00000000000..5f2b9c5edbb --- /dev/null +++ b/Documentation/keys-request-key.txt @@ -0,0 +1,161 @@ + =================== + KEY REQUEST SERVICE + =================== + +The key request service is part of the key retention service (refer to +Documentation/keys.txt). This document explains more fully how that the +requesting algorithm works. + +The process starts by either the kernel requesting a service by calling +request_key(): + + struct key *request_key(const struct key_type *type, + const char *description, + const char *callout_string); + +Or by userspace invoking the request_key system call: + + key_serial_t request_key(const char *type, + const char *description, + const char *callout_info, + key_serial_t dest_keyring); + +The main difference between the two access points is that the in-kernel +interface does not need to link the key to a keyring to prevent it from being +immediately destroyed. The kernel interface returns a pointer directly to the +key, and it's up to the caller to destroy the key. + +The userspace interface links the key to a keyring associated with the process +to prevent the key from going away, and returns the serial number of the key to +the caller. + + +=========== +THE PROCESS +=========== + +A request proceeds in the following manner: + + (1) Process A calls request_key() [the userspace syscall calls the kernel + interface]. + + (2) request_key() searches the process's subscribed keyrings to see if there's + a suitable key there. If there is, it returns the key. If there isn't, and + callout_info is not set, an error is returned. Otherwise the process + proceeds to the next step. + + (3) request_key() sees that A doesn't have the desired key yet, so it creates + two things: + + (a) An uninstantiated key U of requested type and description. + + (b) An authorisation key V that refers to key U and notes that process A + is the context in which key U should be instantiated and secured, and + from which associated key requests may be satisfied. + + (4) request_key() then forks and executes /sbin/request-key with a new session + keyring that contains a link to auth key V. + + (5) /sbin/request-key execs an appropriate program to perform the actual + instantiation. + + (6) The program may want to access another key from A's context (say a + Kerberos TGT key). It just requests the appropriate key, and the keyring + search notes that the session keyring has auth key V in its bottom level. + + This will permit it to then search the keyrings of process A with the + UID, GID, groups and security info of process A as if it was process A, + and come up with key W. + + (7) The program then does what it must to get the data with which to + instantiate key U, using key W as a reference (perhaps it contacts a + Kerberos server using the TGT) and then instantiates key U. + + (8) Upon instantiating key U, auth key V is automatically revoked so that it + may not be used again. + + (9) The program then exits 0 and request_key() deletes key V and returns key + U to the caller. + +This also extends further. If key W (step 5 above) didn't exist, key W would be +created uninstantiated, another auth key (X) would be created [as per step 3] +and another copy of /sbin/request-key spawned [as per step 4]; but the context +specified by auth key X will still be process A, as it was in auth key V. + +This is because process A's keyrings can't simply be attached to +/sbin/request-key at the appropriate places because (a) execve will discard two +of them, and (b) it requires the same UID/GID/Groups all the way through. + + +====================== +NEGATIVE INSTANTIATION +====================== + +Rather than instantiating a key, it is possible for the possessor of an +authorisation key to negatively instantiate a key that's under construction. +This is a short duration placeholder that causes any attempt at re-requesting +the key whilst it exists to fail with error ENOKEY. + +This is provided to prevent excessive repeated spawning of /sbin/request-key +processes for a key that will never be obtainable. + +Should the /sbin/request-key process exit anything other than 0 or die on a +signal, the key under construction will be automatically negatively +instantiated for a short amount of time. + + +==================== +THE SEARCH ALGORITHM +==================== + +A search of any particular keyring proceeds in the following fashion: + + (1) When the key management code searches for a key (keyring_search_aux) it + firstly calls key_permission(SEARCH) on the keyring it's starting with, + if this denies permission, it doesn't search further. + + (2) It considers all the non-keyring keys within that keyring and, if any key + matches the criteria specified, calls key_permission(SEARCH) on it to see + if the key is allowed to be found. If it is, that key is returned; if + not, the search continues, and the error code is retained if of higher + priority than the one currently set. + + (3) It then considers all the keyring-type keys in the keyring it's currently + searching. It calls key_permission(SEARCH) on each keyring, and if this + grants permission, it recurses, executing steps (2) and (3) on that + keyring. + +The process stops immediately a valid key is found with permission granted to +use it. Any error from a previous match attempt is discarded and the key is +returned. + +When search_process_keyrings() is invoked, it performs the following searches +until one succeeds: + + (1) If extant, the process's thread keyring is searched. + + (2) If extant, the process's process keyring is searched. + + (3) The process's session keyring is searched. + + (4) If the process has a request_key() authorisation key in its session + keyring then: + + (a) If extant, the calling process's thread keyring is searched. + + (b) If extant, the calling process's process keyring is searched. + + (c) The calling process's session keyring is searched. + +The moment one succeeds, all pending errors are discarded and the found key is +returned. + +Only if all these fail does the whole thing fail with the highest priority +error. Note that several errors may have come from LSM. + +The error priority is: + + EKEYREVOKED > EKEYEXPIRED > ENOKEY + +EACCES/EPERM are only returned on a direct search of a specific keyring where +the basal keyring does not grant Search permission. diff --git a/Documentation/keys.txt b/Documentation/keys.txt index b22e7c8d059..4afe03a58c5 100644 --- a/Documentation/keys.txt +++ b/Documentation/keys.txt @@ -361,6 +361,8 @@ The main syscalls are: /sbin/request-key will be invoked in an attempt to obtain a key. The callout_info string will be passed as an argument to the program. + See also Documentation/keys-request-key.txt. + The keyctl syscall functions are: @@ -533,8 +535,8 @@ The keyctl syscall functions are: (*) Read the payload data from a key: - key_serial_t keyctl(KEYCTL_READ, key_serial_t keyring, char *buffer, - size_t buflen); + long keyctl(KEYCTL_READ, key_serial_t keyring, char *buffer, + size_t buflen); This function attempts to read the payload data from the specified key into the buffer. The process must have read permission on the key to @@ -555,9 +557,9 @@ The keyctl syscall functions are: (*) Instantiate a partially constructed key. - key_serial_t keyctl(KEYCTL_INSTANTIATE, key_serial_t key, - const void *payload, size_t plen, - key_serial_t keyring); + long keyctl(KEYCTL_INSTANTIATE, key_serial_t key, + const void *payload, size_t plen, + key_serial_t keyring); If the kernel calls back to userspace to complete the instantiation of a key, userspace should use this call to supply data for the key before the @@ -576,8 +578,8 @@ The keyctl syscall functions are: (*) Negatively instantiate a partially constructed key. - key_serial_t keyctl(KEYCTL_NEGATE, key_serial_t key, - unsigned timeout, key_serial_t keyring); + long keyctl(KEYCTL_NEGATE, key_serial_t key, + unsigned timeout, key_serial_t keyring); If the kernel calls back to userspace to complete the instantiation of a key, userspace should use this call mark the key as negative before the @@ -688,6 +690,8 @@ payload contents" for more information. If successful, the key will have been attached to the default keyring for implicitly obtained request-key keys, as set by KEYCTL_SET_REQKEY_KEYRING. + See also Documentation/keys-request-key.txt. + (*) When it is no longer required, the key should be released using: diff --git a/security/keys/request_key.c b/security/keys/request_key.c index e6dd366d43a..5cc4bba70db 100644 --- a/security/keys/request_key.c +++ b/security/keys/request_key.c @@ -7,6 +7,8 @@ * 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. + * + * See Documentation/keys-request-key.txt */ #include diff --git a/security/keys/request_key_auth.c b/security/keys/request_key_auth.c index f80a501e27f..a8e4069d48c 100644 --- a/security/keys/request_key_auth.c +++ b/security/keys/request_key_auth.c @@ -7,6 +7,8 @@ * 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. + * + * See Documentation/keys-request-key.txt */ #include -- cgit v1.2.3 From 468ed2b0c85ec4310b429e60358213b6d077289e Mon Sep 17 00:00:00 2001 From: David Howells Date: Fri, 7 Oct 2005 15:07:38 +0100 Subject: [PATCH] Keys: Split key permissions checking into a .c file The attached patch splits key permissions checking out of key-ui.h and moves it into a .c file. It's quite large and called quite a lot, and it's about to get bigger with the addition of LSM support for keys... key_any_permission() is also discarded as it's no longer used. Signed-Off-By: David Howells Signed-off-by: Linus Torvalds --- include/linux/key-ui.h | 91 +++------------------------------------------- security/keys/Makefile | 1 + security/keys/permission.c | 70 +++++++++++++++++++++++++++++++++++ 3 files changed, 76 insertions(+), 86 deletions(-) create mode 100644 security/keys/permission.c diff --git a/include/linux/key-ui.h b/include/linux/key-ui.h index 918c34a8347..7a2e332067c 100644 --- a/include/linux/key-ui.h +++ b/include/linux/key-ui.h @@ -38,97 +38,16 @@ struct keyring_list { struct key *keys[0]; }; - /* * check to see whether permission is granted to use a key in the desired way */ -static inline int key_permission(const key_ref_t key_ref, key_perm_t perm) -{ - struct key *key = key_ref_to_ptr(key_ref); - key_perm_t kperm; - - if (is_key_possessed(key_ref)) - kperm = key->perm >> 24; - else if (key->uid == current->fsuid) - kperm = key->perm >> 16; - else if (key->gid != -1 && - key->perm & KEY_GRP_ALL && - in_group_p(key->gid) - ) - kperm = key->perm >> 8; - else - kperm = key->perm; - - kperm = kperm & perm & KEY_ALL; - - return kperm == perm; -} - -/* - * check to see whether permission is granted to use a key in at least one of - * the desired ways - */ -static inline int key_any_permission(const key_ref_t key_ref, key_perm_t perm) -{ - struct key *key = key_ref_to_ptr(key_ref); - key_perm_t kperm; - - if (is_key_possessed(key_ref)) - kperm = key->perm >> 24; - else if (key->uid == current->fsuid) - kperm = key->perm >> 16; - else if (key->gid != -1 && - key->perm & KEY_GRP_ALL && - in_group_p(key->gid) - ) - kperm = key->perm >> 8; - else - kperm = key->perm; +extern int key_task_permission(const key_ref_t key_ref, + struct task_struct *context, + key_perm_t perm); - kperm = kperm & perm & KEY_ALL; - - return kperm != 0; -} - -static inline int key_task_groups_search(struct task_struct *tsk, gid_t gid) -{ - int ret; - - task_lock(tsk); - ret = groups_search(tsk->group_info, gid); - task_unlock(tsk); - return ret; -} - -static inline int key_task_permission(const key_ref_t key_ref, - struct task_struct *context, - key_perm_t perm) +static inline int key_permission(const key_ref_t key_ref, key_perm_t perm) { - struct key *key = key_ref_to_ptr(key_ref); - key_perm_t kperm; - - if (is_key_possessed(key_ref)) { - kperm = key->perm >> 24; - } - else if (key->uid == context->fsuid) { - kperm = key->perm >> 16; - } - else if (key->gid != -1 && - key->perm & KEY_GRP_ALL && ( - key->gid == context->fsgid || - key_task_groups_search(context, key->gid) - ) - ) { - kperm = key->perm >> 8; - } - else { - kperm = key->perm; - } - - kperm = kperm & perm & KEY_ALL; - - return kperm == perm; - + return key_task_permission(key_ref, current, perm); } extern key_ref_t lookup_user_key(struct task_struct *context, diff --git a/security/keys/Makefile b/security/keys/Makefile index c392d750b20..5145adfb6a0 100644 --- a/security/keys/Makefile +++ b/security/keys/Makefile @@ -6,6 +6,7 @@ obj-y := \ key.o \ keyring.o \ keyctl.o \ + permission.o \ process_keys.o \ request_key.o \ request_key_auth.o \ diff --git a/security/keys/permission.c b/security/keys/permission.c new file mode 100644 index 00000000000..1c3651670ce --- /dev/null +++ b/security/keys/permission.c @@ -0,0 +1,70 @@ +/* permission.c: key permission determination + * + * Copyright (C) 2005 Red Hat, Inc. All Rights Reserved. + * Written by David Howells (dhowells@redhat.com) + * + * 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. + */ + +#include +#include "internal.h" + +/*****************************************************************************/ +/* + * check to see whether permission is granted to use a key in the desired way, + * but permit the security modules to override + */ +int key_task_permission(const key_ref_t key_ref, + struct task_struct *context, + key_perm_t perm) +{ + struct key *key; + key_perm_t kperm; + int ret; + + key = key_ref_to_ptr(key_ref); + + /* use the top 8-bits of permissions for keys the caller possesses */ + if (is_key_possessed(key_ref)) { + kperm = key->perm >> 24; + goto use_these_perms; + } + + /* use the second 8-bits of permissions for keys the caller owns */ + if (key->uid == context->fsuid) { + kperm = key->perm >> 16; + goto use_these_perms; + } + + /* use the third 8-bits of permissions for keys the caller has a group + * membership in common with */ + if (key->gid != -1 && key->perm & KEY_GRP_ALL) { + if (key->gid == context->fsgid) { + kperm = key->perm >> 8; + goto use_these_perms; + } + + task_lock(context); + ret = groups_search(context->group_info, key->gid); + task_unlock(context); + + if (ret) { + kperm = key->perm >> 8; + goto use_these_perms; + } + } + + /* otherwise use the least-significant 8-bits */ + kperm = key->perm; + +use_these_perms: + kperm = kperm & perm & KEY_ALL; + + return kperm == perm; + +} /* end key_task_permission() */ + +EXPORT_SYMBOL(key_task_permission); -- cgit v1.2.3 From 7ab501db8cb6659efdf04034e0de6b44c059a51b Mon Sep 17 00:00:00 2001 From: David Howells Date: Fri, 7 Oct 2005 16:41:24 +0100 Subject: [PATCH] Keys: Possessor permissions should be additive This patch makes the possessor permissions on a key additive with user/group/other permissions on the same key. This permits extra rights to be granted to the possessor of a key without taking away any rights conferred by them owning the key or having common group membership. Signed-Off-By: David Howells Signed-off-by: Linus Torvalds --- security/keys/permission.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/security/keys/permission.c b/security/keys/permission.c index 1c3651670ce..03db073ba45 100644 --- a/security/keys/permission.c +++ b/security/keys/permission.c @@ -27,12 +27,6 @@ int key_task_permission(const key_ref_t key_ref, key = key_ref_to_ptr(key_ref); - /* use the top 8-bits of permissions for keys the caller possesses */ - if (is_key_possessed(key_ref)) { - kperm = key->perm >> 24; - goto use_these_perms; - } - /* use the second 8-bits of permissions for keys the caller owns */ if (key->uid == context->fsuid) { kperm = key->perm >> 16; @@ -61,6 +55,12 @@ int key_task_permission(const key_ref_t key_ref, kperm = key->perm; use_these_perms: + /* use the top 8-bits of permissions for keys the caller possesses + * - possessor permissions are additive with other permissions + */ + if (is_key_possessed(key_ref)) + kperm |= key->perm >> 24; + kperm = kperm & perm & KEY_ALL; return kperm == perm; -- cgit v1.2.3 From 3b0e77bd144203a507eb191f7117d2c5004ea1de Mon Sep 17 00:00:00 2001 From: Jens Axboe Date: Fri, 7 Oct 2005 19:41:34 +0200 Subject: [PATCH] scsi_ioctl: only warn for rejected commands We should not be warning about commands that we allow, even if they are unknown. So move the if-root-allow check up a notch. Signed-off-by: Jens Axboe Signed-off-by: Linus Torvalds --- drivers/block/scsi_ioctl.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/drivers/block/scsi_ioctl.c b/drivers/block/scsi_ioctl.c index 079ec344eb4..382dea7b224 100644 --- a/drivers/block/scsi_ioctl.c +++ b/drivers/block/scsi_ioctl.c @@ -201,15 +201,15 @@ static int verify_command(struct file *file, unsigned char *cmd) return 0; } + /* And root can do any command.. */ + if (capable(CAP_SYS_RAWIO)) + return 0; + if (!type) { cmd_type[cmd[0]] = CMD_WARNED; printk(KERN_WARNING "scsi: unknown opcode 0x%02x\n", cmd[0]); } - /* And root can do any command.. */ - if (capable(CAP_SYS_RAWIO)) - return 0; - /* Otherwise fail it with an "Operation not permitted" */ return -EPERM; } -- cgit v1.2.3 From dd0fc66fb33cd610bc1a5db8a5e232d34879b4d7 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Fri, 7 Oct 2005 07:46:04 +0100 Subject: [PATCH] gfp flags annotations - part 1 - added typedef unsigned int __nocast gfp_t; - replaced __nocast uses for gfp flags with gfp_t - it gives exactly the same warnings as far as sparse is concerned, doesn't change generated code (from gcc point of view we replaced unsigned int with typedef) and documents what's going on far better. Signed-off-by: Al Viro Signed-off-by: Linus Torvalds --- arch/cris/arch-v32/drivers/pci/dma.c | 2 +- arch/i386/kernel/pci-dma.c | 2 +- arch/ppc64/kernel/bpa_iommu.c | 2 +- arch/ppc64/kernel/dma.c | 2 +- arch/ppc64/kernel/iommu.c | 2 +- arch/ppc64/kernel/pci_direct_iommu.c | 2 +- arch/ppc64/kernel/pci_iommu.c | 2 +- arch/ppc64/kernel/vio.c | 2 +- drivers/atm/ambassador.c | 2 +- drivers/atm/firestream.c | 5 ++--- drivers/atm/fore200e.c | 2 +- drivers/base/dmapool.c | 5 ++--- drivers/block/pktcdvd.c | 4 ++-- drivers/bluetooth/bpa10x.c | 2 +- drivers/bluetooth/hci_usb.c | 2 +- drivers/connector/connector.c | 3 +-- drivers/ieee1394/raw1394.c | 2 +- drivers/infiniband/core/mad.c | 2 +- drivers/infiniband/core/sa_query.c | 6 +++--- drivers/md/dm-crypt.c | 2 +- drivers/md/dm-io.c | 2 +- drivers/md/dm-raid1.c | 2 +- drivers/md/multipath.c | 2 +- drivers/md/raid1.c | 4 ++-- drivers/md/raid10.c | 4 ++-- drivers/net/bonding/bond_main.c | 2 +- drivers/net/ns83820.c | 2 +- drivers/net/sungem.h | 2 +- drivers/s390/scsi/zfcp_aux.c | 2 +- fs/bio.c | 10 +++++----- fs/buffer.c | 2 +- fs/mpage.c | 2 +- fs/ntfs/malloc.h | 2 +- fs/posix_acl.c | 6 +++--- fs/xfs/linux-2.6/kmem.c | 10 +++++----- fs/xfs/linux-2.6/kmem.h | 13 ++++++------- include/asm-generic/dma-mapping.h | 4 ++-- include/asm-i386/dma-mapping.h | 2 +- include/asm-ppc/dma-mapping.h | 2 +- include/asm-ppc64/dma-mapping.h | 4 ++-- include/asm-ppc64/iommu.h | 2 +- include/linux/atmdev.h | 2 +- include/linux/bio.h | 6 +++--- include/linux/buffer_head.h | 2 +- include/linux/connector.h | 2 +- include/linux/cpuset.h | 5 ++--- include/linux/dmapool.h | 2 +- include/linux/gfp.h | 14 +++++++------- include/linux/jbd.h | 2 +- include/linux/kfifo.h | 4 ++-- include/linux/mempool.h | 9 ++++----- include/linux/netlink.h | 2 +- include/linux/pagemap.h | 2 +- include/linux/posix_acl.h | 6 +++--- include/linux/radix-tree.h | 2 +- include/linux/security.h | 6 ++---- include/linux/skbuff.h | 28 ++++++++++++++-------------- include/linux/slab.h | 19 +++++++++---------- include/linux/string.h | 2 +- include/linux/swap.h | 2 +- include/linux/textsearch.h | 2 +- include/linux/types.h | 4 ++++ include/linux/vmalloc.h | 4 ++-- include/net/bluetooth/bluetooth.h | 2 +- include/net/bluetooth/rfcomm.h | 2 +- include/net/dn_nsp.h | 8 ++++---- include/net/dn_route.h | 2 +- include/net/inet_connection_sock.h | 2 +- include/net/ip_vs.h | 2 +- include/net/llc_conn.h | 2 +- include/net/sctp/sctp.h | 2 +- include/net/sctp/sm.h | 10 +++++----- include/net/sctp/structs.h | 24 ++++++++++++------------ include/net/sctp/ulpevent.h | 16 ++++++++-------- include/net/sctp/ulpqueue.h | 11 ++++------- include/net/sock.h | 16 ++++++++-------- include/net/tcp.h | 3 +-- include/net/xfrm.h | 2 +- include/rdma/ib_mad.h | 2 +- include/rdma/ib_sa.h | 10 +++++----- include/rxrpc/call.h | 2 +- include/rxrpc/message.h | 2 +- include/sound/core.h | 8 ++++---- include/sound/driver.h | 2 +- kernel/audit.c | 2 +- kernel/cpuset.c | 2 +- kernel/kfifo.c | 4 ++-- kernel/signal.c | 2 +- lib/radix-tree.c | 2 +- lib/ts_bm.c | 2 +- lib/ts_fsm.c | 2 +- lib/ts_kmp.c | 2 +- mm/highmem.c | 2 +- mm/mempolicy.c | 8 ++++---- mm/mempool.c | 6 +++--- mm/nommu.c | 3 +-- mm/oom_kill.c | 2 +- mm/page_alloc.c | 12 ++++++------ mm/page_io.c | 2 +- mm/shmem.c | 3 +-- mm/slab.c | 34 ++++++++++++++++------------------ mm/swap_state.c | 2 +- mm/vmalloc.c | 4 ++-- net/atm/atm_misc.c | 2 +- net/bluetooth/l2cap.c | 2 +- net/bluetooth/rfcomm/core.c | 2 +- net/bluetooth/rfcomm/sock.c | 2 +- net/bluetooth/rfcomm/tty.c | 2 +- net/bluetooth/sco.c | 2 +- net/core/dev.c | 2 +- net/core/skbuff.c | 14 +++++++------- net/core/sock.c | 10 +++++----- net/dccp/ackvec.c | 2 +- net/dccp/ackvec.h | 4 ++-- net/dccp/ccids/lib/loss_interval.h | 2 +- net/dccp/ccids/lib/packet_history.h | 4 ++-- net/decnet/af_decnet.c | 6 ++---- net/decnet/dn_nsp_out.c | 20 +++++++++----------- net/ieee80211/ieee80211_tx.c | 2 +- net/ipv4/inet_connection_sock.c | 2 +- net/ipv4/ipvs/ip_vs_app.c | 2 +- net/ipv4/tcp_output.c | 2 +- net/key/af_key.c | 6 +++--- net/llc/llc_conn.c | 3 +-- net/netfilter/nfnetlink.c | 3 +-- net/netlink/af_netlink.c | 4 ++-- net/rxrpc/call.c | 2 +- net/rxrpc/connection.c | 2 +- net/sctp/associola.c | 10 +++++----- net/sctp/bind_addr.c | 12 ++++++------ net/sctp/chunk.c | 2 +- net/sctp/endpointola.c | 5 ++--- net/sctp/protocol.c | 2 +- net/sctp/sm_make_chunk.c | 14 +++++++------- net/sctp/sm_sideeffect.c | 12 ++++++------ net/sctp/ssnmap.c | 2 +- net/sctp/transport.c | 4 ++-- net/sctp/ulpevent.c | 18 +++++++++--------- net/sctp/ulpqueue.c | 8 ++++---- net/sunrpc/sched.c | 2 +- net/xfrm/xfrm_policy.c | 2 +- sound/core/memalloc.c | 2 +- sound/core/memory.c | 10 +++++----- sound/core/seq/instr/ainstr_iw.c | 2 +- sound/core/wrappers.c | 2 +- 145 files changed, 340 insertions(+), 360 deletions(-) diff --git a/arch/cris/arch-v32/drivers/pci/dma.c b/arch/cris/arch-v32/drivers/pci/dma.c index 10329306d23..426b09878a0 100644 --- a/arch/cris/arch-v32/drivers/pci/dma.c +++ b/arch/cris/arch-v32/drivers/pci/dma.c @@ -24,7 +24,7 @@ struct dma_coherent_mem { }; void *dma_alloc_coherent(struct device *dev, size_t size, - dma_addr_t *dma_handle, unsigned int __nocast gfp) + dma_addr_t *dma_handle, gfp_t gfp) { void *ret; struct dma_coherent_mem *mem = dev ? dev->dma_mem : NULL; diff --git a/arch/i386/kernel/pci-dma.c b/arch/i386/kernel/pci-dma.c index 1e51427cc9e..25fe6685393 100644 --- a/arch/i386/kernel/pci-dma.c +++ b/arch/i386/kernel/pci-dma.c @@ -23,7 +23,7 @@ struct dma_coherent_mem { }; void *dma_alloc_coherent(struct device *dev, size_t size, - dma_addr_t *dma_handle, unsigned int __nocast gfp) + dma_addr_t *dma_handle, gfp_t gfp) { void *ret; struct dma_coherent_mem *mem = dev ? dev->dma_mem : NULL; diff --git a/arch/ppc64/kernel/bpa_iommu.c b/arch/ppc64/kernel/bpa_iommu.c index 507eb9d0223..5f2460090e0 100644 --- a/arch/ppc64/kernel/bpa_iommu.c +++ b/arch/ppc64/kernel/bpa_iommu.c @@ -310,7 +310,7 @@ static void bpa_map_iommu(void) static void *bpa_alloc_coherent(struct device *hwdev, size_t size, - dma_addr_t *dma_handle, unsigned int __nocast flag) + dma_addr_t *dma_handle, gfp_t flag) { void *ret; diff --git a/arch/ppc64/kernel/dma.c b/arch/ppc64/kernel/dma.c index 4da8e31b2b6..7c3419656cc 100644 --- a/arch/ppc64/kernel/dma.c +++ b/arch/ppc64/kernel/dma.c @@ -53,7 +53,7 @@ int dma_set_mask(struct device *dev, u64 dma_mask) EXPORT_SYMBOL(dma_set_mask); void *dma_alloc_coherent(struct device *dev, size_t size, - dma_addr_t *dma_handle, unsigned int __nocast flag) + dma_addr_t *dma_handle, gfp_t flag) { struct dma_mapping_ops *dma_ops = get_dma_ops(dev); diff --git a/arch/ppc64/kernel/iommu.c b/arch/ppc64/kernel/iommu.c index 9032b6bfe03..4d9b4388918 100644 --- a/arch/ppc64/kernel/iommu.c +++ b/arch/ppc64/kernel/iommu.c @@ -519,7 +519,7 @@ void iommu_unmap_single(struct iommu_table *tbl, dma_addr_t dma_handle, * to the dma address (mapping) of the first page. */ void *iommu_alloc_coherent(struct iommu_table *tbl, size_t size, - dma_addr_t *dma_handle, unsigned int __nocast flag) + dma_addr_t *dma_handle, gfp_t flag) { void *ret = NULL; dma_addr_t mapping; diff --git a/arch/ppc64/kernel/pci_direct_iommu.c b/arch/ppc64/kernel/pci_direct_iommu.c index b8f7f58824f..54055c81017 100644 --- a/arch/ppc64/kernel/pci_direct_iommu.c +++ b/arch/ppc64/kernel/pci_direct_iommu.c @@ -31,7 +31,7 @@ #include "pci.h" static void *pci_direct_alloc_coherent(struct device *hwdev, size_t size, - dma_addr_t *dma_handle, unsigned int __nocast flag) + dma_addr_t *dma_handle, gfp_t flag) { void *ret; diff --git a/arch/ppc64/kernel/pci_iommu.c b/arch/ppc64/kernel/pci_iommu.c index 14647e09c9c..d9e33b7d420 100644 --- a/arch/ppc64/kernel/pci_iommu.c +++ b/arch/ppc64/kernel/pci_iommu.c @@ -76,7 +76,7 @@ static inline struct iommu_table *devnode_table(struct device *dev) * to the dma address (mapping) of the first page. */ static void *pci_iommu_alloc_coherent(struct device *hwdev, size_t size, - dma_addr_t *dma_handle, unsigned int __nocast flag) + dma_addr_t *dma_handle, gfp_t flag) { return iommu_alloc_coherent(devnode_table(hwdev), size, dma_handle, flag); diff --git a/arch/ppc64/kernel/vio.c b/arch/ppc64/kernel/vio.c index c90e1dd875c..0e555b7a658 100644 --- a/arch/ppc64/kernel/vio.c +++ b/arch/ppc64/kernel/vio.c @@ -218,7 +218,7 @@ static void vio_unmap_sg(struct device *dev, struct scatterlist *sglist, } static void *vio_alloc_coherent(struct device *dev, size_t size, - dma_addr_t *dma_handle, unsigned int __nocast flag) + dma_addr_t *dma_handle, gfp_t flag) { return iommu_alloc_coherent(to_vio_dev(dev)->iommu_table, size, dma_handle, flag); diff --git a/drivers/atm/ambassador.c b/drivers/atm/ambassador.c index d74a7c5e75d..4b6bf19c39c 100644 --- a/drivers/atm/ambassador.c +++ b/drivers/atm/ambassador.c @@ -795,7 +795,7 @@ static void drain_rx_pools (amb_dev * dev) { } static inline void fill_rx_pool (amb_dev * dev, unsigned char pool, - unsigned int __nocast priority) + gfp_t priority) { rx_in rx; amb_rxq * rxq; diff --git a/drivers/atm/firestream.c b/drivers/atm/firestream.c index 58219744f5d..7f7ec288824 100644 --- a/drivers/atm/firestream.c +++ b/drivers/atm/firestream.c @@ -1374,8 +1374,7 @@ static void reset_chip (struct fs_dev *dev) } } -static void __devinit *aligned_kmalloc (int size, unsigned int __nocast flags, - int alignment) +static void __devinit *aligned_kmalloc (int size, gfp_t flags, int alignment) { void *t; @@ -1466,7 +1465,7 @@ static inline int nr_buffers_in_freepool (struct fs_dev *dev, struct freepool *f working again after that... -- REW */ static void top_off_fp (struct fs_dev *dev, struct freepool *fp, - unsigned int __nocast gfp_flags) + gfp_t gfp_flags) { struct FS_BPENTRY *qe, *ne; struct sk_buff *skb; diff --git a/drivers/atm/fore200e.c b/drivers/atm/fore200e.c index 6f1a83c9d9e..14f6a6201da 100644 --- a/drivers/atm/fore200e.c +++ b/drivers/atm/fore200e.c @@ -178,7 +178,7 @@ fore200e_irq_itoa(int irq) static void* -fore200e_kmalloc(int size, unsigned int __nocast flags) +fore200e_kmalloc(int size, gfp_t flags) { void *chunk = kzalloc(size, flags); diff --git a/drivers/base/dmapool.c b/drivers/base/dmapool.c index 60a7ef6a201..e2f64f91ed0 100644 --- a/drivers/base/dmapool.c +++ b/drivers/base/dmapool.c @@ -156,7 +156,7 @@ dma_pool_create (const char *name, struct device *dev, static struct dma_page * -pool_alloc_page (struct dma_pool *pool, unsigned int __nocast mem_flags) +pool_alloc_page (struct dma_pool *pool, gfp_t mem_flags) { struct dma_page *page; int mapsize; @@ -262,8 +262,7 @@ dma_pool_destroy (struct dma_pool *pool) * If such a memory block can't be allocated, null is returned. */ void * -dma_pool_alloc (struct dma_pool *pool, unsigned int __nocast mem_flags, - dma_addr_t *handle) +dma_pool_alloc (struct dma_pool *pool, gfp_t mem_flags, dma_addr_t *handle) { unsigned long flags; struct dma_page *page; diff --git a/drivers/block/pktcdvd.c b/drivers/block/pktcdvd.c index 7e22a58926b..a280e679b1c 100644 --- a/drivers/block/pktcdvd.c +++ b/drivers/block/pktcdvd.c @@ -229,7 +229,7 @@ static int pkt_grow_pktlist(struct pktcdvd_device *pd, int nr_packets) return 1; } -static void *pkt_rb_alloc(unsigned int __nocast gfp_mask, void *data) +static void *pkt_rb_alloc(gfp_t gfp_mask, void *data) { return kmalloc(sizeof(struct pkt_rb_node), gfp_mask); } @@ -2082,7 +2082,7 @@ static int pkt_close(struct inode *inode, struct file *file) } -static void *psd_pool_alloc(unsigned int __nocast gfp_mask, void *data) +static void *psd_pool_alloc(gfp_t gfp_mask, void *data) { return kmalloc(sizeof(struct packet_stacked_data), gfp_mask); } diff --git a/drivers/bluetooth/bpa10x.c b/drivers/bluetooth/bpa10x.c index a1bf8f066c8..4fa85234d8b 100644 --- a/drivers/bluetooth/bpa10x.c +++ b/drivers/bluetooth/bpa10x.c @@ -308,7 +308,7 @@ unlock: } static inline struct urb *bpa10x_alloc_urb(struct usb_device *udev, unsigned int pipe, - size_t size, unsigned int __nocast flags, void *data) + size_t size, gfp_t flags, void *data) { struct urb *urb; struct usb_ctrlrequest *cr; diff --git a/drivers/bluetooth/hci_usb.c b/drivers/bluetooth/hci_usb.c index 57c48bbf6fe..6756cb20b75 100644 --- a/drivers/bluetooth/hci_usb.c +++ b/drivers/bluetooth/hci_usb.c @@ -132,7 +132,7 @@ static struct usb_device_id blacklist_ids[] = { { } /* Terminating entry */ }; -static struct _urb *_urb_alloc(int isoc, unsigned int __nocast gfp) +static struct _urb *_urb_alloc(int isoc, gfp_t gfp) { struct _urb *_urb = kmalloc(sizeof(struct _urb) + sizeof(struct usb_iso_packet_descriptor) * isoc, gfp); diff --git a/drivers/connector/connector.c b/drivers/connector/connector.c index 1422285d537..505677fb315 100644 --- a/drivers/connector/connector.c +++ b/drivers/connector/connector.c @@ -69,8 +69,7 @@ int cn_already_initialized = 0; * a new message. * */ -int cn_netlink_send(struct cn_msg *msg, u32 __group, - unsigned int __nocast gfp_mask) +int cn_netlink_send(struct cn_msg *msg, u32 __group, gfp_t gfp_mask) { struct cn_callback_entry *__cbq; unsigned int size; diff --git a/drivers/ieee1394/raw1394.c b/drivers/ieee1394/raw1394.c index 5fe4f2ba097..315f5ca8bed 100644 --- a/drivers/ieee1394/raw1394.c +++ b/drivers/ieee1394/raw1394.c @@ -98,7 +98,7 @@ static struct hpsb_address_ops arm_ops = { static void queue_complete_cb(struct pending_request *req); -static struct pending_request *__alloc_pending_request(unsigned int __nocast flags) +static struct pending_request *__alloc_pending_request(gfp_t flags) { struct pending_request *req; diff --git a/drivers/infiniband/core/mad.c b/drivers/infiniband/core/mad.c index a4a4d9c1eef..a14ca87fda1 100644 --- a/drivers/infiniband/core/mad.c +++ b/drivers/infiniband/core/mad.c @@ -783,7 +783,7 @@ struct ib_mad_send_buf * ib_create_send_mad(struct ib_mad_agent *mad_agent, u32 remote_qpn, u16 pkey_index, struct ib_ah *ah, int rmpp_active, int hdr_len, int data_len, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { struct ib_mad_agent_private *mad_agent_priv; struct ib_mad_send_buf *send_buf; diff --git a/drivers/infiniband/core/sa_query.c b/drivers/infiniband/core/sa_query.c index 78de2dd1a4f..262618210c1 100644 --- a/drivers/infiniband/core/sa_query.c +++ b/drivers/infiniband/core/sa_query.c @@ -574,7 +574,7 @@ static void ib_sa_path_rec_release(struct ib_sa_query *sa_query) int ib_sa_path_rec_get(struct ib_device *device, u8 port_num, struct ib_sa_path_rec *rec, ib_sa_comp_mask comp_mask, - int timeout_ms, unsigned int __nocast gfp_mask, + int timeout_ms, gfp_t gfp_mask, void (*callback)(int status, struct ib_sa_path_rec *resp, void *context), @@ -676,7 +676,7 @@ static void ib_sa_service_rec_release(struct ib_sa_query *sa_query) int ib_sa_service_rec_query(struct ib_device *device, u8 port_num, u8 method, struct ib_sa_service_rec *rec, ib_sa_comp_mask comp_mask, - int timeout_ms, unsigned int __nocast gfp_mask, + int timeout_ms, gfp_t gfp_mask, void (*callback)(int status, struct ib_sa_service_rec *resp, void *context), @@ -759,7 +759,7 @@ int ib_sa_mcmember_rec_query(struct ib_device *device, u8 port_num, u8 method, struct ib_sa_mcmember_rec *rec, ib_sa_comp_mask comp_mask, - int timeout_ms, unsigned int __nocast gfp_mask, + int timeout_ms, gfp_t gfp_mask, void (*callback)(int status, struct ib_sa_mcmember_rec *resp, void *context), diff --git a/drivers/md/dm-crypt.c b/drivers/md/dm-crypt.c index b82bc315047..b6148f6f783 100644 --- a/drivers/md/dm-crypt.c +++ b/drivers/md/dm-crypt.c @@ -96,7 +96,7 @@ static kmem_cache_t *_crypt_io_pool; /* * Mempool alloc and free functions for the page */ -static void *mempool_alloc_page(unsigned int __nocast gfp_mask, void *data) +static void *mempool_alloc_page(gfp_t gfp_mask, void *data) { return alloc_page(gfp_mask); } diff --git a/drivers/md/dm-io.c b/drivers/md/dm-io.c index 9de000131a8..4809b209fbb 100644 --- a/drivers/md/dm-io.c +++ b/drivers/md/dm-io.c @@ -32,7 +32,7 @@ struct io { static unsigned _num_ios; static mempool_t *_io_pool; -static void *alloc_io(unsigned int __nocast gfp_mask, void *pool_data) +static void *alloc_io(gfp_t gfp_mask, void *pool_data) { return kmalloc(sizeof(struct io), gfp_mask); } diff --git a/drivers/md/dm-raid1.c b/drivers/md/dm-raid1.c index 86328251375..2375709a392 100644 --- a/drivers/md/dm-raid1.c +++ b/drivers/md/dm-raid1.c @@ -122,7 +122,7 @@ static inline sector_t region_to_sector(struct region_hash *rh, region_t region) /* FIXME move this */ static void queue_bio(struct mirror_set *ms, struct bio *bio, int rw); -static void *region_alloc(unsigned int __nocast gfp_mask, void *pool_data) +static void *region_alloc(gfp_t gfp_mask, void *pool_data) { return kmalloc(sizeof(struct region), gfp_mask); } diff --git a/drivers/md/multipath.c b/drivers/md/multipath.c index 286342375fb..1151c3ed300 100644 --- a/drivers/md/multipath.c +++ b/drivers/md/multipath.c @@ -38,7 +38,7 @@ static mdk_personality_t multipath_personality; -static void *mp_pool_alloc(unsigned int __nocast gfp_flags, void *data) +static void *mp_pool_alloc(gfp_t gfp_flags, void *data) { struct multipath_bh *mpb; mpb = kmalloc(sizeof(*mpb), gfp_flags); diff --git a/drivers/md/raid1.c b/drivers/md/raid1.c index a93ca478142..0e1f148dd41 100644 --- a/drivers/md/raid1.c +++ b/drivers/md/raid1.c @@ -52,7 +52,7 @@ static mdk_personality_t raid1_personality; static void unplug_slaves(mddev_t *mddev); -static void * r1bio_pool_alloc(unsigned int __nocast gfp_flags, void *data) +static void * r1bio_pool_alloc(gfp_t gfp_flags, void *data) { struct pool_info *pi = data; r1bio_t *r1_bio; @@ -79,7 +79,7 @@ static void r1bio_pool_free(void *r1_bio, void *data) #define RESYNC_PAGES ((RESYNC_BLOCK_SIZE + PAGE_SIZE-1) / PAGE_SIZE) #define RESYNC_WINDOW (2048*1024) -static void * r1buf_pool_alloc(unsigned int __nocast gfp_flags, void *data) +static void * r1buf_pool_alloc(gfp_t gfp_flags, void *data) { struct pool_info *pi = data; struct page *page; diff --git a/drivers/md/raid10.c b/drivers/md/raid10.c index 5bd1e9ec899..28dd028415e 100644 --- a/drivers/md/raid10.c +++ b/drivers/md/raid10.c @@ -47,7 +47,7 @@ static void unplug_slaves(mddev_t *mddev); -static void * r10bio_pool_alloc(unsigned int __nocast gfp_flags, void *data) +static void * r10bio_pool_alloc(gfp_t gfp_flags, void *data) { conf_t *conf = data; r10bio_t *r10_bio; @@ -81,7 +81,7 @@ static void r10bio_pool_free(void *r10_bio, void *data) * one for write (we recover only one drive per r10buf) * */ -static void * r10buf_pool_alloc(unsigned int __nocast gfp_flags, void *data) +static void * r10buf_pool_alloc(gfp_t gfp_flags, void *data) { conf_t *conf = data; struct page *page; diff --git a/drivers/net/bonding/bond_main.c b/drivers/net/bonding/bond_main.c index f0a5b772a38..f264ff16297 100644 --- a/drivers/net/bonding/bond_main.c +++ b/drivers/net/bonding/bond_main.c @@ -1290,7 +1290,7 @@ static void bond_mc_list_destroy(struct bonding *bond) * Copy all the Multicast addresses from src to the bonding device dst */ static int bond_mc_list_copy(struct dev_mc_list *mc_list, struct bonding *bond, - unsigned int __nocast gfp_flag) + gfp_t gfp_flag) { struct dev_mc_list *dmi, *new_dmi; diff --git a/drivers/net/ns83820.c b/drivers/net/ns83820.c index 83334db2921..e4811b42a6b 100644 --- a/drivers/net/ns83820.c +++ b/drivers/net/ns83820.c @@ -584,7 +584,7 @@ static inline int ns83820_add_rx_skb(struct ns83820 *dev, struct sk_buff *skb) return 0; } -static inline int rx_refill(struct net_device *ndev, unsigned int __nocast gfp) +static inline int rx_refill(struct net_device *ndev, gfp_t gfp) { struct ns83820 *dev = PRIV(ndev); unsigned i; diff --git a/drivers/net/sungem.h b/drivers/net/sungem.h index 16edbb1a4a7..13006d759ad 100644 --- a/drivers/net/sungem.h +++ b/drivers/net/sungem.h @@ -1036,7 +1036,7 @@ struct gem { #define ALIGNED_RX_SKB_ADDR(addr) \ ((((unsigned long)(addr) + (64UL - 1UL)) & ~(64UL - 1UL)) - (unsigned long)(addr)) static __inline__ struct sk_buff *gem_alloc_skb(int size, - unsigned int __nocast gfp_flags) + gfp_t gfp_flags) { struct sk_buff *skb = alloc_skb(size + 64, gfp_flags); diff --git a/drivers/s390/scsi/zfcp_aux.c b/drivers/s390/scsi/zfcp_aux.c index 0b5087f7cab..cab098556b4 100644 --- a/drivers/s390/scsi/zfcp_aux.c +++ b/drivers/s390/scsi/zfcp_aux.c @@ -833,7 +833,7 @@ zfcp_unit_dequeue(struct zfcp_unit *unit) } static void * -zfcp_mempool_alloc(unsigned int __nocast gfp_mask, void *size) +zfcp_mempool_alloc(gfp_t gfp_mask, void *size) { return kmalloc((size_t) size, gfp_mask); } diff --git a/fs/bio.c b/fs/bio.c index 83a34957456..7d81a93afd4 100644 --- a/fs/bio.c +++ b/fs/bio.c @@ -75,7 +75,7 @@ struct bio_set { */ static struct bio_set *fs_bio_set; -static inline struct bio_vec *bvec_alloc_bs(unsigned int __nocast gfp_mask, int nr, unsigned long *idx, struct bio_set *bs) +static inline struct bio_vec *bvec_alloc_bs(gfp_t gfp_mask, int nr, unsigned long *idx, struct bio_set *bs) { struct bio_vec *bvl; struct biovec_slab *bp; @@ -155,7 +155,7 @@ inline void bio_init(struct bio *bio) * allocate bio and iovecs from the memory pools specified by the * bio_set structure. **/ -struct bio *bio_alloc_bioset(unsigned int __nocast gfp_mask, int nr_iovecs, struct bio_set *bs) +struct bio *bio_alloc_bioset(gfp_t gfp_mask, int nr_iovecs, struct bio_set *bs) { struct bio *bio = mempool_alloc(bs->bio_pool, gfp_mask); @@ -181,7 +181,7 @@ out: return bio; } -struct bio *bio_alloc(unsigned int __nocast gfp_mask, int nr_iovecs) +struct bio *bio_alloc(gfp_t gfp_mask, int nr_iovecs) { struct bio *bio = bio_alloc_bioset(gfp_mask, nr_iovecs, fs_bio_set); @@ -277,7 +277,7 @@ inline void __bio_clone(struct bio *bio, struct bio *bio_src) * * Like __bio_clone, only also allocates the returned bio */ -struct bio *bio_clone(struct bio *bio, unsigned int __nocast gfp_mask) +struct bio *bio_clone(struct bio *bio, gfp_t gfp_mask) { struct bio *b = bio_alloc_bioset(gfp_mask, bio->bi_max_vecs, fs_bio_set); @@ -1078,7 +1078,7 @@ struct bio_pair *bio_split(struct bio *bi, mempool_t *pool, int first_sectors) return bp; } -static void *bio_pair_alloc(unsigned int __nocast gfp_flags, void *data) +static void *bio_pair_alloc(gfp_t gfp_flags, void *data) { return kmalloc(sizeof(struct bio_pair), gfp_flags); } diff --git a/fs/buffer.c b/fs/buffer.c index 6cbfceabd95..1216c0d3c8c 100644 --- a/fs/buffer.c +++ b/fs/buffer.c @@ -3045,7 +3045,7 @@ static void recalc_bh_state(void) buffer_heads_over_limit = (tot > max_buffer_heads); } -struct buffer_head *alloc_buffer_head(unsigned int __nocast gfp_flags) +struct buffer_head *alloc_buffer_head(gfp_t gfp_flags) { struct buffer_head *ret = kmem_cache_alloc(bh_cachep, gfp_flags); if (ret) { diff --git a/fs/mpage.c b/fs/mpage.c index bb9aebe9386..c5adcdddf3c 100644 --- a/fs/mpage.c +++ b/fs/mpage.c @@ -102,7 +102,7 @@ static struct bio *mpage_bio_submit(int rw, struct bio *bio) static struct bio * mpage_alloc(struct block_device *bdev, sector_t first_sector, int nr_vecs, - unsigned int __nocast gfp_flags) + gfp_t gfp_flags) { struct bio *bio; diff --git a/fs/ntfs/malloc.h b/fs/ntfs/malloc.h index 006946efca8..590887b943f 100644 --- a/fs/ntfs/malloc.h +++ b/fs/ntfs/malloc.h @@ -40,7 +40,7 @@ * Depending on @gfp_mask the allocation may be guaranteed to succeed. */ static inline void *__ntfs_malloc(unsigned long size, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { if (likely(size <= PAGE_SIZE)) { BUG_ON(!size); diff --git a/fs/posix_acl.c b/fs/posix_acl.c index 296480e96dd..6c8dcf7613f 100644 --- a/fs/posix_acl.c +++ b/fs/posix_acl.c @@ -35,7 +35,7 @@ EXPORT_SYMBOL(posix_acl_permission); * Allocate a new ACL with the specified number of entries. */ struct posix_acl * -posix_acl_alloc(int count, unsigned int __nocast flags) +posix_acl_alloc(int count, gfp_t flags) { const size_t size = sizeof(struct posix_acl) + count * sizeof(struct posix_acl_entry); @@ -51,7 +51,7 @@ posix_acl_alloc(int count, unsigned int __nocast flags) * Clone an ACL. */ struct posix_acl * -posix_acl_clone(const struct posix_acl *acl, unsigned int __nocast flags) +posix_acl_clone(const struct posix_acl *acl, gfp_t flags) { struct posix_acl *clone = NULL; @@ -185,7 +185,7 @@ posix_acl_equiv_mode(const struct posix_acl *acl, mode_t *mode_p) * Create an ACL representing the file mode permission bits of an inode. */ struct posix_acl * -posix_acl_from_mode(mode_t mode, unsigned int __nocast flags) +posix_acl_from_mode(mode_t mode, gfp_t flags) { struct posix_acl *acl = posix_acl_alloc(3, flags); if (!acl) diff --git a/fs/xfs/linux-2.6/kmem.c b/fs/xfs/linux-2.6/kmem.c index 4b184559f23..d2653b589b1 100644 --- a/fs/xfs/linux-2.6/kmem.c +++ b/fs/xfs/linux-2.6/kmem.c @@ -45,7 +45,7 @@ void * -kmem_alloc(size_t size, unsigned int __nocast flags) +kmem_alloc(size_t size, gfp_t flags) { int retries = 0; unsigned int lflags = kmem_flags_convert(flags); @@ -67,7 +67,7 @@ kmem_alloc(size_t size, unsigned int __nocast flags) } void * -kmem_zalloc(size_t size, unsigned int __nocast flags) +kmem_zalloc(size_t size, gfp_t flags) { void *ptr; @@ -90,7 +90,7 @@ kmem_free(void *ptr, size_t size) void * kmem_realloc(void *ptr, size_t newsize, size_t oldsize, - unsigned int __nocast flags) + gfp_t flags) { void *new; @@ -105,7 +105,7 @@ kmem_realloc(void *ptr, size_t newsize, size_t oldsize, } void * -kmem_zone_alloc(kmem_zone_t *zone, unsigned int __nocast flags) +kmem_zone_alloc(kmem_zone_t *zone, gfp_t flags) { int retries = 0; unsigned int lflags = kmem_flags_convert(flags); @@ -124,7 +124,7 @@ kmem_zone_alloc(kmem_zone_t *zone, unsigned int __nocast flags) } void * -kmem_zone_zalloc(kmem_zone_t *zone, unsigned int __nocast flags) +kmem_zone_zalloc(kmem_zone_t *zone, gfp_t flags) { void *ptr; diff --git a/fs/xfs/linux-2.6/kmem.h b/fs/xfs/linux-2.6/kmem.h index 109fcf27e25..ee7010f085b 100644 --- a/fs/xfs/linux-2.6/kmem.h +++ b/fs/xfs/linux-2.6/kmem.h @@ -81,7 +81,7 @@ typedef unsigned long xfs_pflags_t; *(NSTATEP) = *(OSTATEP); \ } while (0) -static __inline unsigned int kmem_flags_convert(unsigned int __nocast flags) +static __inline unsigned int kmem_flags_convert(gfp_t flags) { unsigned int lflags = __GFP_NOWARN; /* we'll report problems, if need be */ @@ -125,13 +125,12 @@ kmem_zone_destroy(kmem_zone_t *zone) BUG(); } -extern void *kmem_zone_zalloc(kmem_zone_t *, unsigned int __nocast); -extern void *kmem_zone_alloc(kmem_zone_t *, unsigned int __nocast); +extern void *kmem_zone_zalloc(kmem_zone_t *, gfp_t); +extern void *kmem_zone_alloc(kmem_zone_t *, gfp_t); -extern void *kmem_alloc(size_t, unsigned int __nocast); -extern void *kmem_realloc(void *, size_t, size_t, - unsigned int __nocast); -extern void *kmem_zalloc(size_t, unsigned int __nocast); +extern void *kmem_alloc(size_t, gfp_t); +extern void *kmem_realloc(void *, size_t, size_t, gfp_t); +extern void *kmem_zalloc(size_t, gfp_t); extern void kmem_free(void *, size_t); typedef struct shrinker *kmem_shaker_t; diff --git a/include/asm-generic/dma-mapping.h b/include/asm-generic/dma-mapping.h index 8cef663c5cd..747d790295f 100644 --- a/include/asm-generic/dma-mapping.h +++ b/include/asm-generic/dma-mapping.h @@ -35,7 +35,7 @@ dma_set_mask(struct device *dev, u64 dma_mask) static inline void * dma_alloc_coherent(struct device *dev, size_t size, dma_addr_t *dma_handle, - unsigned int __nocast flag) + gfp_t flag) { BUG_ON(dev->bus != &pci_bus_type); @@ -168,7 +168,7 @@ dma_set_mask(struct device *dev, u64 dma_mask) static inline void * dma_alloc_coherent(struct device *dev, size_t size, dma_addr_t *dma_handle, - unsigned int __nocast flag) + gfp_t flag) { BUG(); return NULL; diff --git a/include/asm-i386/dma-mapping.h b/include/asm-i386/dma-mapping.h index 563964b2995..e56c335f8ef 100644 --- a/include/asm-i386/dma-mapping.h +++ b/include/asm-i386/dma-mapping.h @@ -11,7 +11,7 @@ #define dma_free_noncoherent(d, s, v, h) dma_free_coherent(d, s, v, h) void *dma_alloc_coherent(struct device *dev, size_t size, - dma_addr_t *dma_handle, unsigned int __nocast flag); + dma_addr_t *dma_handle, gfp_t flag); void dma_free_coherent(struct device *dev, size_t size, void *vaddr, dma_addr_t dma_handle); diff --git a/include/asm-ppc/dma-mapping.h b/include/asm-ppc/dma-mapping.h index 92b8ee78dcc..061bfcac1bf 100644 --- a/include/asm-ppc/dma-mapping.h +++ b/include/asm-ppc/dma-mapping.h @@ -61,7 +61,7 @@ static inline int dma_set_mask(struct device *dev, u64 dma_mask) static inline void *dma_alloc_coherent(struct device *dev, size_t size, dma_addr_t * dma_handle, - unsigned int __nocast gfp) + gfp_t gfp) { #ifdef CONFIG_NOT_COHERENT_CACHE return __dma_alloc_coherent(size, dma_handle, gfp); diff --git a/include/asm-ppc64/dma-mapping.h b/include/asm-ppc64/dma-mapping.h index 9ad8adee006..fb68fa23bea 100644 --- a/include/asm-ppc64/dma-mapping.h +++ b/include/asm-ppc64/dma-mapping.h @@ -19,7 +19,7 @@ extern int dma_supported(struct device *dev, u64 mask); extern int dma_set_mask(struct device *dev, u64 dma_mask); extern void *dma_alloc_coherent(struct device *dev, size_t size, - dma_addr_t *dma_handle, unsigned int __nocast flag); + dma_addr_t *dma_handle, gfp_t flag); extern void dma_free_coherent(struct device *dev, size_t size, void *cpu_addr, dma_addr_t dma_handle); extern dma_addr_t dma_map_single(struct device *dev, void *cpu_addr, @@ -118,7 +118,7 @@ dma_cache_sync(void *vaddr, size_t size, */ struct dma_mapping_ops { void * (*alloc_coherent)(struct device *dev, size_t size, - dma_addr_t *dma_handle, unsigned int __nocast flag); + dma_addr_t *dma_handle, gfp_t flag); void (*free_coherent)(struct device *dev, size_t size, void *vaddr, dma_addr_t dma_handle); dma_addr_t (*map_single)(struct device *dev, void *ptr, diff --git a/include/asm-ppc64/iommu.h b/include/asm-ppc64/iommu.h index 72dcf8116b0..c2f3b6e8a42 100644 --- a/include/asm-ppc64/iommu.h +++ b/include/asm-ppc64/iommu.h @@ -122,7 +122,7 @@ extern void iommu_unmap_sg(struct iommu_table *tbl, struct scatterlist *sglist, int nelems, enum dma_data_direction direction); extern void *iommu_alloc_coherent(struct iommu_table *tbl, size_t size, - dma_addr_t *dma_handle, unsigned int __nocast flag); + dma_addr_t *dma_handle, gfp_t flag); extern void iommu_free_coherent(struct iommu_table *tbl, size_t size, void *vaddr, dma_addr_t dma_handle); extern dma_addr_t iommu_map_single(struct iommu_table *tbl, void *vaddr, diff --git a/include/linux/atmdev.h b/include/linux/atmdev.h index aca9b344bd3..e7d0593bb57 100644 --- a/include/linux/atmdev.h +++ b/include/linux/atmdev.h @@ -467,7 +467,7 @@ static inline void atm_dev_put(struct atm_dev *dev) int atm_charge(struct atm_vcc *vcc,int truesize); struct sk_buff *atm_alloc_charge(struct atm_vcc *vcc,int pdu_size, - unsigned int __nocast gfp_flags); + gfp_t gfp_flags); int atm_pcr_goal(struct atm_trafprm *tp); void vcc_release_async(struct atm_vcc *vcc, int reply); diff --git a/include/linux/bio.h b/include/linux/bio.h index 6e1c79c8b6b..3344b4e8e43 100644 --- a/include/linux/bio.h +++ b/include/linux/bio.h @@ -276,8 +276,8 @@ extern void bio_pair_release(struct bio_pair *dbio); extern struct bio_set *bioset_create(int, int, int); extern void bioset_free(struct bio_set *); -extern struct bio *bio_alloc(unsigned int __nocast, int); -extern struct bio *bio_alloc_bioset(unsigned int __nocast, int, struct bio_set *); +extern struct bio *bio_alloc(gfp_t, int); +extern struct bio *bio_alloc_bioset(gfp_t, int, struct bio_set *); extern void bio_put(struct bio *); extern void bio_free(struct bio *, struct bio_set *); @@ -287,7 +287,7 @@ extern int bio_phys_segments(struct request_queue *, struct bio *); extern int bio_hw_segments(struct request_queue *, struct bio *); extern void __bio_clone(struct bio *, struct bio *); -extern struct bio *bio_clone(struct bio *, unsigned int __nocast); +extern struct bio *bio_clone(struct bio *, gfp_t); extern void bio_init(struct bio *); diff --git a/include/linux/buffer_head.h b/include/linux/buffer_head.h index 90828493791..6a1d154c082 100644 --- a/include/linux/buffer_head.h +++ b/include/linux/buffer_head.h @@ -172,7 +172,7 @@ void __brelse(struct buffer_head *); void __bforget(struct buffer_head *); void __breadahead(struct block_device *, sector_t block, int size); struct buffer_head *__bread(struct block_device *, sector_t block, int size); -struct buffer_head *alloc_buffer_head(unsigned int __nocast gfp_flags); +struct buffer_head *alloc_buffer_head(gfp_t gfp_flags); void free_buffer_head(struct buffer_head * bh); void FASTCALL(unlock_buffer(struct buffer_head *bh)); void FASTCALL(__lock_buffer(struct buffer_head *bh)); diff --git a/include/linux/connector.h b/include/linux/connector.h index 96582c9911a..95952cc1f52 100644 --- a/include/linux/connector.h +++ b/include/linux/connector.h @@ -149,7 +149,7 @@ struct cn_dev { int cn_add_callback(struct cb_id *, char *, void (*callback) (void *)); void cn_del_callback(struct cb_id *); -int cn_netlink_send(struct cn_msg *, u32, unsigned int __nocast); +int cn_netlink_send(struct cn_msg *, u32, gfp_t); int cn_queue_add_callback(struct cn_queue_dev *dev, char *name, struct cb_id *id, void (*callback)(void *)); void cn_queue_del_callback(struct cn_queue_dev *dev, struct cb_id *id); diff --git a/include/linux/cpuset.h b/include/linux/cpuset.h index 24062a1dbf6..6e2deef96b3 100644 --- a/include/linux/cpuset.h +++ b/include/linux/cpuset.h @@ -23,7 +23,7 @@ void cpuset_init_current_mems_allowed(void); void cpuset_update_current_mems_allowed(void); void cpuset_restrict_to_mems_allowed(unsigned long *nodes); int cpuset_zonelist_valid_mems_allowed(struct zonelist *zl); -extern int cpuset_zone_allowed(struct zone *z, unsigned int __nocast gfp_mask); +extern int cpuset_zone_allowed(struct zone *z, gfp_t gfp_mask); extern int cpuset_excl_nodes_overlap(const struct task_struct *p); extern struct file_operations proc_cpuset_operations; extern char *cpuset_task_status_allowed(struct task_struct *task, char *buffer); @@ -49,8 +49,7 @@ static inline int cpuset_zonelist_valid_mems_allowed(struct zonelist *zl) return 1; } -static inline int cpuset_zone_allowed(struct zone *z, - unsigned int __nocast gfp_mask) +static inline int cpuset_zone_allowed(struct zone *z, gfp_t gfp_mask) { return 1; } diff --git a/include/linux/dmapool.h b/include/linux/dmapool.h index 4932ee5c77f..76f12f46db7 100644 --- a/include/linux/dmapool.h +++ b/include/linux/dmapool.h @@ -19,7 +19,7 @@ struct dma_pool *dma_pool_create(const char *name, struct device *dev, void dma_pool_destroy(struct dma_pool *pool); -void *dma_pool_alloc(struct dma_pool *pool, unsigned int __nocast mem_flags, +void *dma_pool_alloc(struct dma_pool *pool, gfp_t mem_flags, dma_addr_t *handle); void dma_pool_free(struct dma_pool *pool, void *vaddr, dma_addr_t addr); diff --git a/include/linux/gfp.h b/include/linux/gfp.h index 4dc990f3b5c..3010e172394 100644 --- a/include/linux/gfp.h +++ b/include/linux/gfp.h @@ -85,9 +85,9 @@ static inline void arch_free_page(struct page *page, int order) { } #endif extern struct page * -FASTCALL(__alloc_pages(unsigned int, unsigned int, struct zonelist *)); +FASTCALL(__alloc_pages(gfp_t, unsigned int, struct zonelist *)); -static inline struct page *alloc_pages_node(int nid, unsigned int __nocast gfp_mask, +static inline struct page *alloc_pages_node(int nid, gfp_t gfp_mask, unsigned int order) { if (unlikely(order >= MAX_ORDER)) @@ -98,17 +98,17 @@ static inline struct page *alloc_pages_node(int nid, unsigned int __nocast gfp_m } #ifdef CONFIG_NUMA -extern struct page *alloc_pages_current(unsigned int __nocast gfp_mask, unsigned order); +extern struct page *alloc_pages_current(gfp_t gfp_mask, unsigned order); static inline struct page * -alloc_pages(unsigned int __nocast gfp_mask, unsigned int order) +alloc_pages(gfp_t gfp_mask, unsigned int order) { if (unlikely(order >= MAX_ORDER)) return NULL; return alloc_pages_current(gfp_mask, order); } -extern struct page *alloc_page_vma(unsigned __nocast gfp_mask, +extern struct page *alloc_page_vma(gfp_t gfp_mask, struct vm_area_struct *vma, unsigned long addr); #else #define alloc_pages(gfp_mask, order) \ @@ -117,8 +117,8 @@ extern struct page *alloc_page_vma(unsigned __nocast gfp_mask, #endif #define alloc_page(gfp_mask) alloc_pages(gfp_mask, 0) -extern unsigned long FASTCALL(__get_free_pages(unsigned int __nocast gfp_mask, unsigned int order)); -extern unsigned long FASTCALL(get_zeroed_page(unsigned int __nocast gfp_mask)); +extern unsigned long FASTCALL(__get_free_pages(gfp_t gfp_mask, unsigned int order)); +extern unsigned long FASTCALL(get_zeroed_page(gfp_t gfp_mask)); #define __get_free_page(gfp_mask) \ __get_free_pages((gfp_mask),0) diff --git a/include/linux/jbd.h b/include/linux/jbd.h index de097269bd7..ff853b3173c 100644 --- a/include/linux/jbd.h +++ b/include/linux/jbd.h @@ -935,7 +935,7 @@ void journal_put_journal_head(struct journal_head *jh); */ extern kmem_cache_t *jbd_handle_cache; -static inline handle_t *jbd_alloc_handle(unsigned int __nocast gfp_flags) +static inline handle_t *jbd_alloc_handle(gfp_t gfp_flags) { return kmem_cache_alloc(jbd_handle_cache, gfp_flags); } diff --git a/include/linux/kfifo.h b/include/linux/kfifo.h index c27cd428d26..48eccd865bd 100644 --- a/include/linux/kfifo.h +++ b/include/linux/kfifo.h @@ -35,8 +35,8 @@ struct kfifo { }; extern struct kfifo *kfifo_init(unsigned char *buffer, unsigned int size, - unsigned int __nocast gfp_mask, spinlock_t *lock); -extern struct kfifo *kfifo_alloc(unsigned int size, unsigned int __nocast gfp_mask, + gfp_t gfp_mask, spinlock_t *lock); +extern struct kfifo *kfifo_alloc(unsigned int size, gfp_t gfp_mask, spinlock_t *lock); extern void kfifo_free(struct kfifo *fifo); extern unsigned int __kfifo_put(struct kfifo *fifo, diff --git a/include/linux/mempool.h b/include/linux/mempool.h index 796220ce47c..f2427d7394b 100644 --- a/include/linux/mempool.h +++ b/include/linux/mempool.h @@ -6,7 +6,7 @@ #include -typedef void * (mempool_alloc_t)(unsigned int __nocast gfp_mask, void *pool_data); +typedef void * (mempool_alloc_t)(gfp_t gfp_mask, void *pool_data); typedef void (mempool_free_t)(void *element, void *pool_data); typedef struct mempool_s { @@ -26,17 +26,16 @@ extern mempool_t *mempool_create(int min_nr, mempool_alloc_t *alloc_fn, extern mempool_t *mempool_create_node(int min_nr, mempool_alloc_t *alloc_fn, mempool_free_t *free_fn, void *pool_data, int nid); -extern int mempool_resize(mempool_t *pool, int new_min_nr, - unsigned int __nocast gfp_mask); +extern int mempool_resize(mempool_t *pool, int new_min_nr, gfp_t gfp_mask); extern void mempool_destroy(mempool_t *pool); -extern void * mempool_alloc(mempool_t *pool, unsigned int __nocast gfp_mask); +extern void * mempool_alloc(mempool_t *pool, gfp_t gfp_mask); extern void mempool_free(void *element, mempool_t *pool); /* * A mempool_alloc_t and mempool_free_t that get the memory from * a slab that is passed in through pool_data. */ -void *mempool_alloc_slab(unsigned int __nocast gfp_mask, void *pool_data); +void *mempool_alloc_slab(gfp_t gfp_mask, void *pool_data); void mempool_free_slab(void *element, void *pool_data); #endif /* _LINUX_MEMPOOL_H */ diff --git a/include/linux/netlink.h b/include/linux/netlink.h index bdebdc56450..ba25ca874c2 100644 --- a/include/linux/netlink.h +++ b/include/linux/netlink.h @@ -131,7 +131,7 @@ extern struct sock *netlink_kernel_create(int unit, unsigned int groups, void (* extern void netlink_ack(struct sk_buff *in_skb, struct nlmsghdr *nlh, int err); extern int netlink_unicast(struct sock *ssk, struct sk_buff *skb, __u32 pid, int nonblock); extern int netlink_broadcast(struct sock *ssk, struct sk_buff *skb, __u32 pid, - __u32 group, unsigned int __nocast allocation); + __u32 group, gfp_t allocation); extern void netlink_set_err(struct sock *ssk, __u32 pid, __u32 group, int code); extern int netlink_register_notifier(struct notifier_block *nb); extern int netlink_unregister_notifier(struct notifier_block *nb); diff --git a/include/linux/pagemap.h b/include/linux/pagemap.h index d9a25647a29..acbf31c154f 100644 --- a/include/linux/pagemap.h +++ b/include/linux/pagemap.h @@ -19,7 +19,7 @@ #define AS_EIO (__GFP_BITS_SHIFT + 0) /* IO error on async write */ #define AS_ENOSPC (__GFP_BITS_SHIFT + 1) /* ENOSPC on async write */ -static inline unsigned int __nocast mapping_gfp_mask(struct address_space * mapping) +static inline gfp_t mapping_gfp_mask(struct address_space * mapping) { return mapping->flags & __GFP_BITS_MASK; } diff --git a/include/linux/posix_acl.h b/include/linux/posix_acl.h index 4caedddaa03..4bc241290c2 100644 --- a/include/linux/posix_acl.h +++ b/include/linux/posix_acl.h @@ -71,11 +71,11 @@ posix_acl_release(struct posix_acl *acl) /* posix_acl.c */ -extern struct posix_acl *posix_acl_alloc(int, unsigned int __nocast); -extern struct posix_acl *posix_acl_clone(const struct posix_acl *, unsigned int __nocast); +extern struct posix_acl *posix_acl_alloc(int, gfp_t); +extern struct posix_acl *posix_acl_clone(const struct posix_acl *, gfp_t); extern int posix_acl_valid(const struct posix_acl *); extern int posix_acl_permission(struct inode *, const struct posix_acl *, int); -extern struct posix_acl *posix_acl_from_mode(mode_t, unsigned int __nocast); +extern struct posix_acl *posix_acl_from_mode(mode_t, gfp_t); extern int posix_acl_equiv_mode(const struct posix_acl *, mode_t *); extern int posix_acl_create_masq(struct posix_acl *, mode_t *); extern int posix_acl_chmod_masq(struct posix_acl *, mode_t); diff --git a/include/linux/radix-tree.h b/include/linux/radix-tree.h index 9c51917b1cc..045d4761feb 100644 --- a/include/linux/radix-tree.h +++ b/include/linux/radix-tree.h @@ -50,7 +50,7 @@ void *radix_tree_delete(struct radix_tree_root *, unsigned long); unsigned int radix_tree_gang_lookup(struct radix_tree_root *root, void **results, unsigned long first_index, unsigned int max_items); -int radix_tree_preload(unsigned int __nocast gfp_mask); +int radix_tree_preload(gfp_t gfp_mask); void radix_tree_init(void); void *radix_tree_tag_set(struct radix_tree_root *root, unsigned long index, int tag); diff --git a/include/linux/security.h b/include/linux/security.h index 0e43460d374..627382e7405 100644 --- a/include/linux/security.h +++ b/include/linux/security.h @@ -2634,8 +2634,7 @@ static inline int security_socket_getpeersec(struct socket *sock, char __user *o return security_ops->socket_getpeersec(sock, optval, optlen, len); } -static inline int security_sk_alloc(struct sock *sk, int family, - unsigned int __nocast priority) +static inline int security_sk_alloc(struct sock *sk, int family, gfp_t priority) { return security_ops->sk_alloc_security(sk, family, priority); } @@ -2752,8 +2751,7 @@ static inline int security_socket_getpeersec(struct socket *sock, char __user *o return -ENOPROTOOPT; } -static inline int security_sk_alloc(struct sock *sk, int family, - unsigned int __nocast priority) +static inline int security_sk_alloc(struct sock *sk, int family, gfp_t priority) { return 0; } diff --git a/include/linux/skbuff.h b/include/linux/skbuff.h index 466c879f82b..8f5d9e7f873 100644 --- a/include/linux/skbuff.h +++ b/include/linux/skbuff.h @@ -302,37 +302,37 @@ struct sk_buff { extern void __kfree_skb(struct sk_buff *skb); extern struct sk_buff *__alloc_skb(unsigned int size, - unsigned int __nocast priority, int fclone); + gfp_t priority, int fclone); static inline struct sk_buff *alloc_skb(unsigned int size, - unsigned int __nocast priority) + gfp_t priority) { return __alloc_skb(size, priority, 0); } static inline struct sk_buff *alloc_skb_fclone(unsigned int size, - unsigned int __nocast priority) + gfp_t priority) { return __alloc_skb(size, priority, 1); } extern struct sk_buff *alloc_skb_from_cache(kmem_cache_t *cp, unsigned int size, - unsigned int __nocast priority); + gfp_t priority); extern void kfree_skbmem(struct sk_buff *skb); extern struct sk_buff *skb_clone(struct sk_buff *skb, - unsigned int __nocast priority); + gfp_t priority); extern struct sk_buff *skb_copy(const struct sk_buff *skb, - unsigned int __nocast priority); + gfp_t priority); extern struct sk_buff *pskb_copy(struct sk_buff *skb, - unsigned int __nocast gfp_mask); + gfp_t gfp_mask); extern int pskb_expand_head(struct sk_buff *skb, int nhead, int ntail, - unsigned int __nocast gfp_mask); + gfp_t gfp_mask); extern struct sk_buff *skb_realloc_headroom(struct sk_buff *skb, unsigned int headroom); extern struct sk_buff *skb_copy_expand(const struct sk_buff *skb, int newheadroom, int newtailroom, - unsigned int __nocast priority); + gfp_t priority); extern struct sk_buff * skb_pad(struct sk_buff *skb, int pad); #define dev_kfree_skb(a) kfree_skb(a) extern void skb_over_panic(struct sk_buff *skb, int len, @@ -484,7 +484,7 @@ static inline int skb_shared(const struct sk_buff *skb) * NULL is returned on a memory allocation failure. */ static inline struct sk_buff *skb_share_check(struct sk_buff *skb, - unsigned int __nocast pri) + gfp_t pri) { might_sleep_if(pri & __GFP_WAIT); if (skb_shared(skb)) { @@ -516,7 +516,7 @@ static inline struct sk_buff *skb_share_check(struct sk_buff *skb, * %NULL is returned on a memory allocation failure. */ static inline struct sk_buff *skb_unshare(struct sk_buff *skb, - unsigned int __nocast pri) + gfp_t pri) { might_sleep_if(pri & __GFP_WAIT); if (skb_cloned(skb)) { @@ -1017,7 +1017,7 @@ static inline void __skb_queue_purge(struct sk_buff_head *list) * %NULL is returned in there is no free memory. */ static inline struct sk_buff *__dev_alloc_skb(unsigned int length, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { struct sk_buff *skb = alloc_skb(length + 16, gfp_mask); if (likely(skb)) @@ -1130,8 +1130,8 @@ static inline int skb_can_coalesce(struct sk_buff *skb, int i, * If there is no free memory -ENOMEM is returned, otherwise zero * is returned and the old skb data released. */ -extern int __skb_linearize(struct sk_buff *skb, unsigned int __nocast gfp); -static inline int skb_linearize(struct sk_buff *skb, unsigned int __nocast gfp) +extern int __skb_linearize(struct sk_buff *skb, gfp_t gfp); +static inline int skb_linearize(struct sk_buff *skb, gfp_t gfp) { return __skb_linearize(skb, gfp); } diff --git a/include/linux/slab.h b/include/linux/slab.h index 1f356f3bbc6..5fc04a16ecb 100644 --- a/include/linux/slab.h +++ b/include/linux/slab.h @@ -61,11 +61,11 @@ extern kmem_cache_t *kmem_cache_create(const char *, size_t, size_t, unsigned lo void (*)(void *, kmem_cache_t *, unsigned long)); extern int kmem_cache_destroy(kmem_cache_t *); extern int kmem_cache_shrink(kmem_cache_t *); -extern void *kmem_cache_alloc(kmem_cache_t *, unsigned int __nocast); +extern void *kmem_cache_alloc(kmem_cache_t *, gfp_t); extern void kmem_cache_free(kmem_cache_t *, void *); extern unsigned int kmem_cache_size(kmem_cache_t *); extern const char *kmem_cache_name(kmem_cache_t *); -extern kmem_cache_t *kmem_find_general_cachep(size_t size, unsigned int __nocast gfpflags); +extern kmem_cache_t *kmem_find_general_cachep(size_t size, gfp_t gfpflags); /* Size description struct for general caches. */ struct cache_sizes { @@ -74,9 +74,9 @@ struct cache_sizes { kmem_cache_t *cs_dmacachep; }; extern struct cache_sizes malloc_sizes[]; -extern void *__kmalloc(size_t, unsigned int __nocast); +extern void *__kmalloc(size_t, gfp_t); -static inline void *kmalloc(size_t size, unsigned int __nocast flags) +static inline void *kmalloc(size_t size, gfp_t flags) { if (__builtin_constant_p(size)) { int i = 0; @@ -99,7 +99,7 @@ found: return __kmalloc(size, flags); } -extern void *kzalloc(size_t, unsigned int __nocast); +extern void *kzalloc(size_t, gfp_t); /** * kcalloc - allocate memory for an array. The memory is set to zero. @@ -107,7 +107,7 @@ extern void *kzalloc(size_t, unsigned int __nocast); * @size: element size. * @flags: the type of memory to allocate. */ -static inline void *kcalloc(size_t n, size_t size, unsigned int __nocast flags) +static inline void *kcalloc(size_t n, size_t size, gfp_t flags) { if (n != 0 && size > INT_MAX / n) return NULL; @@ -118,15 +118,14 @@ extern void kfree(const void *); extern unsigned int ksize(const void *); #ifdef CONFIG_NUMA -extern void *kmem_cache_alloc_node(kmem_cache_t *, - unsigned int __nocast flags, int node); -extern void *kmalloc_node(size_t size, unsigned int __nocast flags, int node); +extern void *kmem_cache_alloc_node(kmem_cache_t *, gfp_t flags, int node); +extern void *kmalloc_node(size_t size, gfp_t flags, int node); #else static inline void *kmem_cache_alloc_node(kmem_cache_t *cachep, int flags, int node) { return kmem_cache_alloc(cachep, flags); } -static inline void *kmalloc_node(size_t size, unsigned int __nocast flags, int node) +static inline void *kmalloc_node(size_t size, gfp_t flags, int node) { return kmalloc(size, flags); } diff --git a/include/linux/string.h b/include/linux/string.h index dab2652acbd..369be3264a5 100644 --- a/include/linux/string.h +++ b/include/linux/string.h @@ -88,7 +88,7 @@ extern int memcmp(const void *,const void *,__kernel_size_t); extern void * memchr(const void *,int,__kernel_size_t); #endif -extern char *kstrdup(const char *s, unsigned int __nocast gfp); +extern char *kstrdup(const char *s, gfp_t gfp); #ifdef __cplusplus } diff --git a/include/linux/swap.h b/include/linux/swap.h index 3c9ff004815..a7bf1a3b149 100644 --- a/include/linux/swap.h +++ b/include/linux/swap.h @@ -147,7 +147,7 @@ struct swap_list_t { #define vm_swap_full() (nr_swap_pages*2 < total_swap_pages) /* linux/mm/oom_kill.c */ -extern void out_of_memory(unsigned int __nocast gfp_mask, int order); +extern void out_of_memory(gfp_t gfp_mask, int order); /* linux/mm/memory.c */ extern void swapin_readahead(swp_entry_t, unsigned long, struct vm_area_struct *); diff --git a/include/linux/textsearch.h b/include/linux/textsearch.h index 1a4990e448e..515046d1b2f 100644 --- a/include/linux/textsearch.h +++ b/include/linux/textsearch.h @@ -159,7 +159,7 @@ extern unsigned int textsearch_find_continuous(struct ts_config *, #define TS_PRIV_ALIGN(len) (((len) + TS_PRIV_ALIGNTO-1) & ~(TS_PRIV_ALIGNTO-1)) static inline struct ts_config *alloc_ts_config(size_t payload, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { struct ts_config *conf; diff --git a/include/linux/types.h b/include/linux/types.h index 2b678c22ca4..0aee34f9da9 100644 --- a/include/linux/types.h +++ b/include/linux/types.h @@ -165,6 +165,10 @@ typedef __u64 __bitwise __le64; typedef __u64 __bitwise __be64; #endif +#ifdef __KERNEL__ +typedef unsigned __nocast gfp_t; +#endif + struct ustat { __kernel_daddr_t f_tfree; __kernel_ino_t f_tinode; diff --git a/include/linux/vmalloc.h b/include/linux/vmalloc.h index b244f69ef68..3701a0673d2 100644 --- a/include/linux/vmalloc.h +++ b/include/linux/vmalloc.h @@ -34,8 +34,8 @@ struct vm_struct { extern void *vmalloc(unsigned long size); extern void *vmalloc_exec(unsigned long size); extern void *vmalloc_32(unsigned long size); -extern void *__vmalloc(unsigned long size, unsigned int __nocast gfp_mask, pgprot_t prot); -extern void *__vmalloc_area(struct vm_struct *area, unsigned int __nocast gfp_mask, pgprot_t prot); +extern void *__vmalloc(unsigned long size, gfp_t gfp_mask, pgprot_t prot); +extern void *__vmalloc_area(struct vm_struct *area, gfp_t gfp_mask, pgprot_t prot); extern void vfree(void *addr); extern void *vmap(struct page **pages, unsigned int count, diff --git a/include/net/bluetooth/bluetooth.h b/include/net/bluetooth/bluetooth.h index 6dfa4a61ffd..21045862484 100644 --- a/include/net/bluetooth/bluetooth.h +++ b/include/net/bluetooth/bluetooth.h @@ -136,7 +136,7 @@ struct bt_skb_cb { }; #define bt_cb(skb) ((struct bt_skb_cb *)(skb->cb)) -static inline struct sk_buff *bt_skb_alloc(unsigned int len, unsigned int __nocast how) +static inline struct sk_buff *bt_skb_alloc(unsigned int len, gfp_t how) { struct sk_buff *skb; diff --git a/include/net/bluetooth/rfcomm.h b/include/net/bluetooth/rfcomm.h index ffea9d54071..fbe557f7ea1 100644 --- a/include/net/bluetooth/rfcomm.h +++ b/include/net/bluetooth/rfcomm.h @@ -230,7 +230,7 @@ int rfcomm_send_rpn(struct rfcomm_session *s, int cr, u8 dlci, u8 xon_char, u8 xoff_char, u16 param_mask); /* ---- RFCOMM DLCs (channels) ---- */ -struct rfcomm_dlc *rfcomm_dlc_alloc(unsigned int __nocast prio); +struct rfcomm_dlc *rfcomm_dlc_alloc(gfp_t prio); void rfcomm_dlc_free(struct rfcomm_dlc *d); int rfcomm_dlc_open(struct rfcomm_dlc *d, bdaddr_t *src, bdaddr_t *dst, u8 channel); int rfcomm_dlc_close(struct rfcomm_dlc *d, int reason); diff --git a/include/net/dn_nsp.h b/include/net/dn_nsp.h index 8a0891e2e88..1ba03be0af3 100644 --- a/include/net/dn_nsp.h +++ b/include/net/dn_nsp.h @@ -19,9 +19,9 @@ extern void dn_nsp_send_data_ack(struct sock *sk); extern void dn_nsp_send_oth_ack(struct sock *sk); extern void dn_nsp_delayed_ack(struct sock *sk); extern void dn_send_conn_ack(struct sock *sk); -extern void dn_send_conn_conf(struct sock *sk, unsigned int __nocast gfp); +extern void dn_send_conn_conf(struct sock *sk, gfp_t gfp); extern void dn_nsp_send_disc(struct sock *sk, unsigned char type, - unsigned short reason, unsigned int __nocast gfp); + unsigned short reason, gfp_t gfp); extern void dn_nsp_return_disc(struct sk_buff *skb, unsigned char type, unsigned short reason); extern void dn_nsp_send_link(struct sock *sk, unsigned char lsflags, char fcval); @@ -29,14 +29,14 @@ extern void dn_nsp_send_conninit(struct sock *sk, unsigned char flags); extern void dn_nsp_output(struct sock *sk); extern int dn_nsp_check_xmit_queue(struct sock *sk, struct sk_buff *skb, struct sk_buff_head *q, unsigned short acknum); -extern void dn_nsp_queue_xmit(struct sock *sk, struct sk_buff *skb, unsigned int __nocast gfp, int oob); +extern void dn_nsp_queue_xmit(struct sock *sk, struct sk_buff *skb, gfp_t gfp, int oob); extern unsigned long dn_nsp_persist(struct sock *sk); extern int dn_nsp_xmit_timeout(struct sock *sk); extern int dn_nsp_rx(struct sk_buff *); extern int dn_nsp_backlog_rcv(struct sock *sk, struct sk_buff *skb); -extern struct sk_buff *dn_alloc_skb(struct sock *sk, int size, unsigned int __nocast pri); +extern struct sk_buff *dn_alloc_skb(struct sock *sk, int size, gfp_t pri); extern struct sk_buff *dn_alloc_send_skb(struct sock *sk, size_t *size, int noblock, long timeo, int *err); #define NSP_REASON_OK 0 /* No error */ diff --git a/include/net/dn_route.h b/include/net/dn_route.h index 11fe973cf38..5122da3f2eb 100644 --- a/include/net/dn_route.h +++ b/include/net/dn_route.h @@ -15,7 +15,7 @@ GNU General Public License for more details. *******************************************************************************/ -extern struct sk_buff *dn_alloc_skb(struct sock *sk, int size, unsigned int __nocast pri); +extern struct sk_buff *dn_alloc_skb(struct sock *sk, int size, gfp_t pri); extern int dn_route_output_sock(struct dst_entry **pprt, struct flowi *, struct sock *sk, int flags); extern int dn_cache_dump(struct sk_buff *skb, struct netlink_callback *cb); extern int dn_cache_getroute(struct sk_buff *skb, struct nlmsghdr *nlh, void *arg); diff --git a/include/net/inet_connection_sock.h b/include/net/inet_connection_sock.h index 651f824c100..b0c99060b78 100644 --- a/include/net/inet_connection_sock.h +++ b/include/net/inet_connection_sock.h @@ -94,7 +94,7 @@ static inline void *inet_csk_ca(const struct sock *sk) extern struct sock *inet_csk_clone(struct sock *sk, const struct request_sock *req, - const unsigned int __nocast priority); + const gfp_t priority); enum inet_csk_ack_state_t { ICSK_ACK_SCHED = 1, diff --git a/include/net/ip_vs.h b/include/net/ip_vs.h index ecb2b061f59..3b5559a023a 100644 --- a/include/net/ip_vs.h +++ b/include/net/ip_vs.h @@ -832,7 +832,7 @@ extern void ip_vs_app_inc_put(struct ip_vs_app *inc); extern int ip_vs_app_pkt_out(struct ip_vs_conn *, struct sk_buff **pskb); extern int ip_vs_app_pkt_in(struct ip_vs_conn *, struct sk_buff **pskb); -extern int ip_vs_skb_replace(struct sk_buff *skb, unsigned int __nocast pri, +extern int ip_vs_skb_replace(struct sk_buff *skb, gfp_t pri, char *o_buf, int o_len, char *n_buf, int n_len); extern int ip_vs_app_init(void); extern void ip_vs_app_cleanup(void); diff --git a/include/net/llc_conn.h b/include/net/llc_conn.h index 54852ff6033..00730d21b52 100644 --- a/include/net/llc_conn.h +++ b/include/net/llc_conn.h @@ -93,7 +93,7 @@ static __inline__ char llc_backlog_type(struct sk_buff *skb) return skb->cb[sizeof(skb->cb) - 1]; } -extern struct sock *llc_sk_alloc(int family, unsigned int __nocast priority, +extern struct sock *llc_sk_alloc(int family, gfp_t priority, struct proto *prot); extern void llc_sk_free(struct sock *sk); diff --git a/include/net/sctp/sctp.h b/include/net/sctp/sctp.h index e1d5ec1c23c..8f241216f46 100644 --- a/include/net/sctp/sctp.h +++ b/include/net/sctp/sctp.h @@ -125,7 +125,7 @@ */ extern struct sock *sctp_get_ctl_sock(void); extern int sctp_copy_local_addr_list(struct sctp_bind_addr *, - sctp_scope_t, unsigned int __nocast gfp, + sctp_scope_t, gfp_t gfp, int flags); extern struct sctp_pf *sctp_get_pf_specific(sa_family_t family); extern int sctp_register_pf(struct sctp_pf *, sa_family_t); diff --git a/include/net/sctp/sm.h b/include/net/sctp/sm.h index 58462164d96..1eac3d0eb7a 100644 --- a/include/net/sctp/sm.h +++ b/include/net/sctp/sm.h @@ -181,17 +181,17 @@ const sctp_sm_table_entry_t *sctp_sm_lookup_event(sctp_event_t, int sctp_chunk_iif(const struct sctp_chunk *); struct sctp_association *sctp_make_temp_asoc(const struct sctp_endpoint *, struct sctp_chunk *, - unsigned int __nocast gfp); + gfp_t gfp); __u32 sctp_generate_verification_tag(void); void sctp_populate_tie_tags(__u8 *cookie, __u32 curTag, __u32 hisTag); /* Prototypes for chunk-building functions. */ struct sctp_chunk *sctp_make_init(const struct sctp_association *, const struct sctp_bind_addr *, - unsigned int __nocast gfp, int vparam_len); + gfp_t gfp, int vparam_len); struct sctp_chunk *sctp_make_init_ack(const struct sctp_association *, const struct sctp_chunk *, - const unsigned int __nocast gfp, + const gfp_t gfp, const int unkparam_len); struct sctp_chunk *sctp_make_cookie_echo(const struct sctp_association *, const struct sctp_chunk *); @@ -265,7 +265,7 @@ int sctp_do_sm(sctp_event_t event_type, sctp_subtype_t subtype, struct sctp_endpoint *, struct sctp_association *asoc, void *event_arg, - unsigned int __nocast gfp); + gfp_t gfp); /* 2nd level prototypes */ void sctp_generate_t3_rtx_event(unsigned long peer); @@ -276,7 +276,7 @@ void sctp_ootb_pkt_free(struct sctp_packet *); struct sctp_association *sctp_unpack_cookie(const struct sctp_endpoint *, const struct sctp_association *, struct sctp_chunk *, - unsigned int __nocast gfp, int *err, + gfp_t gfp, int *err, struct sctp_chunk **err_chk_p); int sctp_addip_addr_config(struct sctp_association *, sctp_param_t, struct sockaddr_storage*, int); diff --git a/include/net/sctp/structs.h b/include/net/sctp/structs.h index 994009bbe3b..9c385b6417c 100644 --- a/include/net/sctp/structs.h +++ b/include/net/sctp/structs.h @@ -446,7 +446,7 @@ struct sctp_ssnmap { }; struct sctp_ssnmap *sctp_ssnmap_new(__u16 in, __u16 out, - unsigned int __nocast gfp); + gfp_t gfp); void sctp_ssnmap_free(struct sctp_ssnmap *map); void sctp_ssnmap_clear(struct sctp_ssnmap *map); @@ -947,7 +947,7 @@ struct sctp_transport { }; struct sctp_transport *sctp_transport_new(const union sctp_addr *, - unsigned int __nocast); + gfp_t); void sctp_transport_set_owner(struct sctp_transport *, struct sctp_association *); void sctp_transport_route(struct sctp_transport *, union sctp_addr *, @@ -1095,10 +1095,10 @@ void sctp_bind_addr_init(struct sctp_bind_addr *, __u16 port); void sctp_bind_addr_free(struct sctp_bind_addr *); int sctp_bind_addr_copy(struct sctp_bind_addr *dest, const struct sctp_bind_addr *src, - sctp_scope_t scope, unsigned int __nocast gfp, + sctp_scope_t scope, gfp_t gfp, int flags); int sctp_add_bind_addr(struct sctp_bind_addr *, union sctp_addr *, - unsigned int __nocast gfp); + gfp_t gfp); int sctp_del_bind_addr(struct sctp_bind_addr *, union sctp_addr *); int sctp_bind_addr_match(struct sctp_bind_addr *, const union sctp_addr *, struct sctp_sock *); @@ -1108,9 +1108,9 @@ union sctp_addr *sctp_find_unmatch_addr(struct sctp_bind_addr *bp, struct sctp_sock *opt); union sctp_params sctp_bind_addrs_to_raw(const struct sctp_bind_addr *bp, int *addrs_len, - unsigned int __nocast gfp); + gfp_t gfp); int sctp_raw_to_bind_addrs(struct sctp_bind_addr *bp, __u8 *raw, int len, - __u16 port, unsigned int __nocast gfp); + __u16 port, gfp_t gfp); sctp_scope_t sctp_scope(const union sctp_addr *); int sctp_in_scope(const union sctp_addr *addr, const sctp_scope_t scope); @@ -1239,7 +1239,7 @@ static inline struct sctp_endpoint *sctp_ep(struct sctp_ep_common *base) } /* These are function signatures for manipulating endpoints. */ -struct sctp_endpoint *sctp_endpoint_new(struct sock *, unsigned int __nocast); +struct sctp_endpoint *sctp_endpoint_new(struct sock *, gfp_t); void sctp_endpoint_free(struct sctp_endpoint *); void sctp_endpoint_put(struct sctp_endpoint *); void sctp_endpoint_hold(struct sctp_endpoint *); @@ -1260,7 +1260,7 @@ int sctp_verify_init(const struct sctp_association *asoc, sctp_cid_t, struct sctp_chunk **err_chunk); int sctp_process_init(struct sctp_association *, sctp_cid_t cid, const union sctp_addr *peer, - sctp_init_chunk_t *init, unsigned int __nocast gfp); + sctp_init_chunk_t *init, gfp_t gfp); __u32 sctp_generate_tag(const struct sctp_endpoint *); __u32 sctp_generate_tsn(const struct sctp_endpoint *); @@ -1723,7 +1723,7 @@ static inline struct sctp_association *sctp_assoc(struct sctp_ep_common *base) struct sctp_association * sctp_association_new(const struct sctp_endpoint *, const struct sock *, - sctp_scope_t scope, unsigned int __nocast gfp); + sctp_scope_t scope, gfp_t gfp); void sctp_association_free(struct sctp_association *); void sctp_association_put(struct sctp_association *); void sctp_association_hold(struct sctp_association *); @@ -1739,7 +1739,7 @@ int sctp_assoc_lookup_laddr(struct sctp_association *asoc, const union sctp_addr *laddr); struct sctp_transport *sctp_assoc_add_peer(struct sctp_association *, const union sctp_addr *address, - const unsigned int __nocast gfp, + const gfp_t gfp, const int peer_state); void sctp_assoc_del_peer(struct sctp_association *asoc, const union sctp_addr *addr); @@ -1764,10 +1764,10 @@ void sctp_assoc_rwnd_decrease(struct sctp_association *, unsigned); void sctp_assoc_set_primary(struct sctp_association *, struct sctp_transport *); int sctp_assoc_set_bind_addr_from_ep(struct sctp_association *, - unsigned int __nocast); + gfp_t); int sctp_assoc_set_bind_addr_from_cookie(struct sctp_association *, struct sctp_cookie*, - unsigned int __nocast gfp); + gfp_t gfp); int sctp_cmp_addr_exact(const union sctp_addr *ss1, const union sctp_addr *ss2); diff --git a/include/net/sctp/ulpevent.h b/include/net/sctp/ulpevent.h index 90fe4bf6754..6c40cfc4832 100644 --- a/include/net/sctp/ulpevent.h +++ b/include/net/sctp/ulpevent.h @@ -88,7 +88,7 @@ struct sctp_ulpevent *sctp_ulpevent_make_assoc_change( __u16 error, __u16 outbound, __u16 inbound, - unsigned int __nocast gfp); + gfp_t gfp); struct sctp_ulpevent *sctp_ulpevent_make_peer_addr_change( const struct sctp_association *asoc, @@ -96,35 +96,35 @@ struct sctp_ulpevent *sctp_ulpevent_make_peer_addr_change( int flags, int state, int error, - unsigned int __nocast gfp); + gfp_t gfp); struct sctp_ulpevent *sctp_ulpevent_make_remote_error( const struct sctp_association *asoc, struct sctp_chunk *chunk, __u16 flags, - unsigned int __nocast gfp); + gfp_t gfp); struct sctp_ulpevent *sctp_ulpevent_make_send_failed( const struct sctp_association *asoc, struct sctp_chunk *chunk, __u16 flags, __u32 error, - unsigned int __nocast gfp); + gfp_t gfp); struct sctp_ulpevent *sctp_ulpevent_make_shutdown_event( const struct sctp_association *asoc, __u16 flags, - unsigned int __nocast gfp); + gfp_t gfp); struct sctp_ulpevent *sctp_ulpevent_make_pdapi( const struct sctp_association *asoc, - __u32 indication, unsigned int __nocast gfp); + __u32 indication, gfp_t gfp); struct sctp_ulpevent *sctp_ulpevent_make_adaption_indication( - const struct sctp_association *asoc, unsigned int __nocast gfp); + const struct sctp_association *asoc, gfp_t gfp); struct sctp_ulpevent *sctp_ulpevent_make_rcvmsg(struct sctp_association *asoc, struct sctp_chunk *chunk, - unsigned int __nocast gfp); + gfp_t gfp); void sctp_ulpevent_read_sndrcvinfo(const struct sctp_ulpevent *event, struct msghdr *); diff --git a/include/net/sctp/ulpqueue.h b/include/net/sctp/ulpqueue.h index 1a60c6d943c..a43c8788b65 100644 --- a/include/net/sctp/ulpqueue.h +++ b/include/net/sctp/ulpqueue.h @@ -62,22 +62,19 @@ struct sctp_ulpq *sctp_ulpq_init(struct sctp_ulpq *, void sctp_ulpq_free(struct sctp_ulpq *); /* Add a new DATA chunk for processing. */ -int sctp_ulpq_tail_data(struct sctp_ulpq *, struct sctp_chunk *, - unsigned int __nocast); +int sctp_ulpq_tail_data(struct sctp_ulpq *, struct sctp_chunk *, gfp_t); /* Add a new event for propagation to the ULP. */ int sctp_ulpq_tail_event(struct sctp_ulpq *, struct sctp_ulpevent *ev); /* Renege previously received chunks. */ -void sctp_ulpq_renege(struct sctp_ulpq *, struct sctp_chunk *, - unsigned int __nocast); +void sctp_ulpq_renege(struct sctp_ulpq *, struct sctp_chunk *, gfp_t); /* Perform partial delivery. */ -void sctp_ulpq_partial_delivery(struct sctp_ulpq *, struct sctp_chunk *, - unsigned int __nocast); +void sctp_ulpq_partial_delivery(struct sctp_ulpq *, struct sctp_chunk *, gfp_t); /* Abort the partial delivery. */ -void sctp_ulpq_abort_pd(struct sctp_ulpq *, unsigned int __nocast); +void sctp_ulpq_abort_pd(struct sctp_ulpq *, gfp_t); /* Clear the partial data delivery condition on this socket. */ int sctp_clear_pd(struct sock *sk); diff --git a/include/net/sock.h b/include/net/sock.h index b6440805c42..ecb75526cba 100644 --- a/include/net/sock.h +++ b/include/net/sock.h @@ -739,18 +739,18 @@ extern void FASTCALL(release_sock(struct sock *sk)); #define bh_unlock_sock(__sk) spin_unlock(&((__sk)->sk_lock.slock)) extern struct sock *sk_alloc(int family, - unsigned int __nocast priority, + gfp_t priority, struct proto *prot, int zero_it); extern void sk_free(struct sock *sk); extern struct sock *sk_clone(const struct sock *sk, - const unsigned int __nocast priority); + const gfp_t priority); extern struct sk_buff *sock_wmalloc(struct sock *sk, unsigned long size, int force, - unsigned int __nocast priority); + gfp_t priority); extern struct sk_buff *sock_rmalloc(struct sock *sk, unsigned long size, int force, - unsigned int __nocast priority); + gfp_t priority); extern void sock_wfree(struct sk_buff *skb); extern void sock_rfree(struct sk_buff *skb); @@ -766,7 +766,7 @@ extern struct sk_buff *sock_alloc_send_skb(struct sock *sk, int noblock, int *errcode); extern void *sock_kmalloc(struct sock *sk, int size, - unsigned int __nocast priority); + gfp_t priority); extern void sock_kfree_s(struct sock *sk, void *mem, int size); extern void sk_send_sigurg(struct sock *sk); @@ -1201,7 +1201,7 @@ static inline void sk_stream_moderate_sndbuf(struct sock *sk) static inline struct sk_buff *sk_stream_alloc_pskb(struct sock *sk, int size, int mem, - unsigned int __nocast gfp) + gfp_t gfp) { struct sk_buff *skb; int hdr_len; @@ -1224,7 +1224,7 @@ static inline struct sk_buff *sk_stream_alloc_pskb(struct sock *sk, static inline struct sk_buff *sk_stream_alloc_skb(struct sock *sk, int size, - unsigned int __nocast gfp) + gfp_t gfp) { return sk_stream_alloc_pskb(sk, size, 0, gfp); } @@ -1255,7 +1255,7 @@ static inline int sock_writeable(const struct sock *sk) return atomic_read(&sk->sk_wmem_alloc) < (sk->sk_sndbuf / 2); } -static inline unsigned int __nocast gfp_any(void) +static inline gfp_t gfp_any(void) { return in_softirq() ? GFP_ATOMIC : GFP_KERNEL; } diff --git a/include/net/tcp.h b/include/net/tcp.h index 97af77c4d09..c24339c4e31 100644 --- a/include/net/tcp.h +++ b/include/net/tcp.h @@ -460,8 +460,7 @@ extern void tcp_send_probe0(struct sock *); extern void tcp_send_partial(struct sock *); extern int tcp_write_wakeup(struct sock *); extern void tcp_send_fin(struct sock *sk); -extern void tcp_send_active_reset(struct sock *sk, - unsigned int __nocast priority); +extern void tcp_send_active_reset(struct sock *sk, gfp_t priority); extern int tcp_send_synack(struct sock *); extern void tcp_push_one(struct sock *, unsigned int mss_now); extern void tcp_send_ack(struct sock *sk); diff --git a/include/net/xfrm.h b/include/net/xfrm.h index b6e72f890c6..5beae1ccd57 100644 --- a/include/net/xfrm.h +++ b/include/net/xfrm.h @@ -875,7 +875,7 @@ static inline int xfrm_dst_lookup(struct xfrm_dst **dst, struct flowi *fl, unsig } #endif -struct xfrm_policy *xfrm_policy_alloc(unsigned int __nocast gfp); +struct xfrm_policy *xfrm_policy_alloc(gfp_t gfp); extern int xfrm_policy_walk(int (*func)(struct xfrm_policy *, int, int, void*), void *); int xfrm_policy_insert(int dir, struct xfrm_policy *policy, int excl); struct xfrm_policy *xfrm_policy_bysel(int dir, struct xfrm_selector *sel, diff --git a/include/rdma/ib_mad.h b/include/rdma/ib_mad.h index 0e293fe733b..4172e6841e3 100644 --- a/include/rdma/ib_mad.h +++ b/include/rdma/ib_mad.h @@ -596,7 +596,7 @@ struct ib_mad_send_buf * ib_create_send_mad(struct ib_mad_agent *mad_agent, u32 remote_qpn, u16 pkey_index, struct ib_ah *ah, int rmpp_active, int hdr_len, int data_len, - unsigned int __nocast gfp_mask); + gfp_t gfp_mask); /** * ib_free_send_mad - Returns data buffers used to send a MAD. diff --git a/include/rdma/ib_sa.h b/include/rdma/ib_sa.h index a7555c800ec..f404fe21cc2 100644 --- a/include/rdma/ib_sa.h +++ b/include/rdma/ib_sa.h @@ -285,7 +285,7 @@ void ib_sa_cancel_query(int id, struct ib_sa_query *query); int ib_sa_path_rec_get(struct ib_device *device, u8 port_num, struct ib_sa_path_rec *rec, ib_sa_comp_mask comp_mask, - int timeout_ms, unsigned int __nocast gfp_mask, + int timeout_ms, gfp_t gfp_mask, void (*callback)(int status, struct ib_sa_path_rec *resp, void *context), @@ -296,7 +296,7 @@ int ib_sa_mcmember_rec_query(struct ib_device *device, u8 port_num, u8 method, struct ib_sa_mcmember_rec *rec, ib_sa_comp_mask comp_mask, - int timeout_ms, unsigned int __nocast gfp_mask, + int timeout_ms, gfp_t gfp_mask, void (*callback)(int status, struct ib_sa_mcmember_rec *resp, void *context), @@ -307,7 +307,7 @@ int ib_sa_service_rec_query(struct ib_device *device, u8 port_num, u8 method, struct ib_sa_service_rec *rec, ib_sa_comp_mask comp_mask, - int timeout_ms, unsigned int __nocast gfp_mask, + int timeout_ms, gfp_t gfp_mask, void (*callback)(int status, struct ib_sa_service_rec *resp, void *context), @@ -342,7 +342,7 @@ static inline int ib_sa_mcmember_rec_set(struct ib_device *device, u8 port_num, struct ib_sa_mcmember_rec *rec, ib_sa_comp_mask comp_mask, - int timeout_ms, unsigned int __nocast gfp_mask, + int timeout_ms, gfp_t gfp_mask, void (*callback)(int status, struct ib_sa_mcmember_rec *resp, void *context), @@ -384,7 +384,7 @@ static inline int ib_sa_mcmember_rec_delete(struct ib_device *device, u8 port_num, struct ib_sa_mcmember_rec *rec, ib_sa_comp_mask comp_mask, - int timeout_ms, unsigned int __nocast gfp_mask, + int timeout_ms, gfp_t gfp_mask, void (*callback)(int status, struct ib_sa_mcmember_rec *resp, void *context), diff --git a/include/rxrpc/call.h b/include/rxrpc/call.h index 8118731e7d9..b86f8374351 100644 --- a/include/rxrpc/call.h +++ b/include/rxrpc/call.h @@ -203,7 +203,7 @@ extern int rxrpc_call_write_data(struct rxrpc_call *call, size_t sioc, struct kvec *siov, uint8_t rxhdr_flags, - unsigned int __nocast alloc_flags, + gfp_t alloc_flags, int dup_data, size_t *size_sent); diff --git a/include/rxrpc/message.h b/include/rxrpc/message.h index 983d9f9eee1..b318f273d4f 100644 --- a/include/rxrpc/message.h +++ b/include/rxrpc/message.h @@ -63,7 +63,7 @@ extern int rxrpc_conn_newmsg(struct rxrpc_connection *conn, uint8_t type, int count, struct kvec *diov, - unsigned int __nocast alloc_flags, + gfp_t alloc_flags, struct rxrpc_message **_msg); extern int rxrpc_conn_sendmsg(struct rxrpc_connection *conn, struct rxrpc_message *msg); diff --git a/include/sound/core.h b/include/sound/core.h index 26160adcdff..6d971a4c4ca 100644 --- a/include/sound/core.h +++ b/include/sound/core.h @@ -290,13 +290,13 @@ void snd_memory_init(void); void snd_memory_done(void); int snd_memory_info_init(void); int snd_memory_info_done(void); -void *snd_hidden_kmalloc(size_t size, unsigned int __nocast flags); -void *snd_hidden_kzalloc(size_t size, unsigned int __nocast flags); -void *snd_hidden_kcalloc(size_t n, size_t size, unsigned int __nocast flags); +void *snd_hidden_kmalloc(size_t size, gfp_t flags); +void *snd_hidden_kzalloc(size_t size, gfp_t flags); +void *snd_hidden_kcalloc(size_t n, size_t size, gfp_t flags); void snd_hidden_kfree(const void *obj); void *snd_hidden_vmalloc(unsigned long size); void snd_hidden_vfree(void *obj); -char *snd_hidden_kstrdup(const char *s, unsigned int __nocast flags); +char *snd_hidden_kstrdup(const char *s, gfp_t flags); #define kmalloc(size, flags) snd_hidden_kmalloc(size, flags) #define kzalloc(size, flags) snd_hidden_kzalloc(size, flags) #define kcalloc(n, size, flags) snd_hidden_kcalloc(n, size, flags) diff --git a/include/sound/driver.h b/include/sound/driver.h index 0d12456ec3a..1ec2fae050a 100644 --- a/include/sound/driver.h +++ b/include/sound/driver.h @@ -51,7 +51,7 @@ #ifdef CONFIG_SND_DEBUG_MEMORY #include #include -void *snd_wrapper_kmalloc(size_t, unsigned int __nocast); +void *snd_wrapper_kmalloc(size_t, gfp_t); #undef kmalloc void snd_wrapper_kfree(const void *); #undef kfree diff --git a/kernel/audit.c b/kernel/audit.c index 83096b67510..aefa73a8a58 100644 --- a/kernel/audit.c +++ b/kernel/audit.c @@ -560,7 +560,7 @@ static void audit_buffer_free(struct audit_buffer *ab) } static struct audit_buffer * audit_buffer_alloc(struct audit_context *ctx, - unsigned int __nocast gfp_mask, int type) + gfp_t gfp_mask, int type) { unsigned long flags; struct audit_buffer *ab = NULL; diff --git a/kernel/cpuset.c b/kernel/cpuset.c index 45a5719a010..28176d083f7 100644 --- a/kernel/cpuset.c +++ b/kernel/cpuset.c @@ -1670,7 +1670,7 @@ static const struct cpuset *nearest_exclusive_ancestor(const struct cpuset *cs) * GFP_USER - only nodes in current tasks mems allowed ok. **/ -int cpuset_zone_allowed(struct zone *z, unsigned int __nocast gfp_mask) +int cpuset_zone_allowed(struct zone *z, gfp_t gfp_mask) { int node; /* node that zone z is on */ const struct cpuset *cs; /* current cpuset ancestors */ diff --git a/kernel/kfifo.c b/kernel/kfifo.c index 179baafcdd9..64ab045c3d9 100644 --- a/kernel/kfifo.c +++ b/kernel/kfifo.c @@ -36,7 +36,7 @@ * struct kfifo with kfree(). */ struct kfifo *kfifo_init(unsigned char *buffer, unsigned int size, - unsigned int __nocast gfp_mask, spinlock_t *lock) + gfp_t gfp_mask, spinlock_t *lock) { struct kfifo *fifo; @@ -64,7 +64,7 @@ EXPORT_SYMBOL(kfifo_init); * * The size will be rounded-up to a power of 2. */ -struct kfifo *kfifo_alloc(unsigned int size, unsigned int __nocast gfp_mask, spinlock_t *lock) +struct kfifo *kfifo_alloc(unsigned int size, gfp_t gfp_mask, spinlock_t *lock) { unsigned char *buffer; struct kfifo *ret; diff --git a/kernel/signal.c b/kernel/signal.c index c135f5aa2c2..cba193ceda0 100644 --- a/kernel/signal.c +++ b/kernel/signal.c @@ -262,7 +262,7 @@ next_signal(struct sigpending *pending, sigset_t *mask) return sig; } -static struct sigqueue *__sigqueue_alloc(struct task_struct *t, unsigned int __nocast flags, +static struct sigqueue *__sigqueue_alloc(struct task_struct *t, gfp_t flags, int override_rlimit) { struct sigqueue *q = NULL; diff --git a/lib/radix-tree.c b/lib/radix-tree.c index 6a8bc6e0643..d1c057e71b6 100644 --- a/lib/radix-tree.c +++ b/lib/radix-tree.c @@ -110,7 +110,7 @@ radix_tree_node_free(struct radix_tree_node *node) * success, return zero, with preemption disabled. On error, return -ENOMEM * with preemption not disabled. */ -int radix_tree_preload(unsigned int __nocast gfp_mask) +int radix_tree_preload(gfp_t gfp_mask) { struct radix_tree_preload *rtp; struct radix_tree_node *node; diff --git a/lib/ts_bm.c b/lib/ts_bm.c index 1b61fceef77..8a8b3a16133 100644 --- a/lib/ts_bm.c +++ b/lib/ts_bm.c @@ -127,7 +127,7 @@ static void compute_prefix_tbl(struct ts_bm *bm, const u8 *pattern, } static struct ts_config *bm_init(const void *pattern, unsigned int len, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { struct ts_config *conf; struct ts_bm *bm; diff --git a/lib/ts_fsm.c b/lib/ts_fsm.c index ef9779e0050..ca3211206ee 100644 --- a/lib/ts_fsm.c +++ b/lib/ts_fsm.c @@ -258,7 +258,7 @@ found_match: } static struct ts_config *fsm_init(const void *pattern, unsigned int len, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { int i, err = -EINVAL; struct ts_config *conf; diff --git a/lib/ts_kmp.c b/lib/ts_kmp.c index e45f0f0c237..7fd45451b44 100644 --- a/lib/ts_kmp.c +++ b/lib/ts_kmp.c @@ -87,7 +87,7 @@ static inline void compute_prefix_tbl(const u8 *pattern, unsigned int len, } static struct ts_config *kmp_init(const void *pattern, unsigned int len, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { struct ts_config *conf; struct ts_kmp *kmp; diff --git a/mm/highmem.c b/mm/highmem.c index 40091159946..90e1861e2da 100644 --- a/mm/highmem.c +++ b/mm/highmem.c @@ -30,7 +30,7 @@ static mempool_t *page_pool, *isa_page_pool; -static void *page_pool_alloc(unsigned int __nocast gfp_mask, void *data) +static void *page_pool_alloc(gfp_t gfp_mask, void *data) { unsigned int gfp = gfp_mask | (unsigned int) (long) data; diff --git a/mm/mempolicy.c b/mm/mempolicy.c index 9033f0859aa..37af443eb09 100644 --- a/mm/mempolicy.c +++ b/mm/mempolicy.c @@ -687,7 +687,7 @@ get_vma_policy(struct task_struct *task, struct vm_area_struct *vma, unsigned lo } /* Return a zonelist representing a mempolicy */ -static struct zonelist *zonelist_policy(unsigned int __nocast gfp, struct mempolicy *policy) +static struct zonelist *zonelist_policy(gfp_t gfp, struct mempolicy *policy) { int nd; @@ -751,7 +751,7 @@ static unsigned offset_il_node(struct mempolicy *pol, /* Allocate a page in interleaved policy. Own path because it needs to do special accounting. */ -static struct page *alloc_page_interleave(unsigned int __nocast gfp, unsigned order, unsigned nid) +static struct page *alloc_page_interleave(gfp_t gfp, unsigned order, unsigned nid) { struct zonelist *zl; struct page *page; @@ -789,7 +789,7 @@ static struct page *alloc_page_interleave(unsigned int __nocast gfp, unsigned or * Should be called with the mm_sem of the vma hold. */ struct page * -alloc_page_vma(unsigned int __nocast gfp, struct vm_area_struct *vma, unsigned long addr) +alloc_page_vma(gfp_t gfp, struct vm_area_struct *vma, unsigned long addr) { struct mempolicy *pol = get_vma_policy(current, vma, addr); @@ -832,7 +832,7 @@ alloc_page_vma(unsigned int __nocast gfp, struct vm_area_struct *vma, unsigned l * 1) it's ok to take cpuset_sem (can WAIT), and * 2) allocating for current task (not interrupt). */ -struct page *alloc_pages_current(unsigned int __nocast gfp, unsigned order) +struct page *alloc_pages_current(gfp_t gfp, unsigned order) { struct mempolicy *pol = current->mempolicy; diff --git a/mm/mempool.c b/mm/mempool.c index 65f2957b8d5..9e377ea700b 100644 --- a/mm/mempool.c +++ b/mm/mempool.c @@ -112,7 +112,7 @@ EXPORT_SYMBOL(mempool_create_node); * while this function is running. mempool_alloc() & mempool_free() * might be called (eg. from IRQ contexts) while this function executes. */ -int mempool_resize(mempool_t *pool, int new_min_nr, unsigned int __nocast gfp_mask) +int mempool_resize(mempool_t *pool, int new_min_nr, gfp_t gfp_mask) { void *element; void **new_elements; @@ -200,7 +200,7 @@ EXPORT_SYMBOL(mempool_destroy); * *never* fails when called from process contexts. (it might * fail if called from an IRQ context.) */ -void * mempool_alloc(mempool_t *pool, unsigned int __nocast gfp_mask) +void * mempool_alloc(mempool_t *pool, gfp_t gfp_mask) { void *element; unsigned long flags; @@ -276,7 +276,7 @@ EXPORT_SYMBOL(mempool_free); /* * A commonly used alloc and free fn. */ -void *mempool_alloc_slab(unsigned int __nocast gfp_mask, void *pool_data) +void *mempool_alloc_slab(gfp_t gfp_mask, void *pool_data) { kmem_cache_t *mem = (kmem_cache_t *) pool_data; return kmem_cache_alloc(mem, gfp_mask); diff --git a/mm/nommu.c b/mm/nommu.c index 064d7044289..0ef241ae376 100644 --- a/mm/nommu.c +++ b/mm/nommu.c @@ -157,8 +157,7 @@ void vfree(void *addr) kfree(addr); } -void *__vmalloc(unsigned long size, unsigned int __nocast gfp_mask, - pgprot_t prot) +void *__vmalloc(unsigned long size, gfp_t gfp_mask, pgprot_t prot) { /* * kmalloc doesn't like __GFP_HIGHMEM for some reason diff --git a/mm/oom_kill.c b/mm/oom_kill.c index ac3bf33e537..d348b903595 100644 --- a/mm/oom_kill.c +++ b/mm/oom_kill.c @@ -263,7 +263,7 @@ static struct mm_struct *oom_kill_process(struct task_struct *p) * OR try to be smart about which process to kill. Note that we * don't have to be perfect here, we just have to be good. */ -void out_of_memory(unsigned int __nocast gfp_mask, int order) +void out_of_memory(gfp_t gfp_mask, int order) { struct mm_struct *mm = NULL; task_t * p; diff --git a/mm/page_alloc.c b/mm/page_alloc.c index ae2903339e7..cc1fe2672a3 100644 --- a/mm/page_alloc.c +++ b/mm/page_alloc.c @@ -671,7 +671,7 @@ void fastcall free_cold_page(struct page *page) free_hot_cold_page(page, 1); } -static inline void prep_zero_page(struct page *page, int order, unsigned int __nocast gfp_flags) +static inline void prep_zero_page(struct page *page, int order, gfp_t gfp_flags) { int i; @@ -686,7 +686,7 @@ static inline void prep_zero_page(struct page *page, int order, unsigned int __n * or two. */ static struct page * -buffered_rmqueue(struct zone *zone, int order, unsigned int __nocast gfp_flags) +buffered_rmqueue(struct zone *zone, int order, gfp_t gfp_flags) { unsigned long flags; struct page *page = NULL; @@ -761,7 +761,7 @@ int zone_watermark_ok(struct zone *z, int order, unsigned long mark, } static inline int -should_reclaim_zone(struct zone *z, unsigned int gfp_mask) +should_reclaim_zone(struct zone *z, gfp_t gfp_mask) { if (!z->reclaim_pages) return 0; @@ -774,7 +774,7 @@ should_reclaim_zone(struct zone *z, unsigned int gfp_mask) * This is the 'heart' of the zoned buddy allocator. */ struct page * fastcall -__alloc_pages(unsigned int __nocast gfp_mask, unsigned int order, +__alloc_pages(gfp_t gfp_mask, unsigned int order, struct zonelist *zonelist) { const int wait = gfp_mask & __GFP_WAIT; @@ -977,7 +977,7 @@ EXPORT_SYMBOL(__alloc_pages); /* * Common helper functions. */ -fastcall unsigned long __get_free_pages(unsigned int __nocast gfp_mask, unsigned int order) +fastcall unsigned long __get_free_pages(gfp_t gfp_mask, unsigned int order) { struct page * page; page = alloc_pages(gfp_mask, order); @@ -988,7 +988,7 @@ fastcall unsigned long __get_free_pages(unsigned int __nocast gfp_mask, unsigned EXPORT_SYMBOL(__get_free_pages); -fastcall unsigned long get_zeroed_page(unsigned int __nocast gfp_mask) +fastcall unsigned long get_zeroed_page(gfp_t gfp_mask) { struct page * page; diff --git a/mm/page_io.c b/mm/page_io.c index 2e605a19ce5..330e00d6db0 100644 --- a/mm/page_io.c +++ b/mm/page_io.c @@ -19,7 +19,7 @@ #include #include -static struct bio *get_swap_bio(unsigned int __nocast gfp_flags, pgoff_t index, +static struct bio *get_swap_bio(gfp_t gfp_flags, pgoff_t index, struct page *page, bio_end_io_t end_io) { struct bio *bio; diff --git a/mm/shmem.c b/mm/shmem.c index 1f7aeb210c7..ea064d89cda 100644 --- a/mm/shmem.c +++ b/mm/shmem.c @@ -921,8 +921,7 @@ shmem_swapin(struct shmem_inode_info *info,swp_entry_t entry,unsigned long idx) } static inline struct page * -shmem_alloc_page(unsigned int __nocast gfp,struct shmem_inode_info *info, - unsigned long idx) +shmem_alloc_page(gfp_t gfp,struct shmem_inode_info *info, unsigned long idx) { return alloc_page(gfp | __GFP_ZERO); } diff --git a/mm/slab.c b/mm/slab.c index 5cbbdfa6dd0..d05c678bceb 100644 --- a/mm/slab.c +++ b/mm/slab.c @@ -650,8 +650,7 @@ static inline struct array_cache *ac_data(kmem_cache_t *cachep) return cachep->array[smp_processor_id()]; } -static inline kmem_cache_t *__find_general_cachep(size_t size, - unsigned int __nocast gfpflags) +static inline kmem_cache_t *__find_general_cachep(size_t size, gfp_t gfpflags) { struct cache_sizes *csizep = malloc_sizes; @@ -675,8 +674,7 @@ static inline kmem_cache_t *__find_general_cachep(size_t size, return csizep->cs_cachep; } -kmem_cache_t *kmem_find_general_cachep(size_t size, - unsigned int __nocast gfpflags) +kmem_cache_t *kmem_find_general_cachep(size_t size, gfp_t gfpflags) { return __find_general_cachep(size, gfpflags); } @@ -1185,7 +1183,7 @@ __initcall(cpucache_init); * did not request dmaable memory, we might get it, but that * would be relatively rare and ignorable. */ -static void *kmem_getpages(kmem_cache_t *cachep, unsigned int __nocast flags, int nodeid) +static void *kmem_getpages(kmem_cache_t *cachep, gfp_t flags, int nodeid) { struct page *page; void *addr; @@ -2048,7 +2046,7 @@ EXPORT_SYMBOL(kmem_cache_destroy); /* Get the memory for a slab management obj. */ static struct slab* alloc_slabmgmt(kmem_cache_t *cachep, void *objp, - int colour_off, unsigned int __nocast local_flags) + int colour_off, gfp_t local_flags) { struct slab *slabp; @@ -2149,7 +2147,7 @@ static void set_slab_attr(kmem_cache_t *cachep, struct slab *slabp, void *objp) * Grow (by 1) the number of slabs within a cache. This is called by * kmem_cache_alloc() when there are no active objs left in a cache. */ -static int cache_grow(kmem_cache_t *cachep, unsigned int __nocast flags, int nodeid) +static int cache_grow(kmem_cache_t *cachep, gfp_t flags, int nodeid) { struct slab *slabp; void *objp; @@ -2356,7 +2354,7 @@ bad: #define check_slabp(x,y) do { } while(0) #endif -static void *cache_alloc_refill(kmem_cache_t *cachep, unsigned int __nocast flags) +static void *cache_alloc_refill(kmem_cache_t *cachep, gfp_t flags) { int batchcount; struct kmem_list3 *l3; @@ -2456,7 +2454,7 @@ alloc_done: } static inline void -cache_alloc_debugcheck_before(kmem_cache_t *cachep, unsigned int __nocast flags) +cache_alloc_debugcheck_before(kmem_cache_t *cachep, gfp_t flags) { might_sleep_if(flags & __GFP_WAIT); #if DEBUG @@ -2467,7 +2465,7 @@ cache_alloc_debugcheck_before(kmem_cache_t *cachep, unsigned int __nocast flags) #if DEBUG static void * cache_alloc_debugcheck_after(kmem_cache_t *cachep, - unsigned int __nocast flags, void *objp, void *caller) + gfp_t flags, void *objp, void *caller) { if (!objp) return objp; @@ -2510,7 +2508,7 @@ cache_alloc_debugcheck_after(kmem_cache_t *cachep, #define cache_alloc_debugcheck_after(a,b,objp,d) (objp) #endif -static inline void *____cache_alloc(kmem_cache_t *cachep, unsigned int __nocast flags) +static inline void *____cache_alloc(kmem_cache_t *cachep, gfp_t flags) { void* objp; struct array_cache *ac; @@ -2528,7 +2526,7 @@ static inline void *____cache_alloc(kmem_cache_t *cachep, unsigned int __nocast return objp; } -static inline void *__cache_alloc(kmem_cache_t *cachep, unsigned int __nocast flags) +static inline void *__cache_alloc(kmem_cache_t *cachep, gfp_t flags) { unsigned long save_flags; void* objp; @@ -2787,7 +2785,7 @@ static inline void __cache_free(kmem_cache_t *cachep, void *objp) * Allocate an object from this cache. The flags are only relevant * if the cache has no available objects. */ -void *kmem_cache_alloc(kmem_cache_t *cachep, unsigned int __nocast flags) +void *kmem_cache_alloc(kmem_cache_t *cachep, gfp_t flags) { return __cache_alloc(cachep, flags); } @@ -2848,7 +2846,7 @@ out: * New and improved: it will now make sure that the object gets * put on the correct node list so that there is no false sharing. */ -void *kmem_cache_alloc_node(kmem_cache_t *cachep, unsigned int __nocast flags, int nodeid) +void *kmem_cache_alloc_node(kmem_cache_t *cachep, gfp_t flags, int nodeid) { unsigned long save_flags; void *ptr; @@ -2875,7 +2873,7 @@ void *kmem_cache_alloc_node(kmem_cache_t *cachep, unsigned int __nocast flags, i } EXPORT_SYMBOL(kmem_cache_alloc_node); -void *kmalloc_node(size_t size, unsigned int __nocast flags, int node) +void *kmalloc_node(size_t size, gfp_t flags, int node) { kmem_cache_t *cachep; @@ -2908,7 +2906,7 @@ EXPORT_SYMBOL(kmalloc_node); * platforms. For example, on i386, it means that the memory must come * from the first 16MB. */ -void *__kmalloc(size_t size, unsigned int __nocast flags) +void *__kmalloc(size_t size, gfp_t flags) { kmem_cache_t *cachep; @@ -2997,7 +2995,7 @@ EXPORT_SYMBOL(kmem_cache_free); * @size: how many bytes of memory are required. * @flags: the type of memory to allocate. */ -void *kzalloc(size_t size, unsigned int __nocast flags) +void *kzalloc(size_t size, gfp_t flags) { void *ret = kmalloc(size, flags); if (ret) @@ -3603,7 +3601,7 @@ unsigned int ksize(const void *objp) * @s: the string to duplicate * @gfp: the GFP mask used in the kmalloc() call when allocating memory */ -char *kstrdup(const char *s, unsigned int __nocast gfp) +char *kstrdup(const char *s, gfp_t gfp) { size_t len; char *buf; diff --git a/mm/swap_state.c b/mm/swap_state.c index adbc2b426c2..132164f7d0a 100644 --- a/mm/swap_state.c +++ b/mm/swap_state.c @@ -68,7 +68,7 @@ void show_swap_cache_info(void) * but sets SwapCache flag and private instead of mapping and index. */ static int __add_to_swap_cache(struct page *page, swp_entry_t entry, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { int error; diff --git a/mm/vmalloc.c b/mm/vmalloc.c index 13c3d82968a..1150229b636 100644 --- a/mm/vmalloc.c +++ b/mm/vmalloc.c @@ -395,7 +395,7 @@ void *vmap(struct page **pages, unsigned int count, EXPORT_SYMBOL(vmap); -void *__vmalloc_area(struct vm_struct *area, unsigned int __nocast gfp_mask, pgprot_t prot) +void *__vmalloc_area(struct vm_struct *area, gfp_t gfp_mask, pgprot_t prot) { struct page **pages; unsigned int nr_pages, array_size, i; @@ -446,7 +446,7 @@ fail: * allocator with @gfp_mask flags. Map them into contiguous * kernel virtual space, using a pagetable protection of @prot. */ -void *__vmalloc(unsigned long size, unsigned int __nocast gfp_mask, pgprot_t prot) +void *__vmalloc(unsigned long size, gfp_t gfp_mask, pgprot_t prot) { struct vm_struct *area; diff --git a/net/atm/atm_misc.c b/net/atm/atm_misc.c index 71abc99ec81..223c7ad5bd0 100644 --- a/net/atm/atm_misc.c +++ b/net/atm/atm_misc.c @@ -25,7 +25,7 @@ int atm_charge(struct atm_vcc *vcc,int truesize) struct sk_buff *atm_alloc_charge(struct atm_vcc *vcc,int pdu_size, - unsigned int __nocast gfp_flags) + gfp_t gfp_flags) { struct sock *sk = sk_atm(vcc); int guess = atm_guess_pdu2truesize(pdu_size); diff --git a/net/bluetooth/l2cap.c b/net/bluetooth/l2cap.c index d3d6bc54721..59b2dd36baa 100644 --- a/net/bluetooth/l2cap.c +++ b/net/bluetooth/l2cap.c @@ -372,7 +372,7 @@ static struct proto l2cap_proto = { .obj_size = sizeof(struct l2cap_pinfo) }; -static struct sock *l2cap_sock_alloc(struct socket *sock, int proto, unsigned int __nocast prio) +static struct sock *l2cap_sock_alloc(struct socket *sock, int proto, gfp_t prio) { struct sock *sk; diff --git a/net/bluetooth/rfcomm/core.c b/net/bluetooth/rfcomm/core.c index 173f46e8cda..35adce6482b 100644 --- a/net/bluetooth/rfcomm/core.c +++ b/net/bluetooth/rfcomm/core.c @@ -229,7 +229,7 @@ static void rfcomm_dlc_clear_state(struct rfcomm_dlc *d) d->rx_credits = RFCOMM_DEFAULT_CREDITS; } -struct rfcomm_dlc *rfcomm_dlc_alloc(unsigned int __nocast prio) +struct rfcomm_dlc *rfcomm_dlc_alloc(gfp_t prio) { struct rfcomm_dlc *d = kmalloc(sizeof(*d), prio); if (!d) diff --git a/net/bluetooth/rfcomm/sock.c b/net/bluetooth/rfcomm/sock.c index f49e7e938bf..a2b30f0aedb 100644 --- a/net/bluetooth/rfcomm/sock.c +++ b/net/bluetooth/rfcomm/sock.c @@ -284,7 +284,7 @@ static struct proto rfcomm_proto = { .obj_size = sizeof(struct rfcomm_pinfo) }; -static struct sock *rfcomm_sock_alloc(struct socket *sock, int proto, unsigned int __nocast prio) +static struct sock *rfcomm_sock_alloc(struct socket *sock, int proto, gfp_t prio) { struct rfcomm_dlc *d; struct sock *sk; diff --git a/net/bluetooth/rfcomm/tty.c b/net/bluetooth/rfcomm/tty.c index 1bca860a610..158a9c46d86 100644 --- a/net/bluetooth/rfcomm/tty.c +++ b/net/bluetooth/rfcomm/tty.c @@ -286,7 +286,7 @@ static inline void rfcomm_set_owner_w(struct sk_buff *skb, struct rfcomm_dev *de skb->destructor = rfcomm_wfree; } -static struct sk_buff *rfcomm_wmalloc(struct rfcomm_dev *dev, unsigned long size, unsigned int __nocast priority) +static struct sk_buff *rfcomm_wmalloc(struct rfcomm_dev *dev, unsigned long size, gfp_t priority) { if (atomic_read(&dev->wmem_alloc) < rfcomm_room(dev->dlc)) { struct sk_buff *skb = alloc_skb(size, priority); diff --git a/net/bluetooth/sco.c b/net/bluetooth/sco.c index ce7ab7dfa0b..997e42df115 100644 --- a/net/bluetooth/sco.c +++ b/net/bluetooth/sco.c @@ -418,7 +418,7 @@ static struct proto sco_proto = { .obj_size = sizeof(struct sco_pinfo) }; -static struct sock *sco_sock_alloc(struct socket *sock, int proto, unsigned int __nocast prio) +static struct sock *sco_sock_alloc(struct socket *sock, int proto, gfp_t prio) { struct sock *sk; diff --git a/net/core/dev.c b/net/core/dev.c index 9066c874e27..a44eeef24ed 100644 --- a/net/core/dev.c +++ b/net/core/dev.c @@ -1132,7 +1132,7 @@ static inline int illegal_highdma(struct net_device *dev, struct sk_buff *skb) #endif /* Keep head the same: replace data */ -int __skb_linearize(struct sk_buff *skb, unsigned int __nocast gfp_mask) +int __skb_linearize(struct sk_buff *skb, gfp_t gfp_mask) { unsigned int size; u8 *data; diff --git a/net/core/skbuff.c b/net/core/skbuff.c index 0e9431b59fb..af9b1516e21 100644 --- a/net/core/skbuff.c +++ b/net/core/skbuff.c @@ -130,7 +130,7 @@ void skb_under_panic(struct sk_buff *skb, int sz, void *here) * Buffers may only be allocated from interrupts using a @gfp_mask of * %GFP_ATOMIC. */ -struct sk_buff *__alloc_skb(unsigned int size, unsigned int __nocast gfp_mask, +struct sk_buff *__alloc_skb(unsigned int size, gfp_t gfp_mask, int fclone) { struct sk_buff *skb; @@ -198,7 +198,7 @@ nodata: */ struct sk_buff *alloc_skb_from_cache(kmem_cache_t *cp, unsigned int size, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { struct sk_buff *skb; u8 *data; @@ -361,7 +361,7 @@ void __kfree_skb(struct sk_buff *skb) * %GFP_ATOMIC. */ -struct sk_buff *skb_clone(struct sk_buff *skb, unsigned int __nocast gfp_mask) +struct sk_buff *skb_clone(struct sk_buff *skb, gfp_t gfp_mask) { struct sk_buff *n; @@ -500,7 +500,7 @@ static void copy_skb_header(struct sk_buff *new, const struct sk_buff *old) * header is going to be modified. Use pskb_copy() instead. */ -struct sk_buff *skb_copy(const struct sk_buff *skb, unsigned int __nocast gfp_mask) +struct sk_buff *skb_copy(const struct sk_buff *skb, gfp_t gfp_mask) { int headerlen = skb->data - skb->head; /* @@ -539,7 +539,7 @@ struct sk_buff *skb_copy(const struct sk_buff *skb, unsigned int __nocast gfp_ma * The returned buffer has a reference count of 1. */ -struct sk_buff *pskb_copy(struct sk_buff *skb, unsigned int __nocast gfp_mask) +struct sk_buff *pskb_copy(struct sk_buff *skb, gfp_t gfp_mask) { /* * Allocate the copy buffer @@ -598,7 +598,7 @@ out: */ int pskb_expand_head(struct sk_buff *skb, int nhead, int ntail, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { int i; u8 *data; @@ -689,7 +689,7 @@ struct sk_buff *skb_realloc_headroom(struct sk_buff *skb, unsigned int headroom) */ struct sk_buff *skb_copy_expand(const struct sk_buff *skb, int newheadroom, int newtailroom, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { /* * Allocate the copy buffer diff --git a/net/core/sock.c b/net/core/sock.c index 928d2a1d6d8..1c52fe809ed 100644 --- a/net/core/sock.c +++ b/net/core/sock.c @@ -637,7 +637,7 @@ lenout: * @prot: struct proto associated with this new sock instance * @zero_it: if we should zero the newly allocated sock */ -struct sock *sk_alloc(int family, unsigned int __nocast priority, +struct sock *sk_alloc(int family, gfp_t priority, struct proto *prot, int zero_it) { struct sock *sk = NULL; @@ -704,7 +704,7 @@ void sk_free(struct sock *sk) module_put(owner); } -struct sock *sk_clone(const struct sock *sk, const unsigned int __nocast priority) +struct sock *sk_clone(const struct sock *sk, const gfp_t priority) { struct sock *newsk = sk_alloc(sk->sk_family, priority, sk->sk_prot, 0); @@ -845,7 +845,7 @@ unsigned long sock_i_ino(struct sock *sk) * Allocate a skb from the socket's send buffer. */ struct sk_buff *sock_wmalloc(struct sock *sk, unsigned long size, int force, - unsigned int __nocast priority) + gfp_t priority) { if (force || atomic_read(&sk->sk_wmem_alloc) < sk->sk_sndbuf) { struct sk_buff * skb = alloc_skb(size, priority); @@ -861,7 +861,7 @@ struct sk_buff *sock_wmalloc(struct sock *sk, unsigned long size, int force, * Allocate a skb from the socket's receive buffer. */ struct sk_buff *sock_rmalloc(struct sock *sk, unsigned long size, int force, - unsigned int __nocast priority) + gfp_t priority) { if (force || atomic_read(&sk->sk_rmem_alloc) < sk->sk_rcvbuf) { struct sk_buff *skb = alloc_skb(size, priority); @@ -876,7 +876,7 @@ struct sk_buff *sock_rmalloc(struct sock *sk, unsigned long size, int force, /* * Allocate a memory block from the socket's option memory buffer. */ -void *sock_kmalloc(struct sock *sk, int size, unsigned int __nocast priority) +void *sock_kmalloc(struct sock *sk, int size, gfp_t priority) { if ((unsigned)size <= sysctl_optmem_max && atomic_read(&sk->sk_omem_alloc) + size < sysctl_optmem_max) { diff --git a/net/dccp/ackvec.c b/net/dccp/ackvec.c index 6530283eafc..c9a62cca22f 100644 --- a/net/dccp/ackvec.c +++ b/net/dccp/ackvec.c @@ -91,7 +91,7 @@ int dccp_insert_option_ackvec(struct sock *sk, struct sk_buff *skb) } struct dccp_ackvec *dccp_ackvec_alloc(const unsigned int len, - const unsigned int __nocast priority) + const gfp_t priority) { struct dccp_ackvec *av = kmalloc(sizeof(*av) + len, priority); diff --git a/net/dccp/ackvec.h b/net/dccp/ackvec.h index 8ca51c9191f..d0fd6c60c57 100644 --- a/net/dccp/ackvec.h +++ b/net/dccp/ackvec.h @@ -74,7 +74,7 @@ struct sk_buff; #ifdef CONFIG_IP_DCCP_ACKVEC extern struct dccp_ackvec *dccp_ackvec_alloc(unsigned int len, - const unsigned int __nocast priority); + const gfp_t priority); extern void dccp_ackvec_free(struct dccp_ackvec *av); extern int dccp_ackvec_add(struct dccp_ackvec *av, const struct sock *sk, @@ -93,7 +93,7 @@ static inline int dccp_ackvec_pending(const struct dccp_ackvec *av) } #else /* CONFIG_IP_DCCP_ACKVEC */ static inline struct dccp_ackvec *dccp_ackvec_alloc(unsigned int len, - const unsigned int __nocast priority) + const gfp_t priority) { return NULL; } diff --git a/net/dccp/ccids/lib/loss_interval.h b/net/dccp/ccids/lib/loss_interval.h index 13ad47ba142..417d9d82df3 100644 --- a/net/dccp/ccids/lib/loss_interval.h +++ b/net/dccp/ccids/lib/loss_interval.h @@ -36,7 +36,7 @@ struct dccp_li_hist_entry { static inline struct dccp_li_hist_entry * dccp_li_hist_entry_new(struct dccp_li_hist *hist, - const unsigned int __nocast prio) + const gfp_t prio) { return kmem_cache_alloc(hist->dccplih_slab, prio); } diff --git a/net/dccp/ccids/lib/packet_history.h b/net/dccp/ccids/lib/packet_history.h index b375ebdb7dc..122e96737ff 100644 --- a/net/dccp/ccids/lib/packet_history.h +++ b/net/dccp/ccids/lib/packet_history.h @@ -86,7 +86,7 @@ extern struct dccp_rx_hist_entry * static inline struct dccp_tx_hist_entry * dccp_tx_hist_entry_new(struct dccp_tx_hist *hist, - const unsigned int __nocast prio) + const gfp_t prio) { struct dccp_tx_hist_entry *entry = kmem_cache_alloc(hist->dccptxh_slab, prio); @@ -137,7 +137,7 @@ static inline struct dccp_rx_hist_entry * const struct sock *sk, const u32 ndp, const struct sk_buff *skb, - const unsigned int __nocast prio) + const gfp_t prio) { struct dccp_rx_hist_entry *entry = kmem_cache_alloc(hist->dccprxh_slab, prio); diff --git a/net/decnet/af_decnet.c b/net/decnet/af_decnet.c index 34d4128d56d..1186dc44cdf 100644 --- a/net/decnet/af_decnet.c +++ b/net/decnet/af_decnet.c @@ -452,8 +452,7 @@ static struct proto dn_proto = { .obj_size = sizeof(struct dn_sock), }; -static struct sock *dn_alloc_sock(struct socket *sock, - unsigned int __nocast gfp) +static struct sock *dn_alloc_sock(struct socket *sock, gfp_t gfp) { struct dn_scp *scp; struct sock *sk = sk_alloc(PF_DECnet, gfp, &dn_proto, 1); @@ -805,8 +804,7 @@ static int dn_auto_bind(struct socket *sock) return rv; } -static int dn_confirm_accept(struct sock *sk, long *timeo, - unsigned int __nocast allocation) +static int dn_confirm_accept(struct sock *sk, long *timeo, gfp_t allocation) { struct dn_scp *scp = DN_SK(sk); DEFINE_WAIT(wait); diff --git a/net/decnet/dn_nsp_out.c b/net/decnet/dn_nsp_out.c index cd08244aa10..c96c767b1f7 100644 --- a/net/decnet/dn_nsp_out.c +++ b/net/decnet/dn_nsp_out.c @@ -117,8 +117,7 @@ try_again: * The eventual aim is for each socket to have a cached header size * for its outgoing packets, and to set hdr from this when sk != NULL. */ -struct sk_buff *dn_alloc_skb(struct sock *sk, int size, - unsigned int __nocast pri) +struct sk_buff *dn_alloc_skb(struct sock *sk, int size, gfp_t pri) { struct sk_buff *skb; int hdr = 64; @@ -212,7 +211,7 @@ static void dn_nsp_rtt(struct sock *sk, long rtt) * Returns: The number of times the packet has been sent previously */ static inline unsigned dn_nsp_clone_and_send(struct sk_buff *skb, - unsigned int __nocast gfp) + gfp_t gfp) { struct dn_skb_cb *cb = DN_SKB_CB(skb); struct sk_buff *skb2; @@ -353,7 +352,7 @@ static unsigned short *dn_nsp_mk_data_header(struct sock *sk, struct sk_buff *sk } void dn_nsp_queue_xmit(struct sock *sk, struct sk_buff *skb, - unsigned int __nocast gfp, int oth) + gfp_t gfp, int oth) { struct dn_scp *scp = DN_SK(sk); struct dn_skb_cb *cb = DN_SKB_CB(skb); @@ -520,7 +519,7 @@ static int dn_nsp_retrans_conn_conf(struct sock *sk) return 0; } -void dn_send_conn_conf(struct sock *sk, unsigned int __nocast gfp) +void dn_send_conn_conf(struct sock *sk, gfp_t gfp) { struct dn_scp *scp = DN_SK(sk); struct sk_buff *skb = NULL; @@ -552,7 +551,7 @@ void dn_send_conn_conf(struct sock *sk, unsigned int __nocast gfp) static __inline__ void dn_nsp_do_disc(struct sock *sk, unsigned char msgflg, - unsigned short reason, unsigned int __nocast gfp, + unsigned short reason, gfp_t gfp, struct dst_entry *dst, int ddl, unsigned char *dd, __u16 rem, __u16 loc) { @@ -595,7 +594,7 @@ static __inline__ void dn_nsp_do_disc(struct sock *sk, unsigned char msgflg, void dn_nsp_send_disc(struct sock *sk, unsigned char msgflg, - unsigned short reason, unsigned int __nocast gfp) + unsigned short reason, gfp_t gfp) { struct dn_scp *scp = DN_SK(sk); int ddl = 0; @@ -616,7 +615,7 @@ void dn_nsp_return_disc(struct sk_buff *skb, unsigned char msgflg, { struct dn_skb_cb *cb = DN_SKB_CB(skb); int ddl = 0; - unsigned int __nocast gfp = GFP_ATOMIC; + gfp_t gfp = GFP_ATOMIC; dn_nsp_do_disc(NULL, msgflg, reason, gfp, skb->dst, ddl, NULL, cb->src_port, cb->dst_port); @@ -628,7 +627,7 @@ void dn_nsp_send_link(struct sock *sk, unsigned char lsflags, char fcval) struct dn_scp *scp = DN_SK(sk); struct sk_buff *skb; unsigned char *ptr; - unsigned int __nocast gfp = GFP_ATOMIC; + gfp_t gfp = GFP_ATOMIC; if ((skb = dn_alloc_skb(sk, DN_MAX_NSP_DATA_HEADER + 2, gfp)) == NULL) return; @@ -663,8 +662,7 @@ void dn_nsp_send_conninit(struct sock *sk, unsigned char msgflg) unsigned char menuver; struct dn_skb_cb *cb; unsigned char type = 1; - unsigned int __nocast allocation = - (msgflg == NSP_CI) ? sk->sk_allocation : GFP_ATOMIC; + gfp_t allocation = (msgflg == NSP_CI) ? sk->sk_allocation : GFP_ATOMIC; struct sk_buff *skb = dn_alloc_skb(sk, 200, allocation); if (!skb) diff --git a/net/ieee80211/ieee80211_tx.c b/net/ieee80211/ieee80211_tx.c index ecdf9f7a538..eed07bbbe6b 100644 --- a/net/ieee80211/ieee80211_tx.c +++ b/net/ieee80211/ieee80211_tx.c @@ -207,7 +207,7 @@ void ieee80211_txb_free(struct ieee80211_txb *txb) } static struct ieee80211_txb *ieee80211_alloc_txb(int nr_frags, int txb_size, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { struct ieee80211_txb *txb; int i; diff --git a/net/ipv4/inet_connection_sock.c b/net/ipv4/inet_connection_sock.c index fe3c6d3d0c9..94468a76c5b 100644 --- a/net/ipv4/inet_connection_sock.c +++ b/net/ipv4/inet_connection_sock.c @@ -494,7 +494,7 @@ void inet_csk_reqsk_queue_prune(struct sock *parent, EXPORT_SYMBOL_GPL(inet_csk_reqsk_queue_prune); struct sock *inet_csk_clone(struct sock *sk, const struct request_sock *req, - const unsigned int __nocast priority) + const gfp_t priority) { struct sock *newsk = sk_clone(sk, priority); diff --git a/net/ipv4/ipvs/ip_vs_app.c b/net/ipv4/ipvs/ip_vs_app.c index b942ff3c886..fc6f95aaa96 100644 --- a/net/ipv4/ipvs/ip_vs_app.c +++ b/net/ipv4/ipvs/ip_vs_app.c @@ -604,7 +604,7 @@ static struct file_operations ip_vs_app_fops = { /* * Replace a segment of data with a new segment */ -int ip_vs_skb_replace(struct sk_buff *skb, unsigned int __nocast pri, +int ip_vs_skb_replace(struct sk_buff *skb, gfp_t pri, char *o_buf, int o_len, char *n_buf, int n_len) { struct iphdr *iph; diff --git a/net/ipv4/tcp_output.c b/net/ipv4/tcp_output.c index c5b911f9b66..8225e425725 100644 --- a/net/ipv4/tcp_output.c +++ b/net/ipv4/tcp_output.c @@ -1610,7 +1610,7 @@ void tcp_send_fin(struct sock *sk) * was unread data in the receive queue. This behavior is recommended * by draft-ietf-tcpimpl-prob-03.txt section 3.10. -DaveM */ -void tcp_send_active_reset(struct sock *sk, unsigned int __nocast priority) +void tcp_send_active_reset(struct sock *sk, gfp_t priority) { struct tcp_sock *tp = tcp_sk(sk); struct sk_buff *skb; diff --git a/net/key/af_key.c b/net/key/af_key.c index bbf0f69181b..39031684b65 100644 --- a/net/key/af_key.c +++ b/net/key/af_key.c @@ -185,7 +185,7 @@ static int pfkey_release(struct socket *sock) } static int pfkey_broadcast_one(struct sk_buff *skb, struct sk_buff **skb2, - unsigned int __nocast allocation, struct sock *sk) + gfp_t allocation, struct sock *sk) { int err = -ENOBUFS; @@ -217,7 +217,7 @@ static int pfkey_broadcast_one(struct sk_buff *skb, struct sk_buff **skb2, #define BROADCAST_ONE 1 #define BROADCAST_REGISTERED 2 #define BROADCAST_PROMISC_ONLY 4 -static int pfkey_broadcast(struct sk_buff *skb, unsigned int __nocast allocation, +static int pfkey_broadcast(struct sk_buff *skb, gfp_t allocation, int broadcast_flags, struct sock *one_sk) { struct sock *sk; @@ -1417,7 +1417,7 @@ static int pfkey_get(struct sock *sk, struct sk_buff *skb, struct sadb_msg *hdr, } static struct sk_buff *compose_sadb_supported(struct sadb_msg *orig, - unsigned int __nocast allocation) + gfp_t allocation) { struct sk_buff *skb; struct sadb_msg *hdr; diff --git a/net/llc/llc_conn.c b/net/llc/llc_conn.c index 042b24a8ca4..c761c15da42 100644 --- a/net/llc/llc_conn.c +++ b/net/llc/llc_conn.c @@ -867,8 +867,7 @@ static void llc_sk_init(struct sock* sk) * Allocates a LLC sock and initializes it. Returns the new LLC sock * or %NULL if there's no memory available for one */ -struct sock *llc_sk_alloc(int family, unsigned int __nocast priority, - struct proto *prot) +struct sock *llc_sk_alloc(int family, gfp_t priority, struct proto *prot) { struct sock *sk = sk_alloc(family, priority, prot, 1); diff --git a/net/netfilter/nfnetlink.c b/net/netfilter/nfnetlink.c index 34d671974a4..1caaca06f69 100644 --- a/net/netfilter/nfnetlink.c +++ b/net/netfilter/nfnetlink.c @@ -195,8 +195,7 @@ nfnetlink_check_attributes(struct nfnetlink_subsystem *subsys, int nfnetlink_send(struct sk_buff *skb, u32 pid, unsigned group, int echo) { - unsigned int __nocast allocation = - in_interrupt() ? GFP_ATOMIC : GFP_KERNEL; + gfp_t allocation = in_interrupt() ? GFP_ATOMIC : GFP_KERNEL; int err = 0; NETLINK_CB(skb).dst_group = group; diff --git a/net/netlink/af_netlink.c b/net/netlink/af_netlink.c index a64e1d5ce3c..678c3f2c0d0 100644 --- a/net/netlink/af_netlink.c +++ b/net/netlink/af_netlink.c @@ -758,7 +758,7 @@ void netlink_detachskb(struct sock *sk, struct sk_buff *skb) } static inline struct sk_buff *netlink_trim(struct sk_buff *skb, - unsigned int __nocast allocation) + gfp_t allocation) { int delta; @@ -880,7 +880,7 @@ out: } int netlink_broadcast(struct sock *ssk, struct sk_buff *skb, u32 pid, - u32 group, unsigned int __nocast allocation) + u32 group, gfp_t allocation) { struct netlink_broadcast_data info; struct hlist_node *node; diff --git a/net/rxrpc/call.c b/net/rxrpc/call.c index 86f77705263..c4aeb7d4026 100644 --- a/net/rxrpc/call.c +++ b/net/rxrpc/call.c @@ -1923,7 +1923,7 @@ int rxrpc_call_write_data(struct rxrpc_call *call, size_t sioc, struct kvec *siov, u8 rxhdr_flags, - unsigned int __nocast alloc_flags, + gfp_t alloc_flags, int dup_data, size_t *size_sent) { diff --git a/net/rxrpc/connection.c b/net/rxrpc/connection.c index be4b2be5895..2ba14a75dbb 100644 --- a/net/rxrpc/connection.c +++ b/net/rxrpc/connection.c @@ -522,7 +522,7 @@ int rxrpc_conn_newmsg(struct rxrpc_connection *conn, uint8_t type, int dcount, struct kvec diov[], - unsigned int __nocast alloc_flags, + gfp_t alloc_flags, struct rxrpc_message **_msg) { struct rxrpc_message *msg; diff --git a/net/sctp/associola.c b/net/sctp/associola.c index 5b24ae0650d..12b0f582a66 100644 --- a/net/sctp/associola.c +++ b/net/sctp/associola.c @@ -71,7 +71,7 @@ static struct sctp_association *sctp_association_init(struct sctp_association *a const struct sctp_endpoint *ep, const struct sock *sk, sctp_scope_t scope, - unsigned int __nocast gfp) + gfp_t gfp) { struct sctp_sock *sp; int i; @@ -273,7 +273,7 @@ fail_init: struct sctp_association *sctp_association_new(const struct sctp_endpoint *ep, const struct sock *sk, sctp_scope_t scope, - unsigned int __nocast gfp) + gfp_t gfp) { struct sctp_association *asoc; @@ -479,7 +479,7 @@ void sctp_assoc_rm_peer(struct sctp_association *asoc, /* Add a transport address to an association. */ struct sctp_transport *sctp_assoc_add_peer(struct sctp_association *asoc, const union sctp_addr *addr, - const unsigned int __nocast gfp, + const gfp_t gfp, const int peer_state) { struct sctp_transport *peer; @@ -1231,7 +1231,7 @@ void sctp_assoc_rwnd_decrease(struct sctp_association *asoc, unsigned len) * local endpoint and the remote peer. */ int sctp_assoc_set_bind_addr_from_ep(struct sctp_association *asoc, - unsigned int __nocast gfp) + gfp_t gfp) { sctp_scope_t scope; int flags; @@ -1254,7 +1254,7 @@ int sctp_assoc_set_bind_addr_from_ep(struct sctp_association *asoc, /* Build the association's bind address list from the cookie. */ int sctp_assoc_set_bind_addr_from_cookie(struct sctp_association *asoc, struct sctp_cookie *cookie, - unsigned int __nocast gfp) + gfp_t gfp) { int var_size2 = ntohs(cookie->peer_init->chunk_hdr.length); int var_size3 = cookie->raw_addr_list_len; diff --git a/net/sctp/bind_addr.c b/net/sctp/bind_addr.c index f71549710f2..2b962627f63 100644 --- a/net/sctp/bind_addr.c +++ b/net/sctp/bind_addr.c @@ -53,7 +53,7 @@ /* Forward declarations for internal helpers. */ static int sctp_copy_one_addr(struct sctp_bind_addr *, union sctp_addr *, - sctp_scope_t scope, unsigned int __nocast gfp, + sctp_scope_t scope, gfp_t gfp, int flags); static void sctp_bind_addr_clean(struct sctp_bind_addr *); @@ -64,7 +64,7 @@ static void sctp_bind_addr_clean(struct sctp_bind_addr *); */ int sctp_bind_addr_copy(struct sctp_bind_addr *dest, const struct sctp_bind_addr *src, - sctp_scope_t scope, unsigned int __nocast gfp, + sctp_scope_t scope, gfp_t gfp, int flags) { struct sctp_sockaddr_entry *addr; @@ -146,7 +146,7 @@ void sctp_bind_addr_free(struct sctp_bind_addr *bp) /* Add an address to the bind address list in the SCTP_bind_addr structure. */ int sctp_add_bind_addr(struct sctp_bind_addr *bp, union sctp_addr *new, - unsigned int __nocast gfp) + gfp_t gfp) { struct sctp_sockaddr_entry *addr; @@ -200,7 +200,7 @@ int sctp_del_bind_addr(struct sctp_bind_addr *bp, union sctp_addr *del_addr) */ union sctp_params sctp_bind_addrs_to_raw(const struct sctp_bind_addr *bp, int *addrs_len, - unsigned int __nocast gfp) + gfp_t gfp) { union sctp_params addrparms; union sctp_params retval; @@ -252,7 +252,7 @@ end_raw: * address parameters). */ int sctp_raw_to_bind_addrs(struct sctp_bind_addr *bp, __u8 *raw_addr_list, - int addrs_len, __u16 port, unsigned int __nocast gfp) + int addrs_len, __u16 port, gfp_t gfp) { union sctp_addr_param *rawaddr; struct sctp_paramhdr *param; @@ -350,7 +350,7 @@ union sctp_addr *sctp_find_unmatch_addr(struct sctp_bind_addr *bp, /* Copy out addresses from the global local address list. */ static int sctp_copy_one_addr(struct sctp_bind_addr *dest, union sctp_addr *addr, - sctp_scope_t scope, unsigned int __nocast gfp, + sctp_scope_t scope, gfp_t gfp, int flags) { int error = 0; diff --git a/net/sctp/chunk.c b/net/sctp/chunk.c index 61da2937e64..83ef411772f 100644 --- a/net/sctp/chunk.c +++ b/net/sctp/chunk.c @@ -62,7 +62,7 @@ static void sctp_datamsg_init(struct sctp_datamsg *msg) } /* Allocate and initialize datamsg. */ -SCTP_STATIC struct sctp_datamsg *sctp_datamsg_new(unsigned int __nocast gfp) +SCTP_STATIC struct sctp_datamsg *sctp_datamsg_new(gfp_t gfp) { struct sctp_datamsg *msg; msg = kmalloc(sizeof(struct sctp_datamsg), gfp); diff --git a/net/sctp/endpointola.c b/net/sctp/endpointola.c index e22ccd65596..96984f7a2d6 100644 --- a/net/sctp/endpointola.c +++ b/net/sctp/endpointola.c @@ -68,7 +68,7 @@ static void sctp_endpoint_bh_rcv(struct sctp_endpoint *ep); */ static struct sctp_endpoint *sctp_endpoint_init(struct sctp_endpoint *ep, struct sock *sk, - unsigned int __nocast gfp) + gfp_t gfp) { struct sctp_sock *sp = sctp_sk(sk); memset(ep, 0, sizeof(struct sctp_endpoint)); @@ -138,8 +138,7 @@ static struct sctp_endpoint *sctp_endpoint_init(struct sctp_endpoint *ep, /* Create a sctp_endpoint with all that boring stuff initialized. * Returns NULL if there isn't enough memory. */ -struct sctp_endpoint *sctp_endpoint_new(struct sock *sk, - unsigned int __nocast gfp) +struct sctp_endpoint *sctp_endpoint_new(struct sock *sk, gfp_t gfp) { struct sctp_endpoint *ep; diff --git a/net/sctp/protocol.c b/net/sctp/protocol.c index f01d1c9002a..26de4d3e1bd 100644 --- a/net/sctp/protocol.c +++ b/net/sctp/protocol.c @@ -219,7 +219,7 @@ static void sctp_free_local_addr_list(void) /* Copy the local addresses which are valid for 'scope' into 'bp'. */ int sctp_copy_local_addr_list(struct sctp_bind_addr *bp, sctp_scope_t scope, - unsigned int __nocast gfp, int copy_flags) + gfp_t gfp, int copy_flags) { struct sctp_sockaddr_entry *addr; int error = 0; diff --git a/net/sctp/sm_make_chunk.c b/net/sctp/sm_make_chunk.c index 3868a8d70cc..10e82ec2ebd 100644 --- a/net/sctp/sm_make_chunk.c +++ b/net/sctp/sm_make_chunk.c @@ -78,7 +78,7 @@ static sctp_cookie_param_t *sctp_pack_cookie(const struct sctp_endpoint *ep, static int sctp_process_param(struct sctp_association *asoc, union sctp_params param, const union sctp_addr *peer_addr, - unsigned int __nocast gfp); + gfp_t gfp); /* What was the inbound interface for this chunk? */ int sctp_chunk_iif(const struct sctp_chunk *chunk) @@ -174,7 +174,7 @@ void sctp_init_cause(struct sctp_chunk *chunk, __u16 cause_code, */ struct sctp_chunk *sctp_make_init(const struct sctp_association *asoc, const struct sctp_bind_addr *bp, - unsigned int __nocast gfp, int vparam_len) + gfp_t gfp, int vparam_len) { sctp_inithdr_t init; union sctp_params addrs; @@ -261,7 +261,7 @@ nodata: struct sctp_chunk *sctp_make_init_ack(const struct sctp_association *asoc, const struct sctp_chunk *chunk, - unsigned int __nocast gfp, int unkparam_len) + gfp_t gfp, int unkparam_len) { sctp_inithdr_t initack; struct sctp_chunk *retval; @@ -1234,7 +1234,7 @@ void sctp_chunk_assign_tsn(struct sctp_chunk *chunk) /* Create a CLOSED association to use with an incoming packet. */ struct sctp_association *sctp_make_temp_asoc(const struct sctp_endpoint *ep, struct sctp_chunk *chunk, - unsigned int __nocast gfp) + gfp_t gfp) { struct sctp_association *asoc; struct sk_buff *skb; @@ -1349,7 +1349,7 @@ nodata: struct sctp_association *sctp_unpack_cookie( const struct sctp_endpoint *ep, const struct sctp_association *asoc, - struct sctp_chunk *chunk, unsigned int __nocast gfp, + struct sctp_chunk *chunk, gfp_t gfp, int *error, struct sctp_chunk **errp) { struct sctp_association *retval = NULL; @@ -1814,7 +1814,7 @@ int sctp_verify_init(const struct sctp_association *asoc, */ int sctp_process_init(struct sctp_association *asoc, sctp_cid_t cid, const union sctp_addr *peer_addr, - sctp_init_chunk_t *peer_init, unsigned int __nocast gfp) + sctp_init_chunk_t *peer_init, gfp_t gfp) { union sctp_params param; struct sctp_transport *transport; @@ -1985,7 +1985,7 @@ nomem: static int sctp_process_param(struct sctp_association *asoc, union sctp_params param, const union sctp_addr *peer_addr, - unsigned int __nocast gfp) + gfp_t gfp) { union sctp_addr addr; int i; diff --git a/net/sctp/sm_sideeffect.c b/net/sctp/sm_sideeffect.c index 39c970b5b19..f84173ea8ec 100644 --- a/net/sctp/sm_sideeffect.c +++ b/net/sctp/sm_sideeffect.c @@ -63,7 +63,7 @@ static int sctp_cmd_interpreter(sctp_event_t event_type, void *event_arg, sctp_disposition_t status, sctp_cmd_seq_t *commands, - unsigned int __nocast gfp); + gfp_t gfp); static int sctp_side_effects(sctp_event_t event_type, sctp_subtype_t subtype, sctp_state_t state, struct sctp_endpoint *ep, @@ -71,7 +71,7 @@ static int sctp_side_effects(sctp_event_t event_type, sctp_subtype_t subtype, void *event_arg, sctp_disposition_t status, sctp_cmd_seq_t *commands, - unsigned int __nocast gfp); + gfp_t gfp); /******************************************************************** * Helper functions @@ -498,7 +498,7 @@ static int sctp_cmd_process_init(sctp_cmd_seq_t *commands, struct sctp_association *asoc, struct sctp_chunk *chunk, sctp_init_chunk_t *peer_init, - unsigned int __nocast gfp) + gfp_t gfp) { int error; @@ -853,7 +853,7 @@ int sctp_do_sm(sctp_event_t event_type, sctp_subtype_t subtype, struct sctp_endpoint *ep, struct sctp_association *asoc, void *event_arg, - unsigned int __nocast gfp) + gfp_t gfp) { sctp_cmd_seq_t commands; const sctp_sm_table_entry_t *state_fn; @@ -898,7 +898,7 @@ static int sctp_side_effects(sctp_event_t event_type, sctp_subtype_t subtype, void *event_arg, sctp_disposition_t status, sctp_cmd_seq_t *commands, - unsigned int __nocast gfp) + gfp_t gfp) { int error; @@ -986,7 +986,7 @@ static int sctp_cmd_interpreter(sctp_event_t event_type, void *event_arg, sctp_disposition_t status, sctp_cmd_seq_t *commands, - unsigned int __nocast gfp) + gfp_t gfp) { int error = 0; int force; diff --git a/net/sctp/ssnmap.c b/net/sctp/ssnmap.c index 25037daf3fa..cbe2513d282 100644 --- a/net/sctp/ssnmap.c +++ b/net/sctp/ssnmap.c @@ -58,7 +58,7 @@ static inline size_t sctp_ssnmap_size(__u16 in, __u16 out) * Allocate room to store at least 'len' contiguous TSNs. */ struct sctp_ssnmap *sctp_ssnmap_new(__u16 in, __u16 out, - unsigned int __nocast gfp) + gfp_t gfp) { struct sctp_ssnmap *retval; int size; diff --git a/net/sctp/transport.c b/net/sctp/transport.c index d2f04ebe508..6bc27200e6c 100644 --- a/net/sctp/transport.c +++ b/net/sctp/transport.c @@ -57,7 +57,7 @@ /* Initialize a new transport from provided memory. */ static struct sctp_transport *sctp_transport_init(struct sctp_transport *peer, const union sctp_addr *addr, - unsigned int __nocast gfp) + gfp_t gfp) { /* Copy in the address. */ peer->ipaddr = *addr; @@ -122,7 +122,7 @@ static struct sctp_transport *sctp_transport_init(struct sctp_transport *peer, /* Allocate and initialize a new transport. */ struct sctp_transport *sctp_transport_new(const union sctp_addr *addr, - unsigned int __nocast gfp) + gfp_t gfp) { struct sctp_transport *transport; diff --git a/net/sctp/ulpevent.c b/net/sctp/ulpevent.c index 0abd5101107..057e7fac3af 100644 --- a/net/sctp/ulpevent.c +++ b/net/sctp/ulpevent.c @@ -74,7 +74,7 @@ SCTP_STATIC void sctp_ulpevent_init(struct sctp_ulpevent *event, int msg_flags) /* Create a new sctp_ulpevent. */ SCTP_STATIC struct sctp_ulpevent *sctp_ulpevent_new(int size, int msg_flags, - unsigned int __nocast gfp) + gfp_t gfp) { struct sctp_ulpevent *event; struct sk_buff *skb; @@ -136,7 +136,7 @@ static inline void sctp_ulpevent_release_owner(struct sctp_ulpevent *event) struct sctp_ulpevent *sctp_ulpevent_make_assoc_change( const struct sctp_association *asoc, __u16 flags, __u16 state, __u16 error, __u16 outbound, - __u16 inbound, unsigned int __nocast gfp) + __u16 inbound, gfp_t gfp) { struct sctp_ulpevent *event; struct sctp_assoc_change *sac; @@ -237,7 +237,7 @@ fail: struct sctp_ulpevent *sctp_ulpevent_make_peer_addr_change( const struct sctp_association *asoc, const struct sockaddr_storage *aaddr, - int flags, int state, int error, unsigned int __nocast gfp) + int flags, int state, int error, gfp_t gfp) { struct sctp_ulpevent *event; struct sctp_paddr_change *spc; @@ -350,7 +350,7 @@ fail: */ struct sctp_ulpevent *sctp_ulpevent_make_remote_error( const struct sctp_association *asoc, struct sctp_chunk *chunk, - __u16 flags, unsigned int __nocast gfp) + __u16 flags, gfp_t gfp) { struct sctp_ulpevent *event; struct sctp_remote_error *sre; @@ -448,7 +448,7 @@ fail: */ struct sctp_ulpevent *sctp_ulpevent_make_send_failed( const struct sctp_association *asoc, struct sctp_chunk *chunk, - __u16 flags, __u32 error, unsigned int __nocast gfp) + __u16 flags, __u32 error, gfp_t gfp) { struct sctp_ulpevent *event; struct sctp_send_failed *ssf; @@ -557,7 +557,7 @@ fail: */ struct sctp_ulpevent *sctp_ulpevent_make_shutdown_event( const struct sctp_association *asoc, - __u16 flags, unsigned int __nocast gfp) + __u16 flags, gfp_t gfp) { struct sctp_ulpevent *event; struct sctp_shutdown_event *sse; @@ -620,7 +620,7 @@ fail: * 5.3.1.6 SCTP_ADAPTION_INDICATION */ struct sctp_ulpevent *sctp_ulpevent_make_adaption_indication( - const struct sctp_association *asoc, unsigned int __nocast gfp) + const struct sctp_association *asoc, gfp_t gfp) { struct sctp_ulpevent *event; struct sctp_adaption_event *sai; @@ -657,7 +657,7 @@ fail: */ struct sctp_ulpevent *sctp_ulpevent_make_rcvmsg(struct sctp_association *asoc, struct sctp_chunk *chunk, - unsigned int __nocast gfp) + gfp_t gfp) { struct sctp_ulpevent *event = NULL; struct sk_buff *skb; @@ -719,7 +719,7 @@ fail: */ struct sctp_ulpevent *sctp_ulpevent_make_pdapi( const struct sctp_association *asoc, __u32 indication, - unsigned int __nocast gfp) + gfp_t gfp) { struct sctp_ulpevent *event; struct sctp_pdapi_event *pd; diff --git a/net/sctp/ulpqueue.c b/net/sctp/ulpqueue.c index ec2c857eae7..2080b2d28c9 100644 --- a/net/sctp/ulpqueue.c +++ b/net/sctp/ulpqueue.c @@ -100,7 +100,7 @@ void sctp_ulpq_free(struct sctp_ulpq *ulpq) /* Process an incoming DATA chunk. */ int sctp_ulpq_tail_data(struct sctp_ulpq *ulpq, struct sctp_chunk *chunk, - unsigned int __nocast gfp) + gfp_t gfp) { struct sk_buff_head temp; sctp_data_chunk_t *hdr; @@ -792,7 +792,7 @@ static __u16 sctp_ulpq_renege_frags(struct sctp_ulpq *ulpq, __u16 needed) /* Partial deliver the first message as there is pressure on rwnd. */ void sctp_ulpq_partial_delivery(struct sctp_ulpq *ulpq, struct sctp_chunk *chunk, - unsigned int __nocast gfp) + gfp_t gfp) { struct sctp_ulpevent *event; struct sctp_association *asoc; @@ -816,7 +816,7 @@ void sctp_ulpq_partial_delivery(struct sctp_ulpq *ulpq, /* Renege some packets to make room for an incoming chunk. */ void sctp_ulpq_renege(struct sctp_ulpq *ulpq, struct sctp_chunk *chunk, - unsigned int __nocast gfp) + gfp_t gfp) { struct sctp_association *asoc; __u16 needed, freed; @@ -855,7 +855,7 @@ void sctp_ulpq_renege(struct sctp_ulpq *ulpq, struct sctp_chunk *chunk, /* Notify the application if an association is aborted and in * partial delivery mode. Send up any pending received messages. */ -void sctp_ulpq_abort_pd(struct sctp_ulpq *ulpq, unsigned int __nocast gfp) +void sctp_ulpq_abort_pd(struct sctp_ulpq *ulpq, gfp_t gfp) { struct sctp_ulpevent *ev = NULL; struct sock *sk; diff --git a/net/sunrpc/sched.c b/net/sunrpc/sched.c index ade730eaf40..54e60a65750 100644 --- a/net/sunrpc/sched.c +++ b/net/sunrpc/sched.c @@ -719,7 +719,7 @@ static void rpc_async_schedule(void *arg) void * rpc_malloc(struct rpc_task *task, size_t size) { - unsigned int __nocast gfp; + gfp_t gfp; if (task->tk_flags & RPC_TASK_SWAPPER) gfp = GFP_ATOMIC; diff --git a/net/xfrm/xfrm_policy.c b/net/xfrm/xfrm_policy.c index 061b44cc245..cbb0ba34a60 100644 --- a/net/xfrm/xfrm_policy.c +++ b/net/xfrm/xfrm_policy.c @@ -225,7 +225,7 @@ expired: * SPD calls. */ -struct xfrm_policy *xfrm_policy_alloc(unsigned int __nocast gfp) +struct xfrm_policy *xfrm_policy_alloc(gfp_t gfp) { struct xfrm_policy *policy; diff --git a/sound/core/memalloc.c b/sound/core/memalloc.c index 91124ddbdda..e72cec77f0d 100644 --- a/sound/core/memalloc.c +++ b/sound/core/memalloc.c @@ -106,7 +106,7 @@ struct snd_mem_list { static void *snd_dma_hack_alloc_coherent(struct device *dev, size_t size, dma_addr_t *dma_handle, - unsigned int __nocast flags) + gfp_t flags) { void *ret; u64 dma_mask, coherent_dma_mask; diff --git a/sound/core/memory.c b/sound/core/memory.c index 8fa888fc53a..7d8e2eebba5 100644 --- a/sound/core/memory.c +++ b/sound/core/memory.c @@ -89,7 +89,7 @@ void snd_memory_done(void) } } -static void *__snd_kmalloc(size_t size, unsigned int __nocast flags, void *caller) +static void *__snd_kmalloc(size_t size, gfp_t flags, void *caller) { unsigned long cpu_flags; struct snd_alloc_track *t; @@ -111,12 +111,12 @@ static void *__snd_kmalloc(size_t size, unsigned int __nocast flags, void *calle } #define _snd_kmalloc(size, flags) __snd_kmalloc((size), (flags), __builtin_return_address(0)); -void *snd_hidden_kmalloc(size_t size, unsigned int __nocast flags) +void *snd_hidden_kmalloc(size_t size, gfp_t flags) { return _snd_kmalloc(size, flags); } -void *snd_hidden_kzalloc(size_t size, unsigned int __nocast flags) +void *snd_hidden_kzalloc(size_t size, gfp_t flags) { void *ret = _snd_kmalloc(size, flags); if (ret) @@ -125,7 +125,7 @@ void *snd_hidden_kzalloc(size_t size, unsigned int __nocast flags) } EXPORT_SYMBOL(snd_hidden_kzalloc); -void *snd_hidden_kcalloc(size_t n, size_t size, unsigned int __nocast flags) +void *snd_hidden_kcalloc(size_t n, size_t size, gfp_t flags) { void *ret = NULL; if (n != 0 && size > INT_MAX / n) @@ -190,7 +190,7 @@ void snd_hidden_vfree(void *obj) snd_wrapper_vfree(obj); } -char *snd_hidden_kstrdup(const char *s, unsigned int __nocast flags) +char *snd_hidden_kstrdup(const char *s, gfp_t flags) { int len; char *buf; diff --git a/sound/core/seq/instr/ainstr_iw.c b/sound/core/seq/instr/ainstr_iw.c index b3cee092b1a..67c24c8e8e7 100644 --- a/sound/core/seq/instr/ainstr_iw.c +++ b/sound/core/seq/instr/ainstr_iw.c @@ -58,7 +58,7 @@ static int snd_seq_iwffff_copy_env_from_stream(__u32 req_stype, iwffff_xenv_t *ex, char __user **data, long *len, - unsigned int __nocast gfp_mask) + gfp_t gfp_mask) { __u32 stype; iwffff_env_record_t *rp, *rp_last; diff --git a/sound/core/wrappers.c b/sound/core/wrappers.c index 508e6d67ee1..296b716f137 100644 --- a/sound/core/wrappers.c +++ b/sound/core/wrappers.c @@ -27,7 +27,7 @@ #include #ifdef CONFIG_SND_DEBUG_MEMORY -void *snd_wrapper_kmalloc(size_t size, unsigned int __nocast flags) +void *snd_wrapper_kmalloc(size_t size, gfp_t flags) { return kmalloc(size, flags); } -- cgit v1.2.3 From 2e457ef667158840c1be511f5d10dd42c6dbbe46 Mon Sep 17 00:00:00 2001 From: Sven Hartge Date: Sat, 8 Oct 2005 21:12:04 -0700 Subject: [SPARC64]: Fix compile error in irq.c irq.c is missing the inclusion of asm/io.h, which causes readb() and writeb() the be undefined. Signed-off-by: Sven Hartge Signed-off-by: David S. Miller --- arch/sparc64/kernel/irq.c | 1 + 1 file changed, 1 insertion(+) diff --git a/arch/sparc64/kernel/irq.c b/arch/sparc64/kernel/irq.c index c9b69167632..233526ba3ab 100644 --- a/arch/sparc64/kernel/irq.c +++ b/arch/sparc64/kernel/irq.c @@ -27,6 +27,7 @@ #include #include #include +#include #include #include #include -- cgit v1.2.3 From ce80cc14810fbd78fa70c15c7e16a0b26d462fc6 Mon Sep 17 00:00:00 2001 From: Russell King Date: Mon, 10 Oct 2005 09:48:10 +0100 Subject: [ARM] Update mach-types Signed-off-by: Russell King --- arch/arm/tools/mach-types | 90 ++++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 86 insertions(+), 4 deletions(-) diff --git a/arch/arm/tools/mach-types b/arch/arm/tools/mach-types index 6d3a79e5fef..ae7c64b8cec 100644 --- a/arch/arm/tools/mach-types +++ b/arch/arm/tools/mach-types @@ -2,11 +2,17 @@ # # This file is linux/arch/arm/tools/mach-types # +# Up to date versions of this file can be obtained from: +# +# http://www.arm.linux.org.uk/developer/machines/?action=download +# # Please do not send patches to this file; it is automatically generated! # To add an entry into this database, please see Documentation/arm/README, -# or contact rmk@arm.linux.org.uk +# or visit: +# +# http://www.arm.linux.org.uk/developer/machines/?action=new # -# Last update: Thu Jun 23 20:19:33 2005 +# Last update: Mon Oct 10 09:46:25 2005 # # machine_is_xxx CONFIG_xxxx MACH_TYPE_xxx number # @@ -421,7 +427,7 @@ mt02 MACH_MT02 MT02 410 mport3s MACH_MPORT3S MPORT3S 411 ra_alpha MACH_RA_ALPHA RA_ALPHA 412 xcep MACH_XCEP XCEP 413 -arcom_mercury MACH_ARCOM_MERCURY ARCOM_MERCURY 414 +arcom_vulcan MACH_ARCOM_VULCAN ARCOM_VULCAN 414 stargate MACH_STARGATE STARGATE 415 armadilloj MACH_ARMADILLOJ ARMADILLOJ 416 elroy_jack MACH_ELROY_JACK ELROY_JACK 417 @@ -454,7 +460,7 @@ esl_sarva MACH_ESL_SARVA ESL_SARVA 443 xm250 MACH_XM250 XM250 444 t6tc1xb MACH_T6TC1XB T6TC1XB 445 ess710 MACH_ESS710 ESS710 446 -mx3ads MACH_MX3ADS MX3ADS 447 +mx31ads MACH_MX3ADS MX3ADS 447 himalaya MACH_HIMALAYA HIMALAYA 448 bolfenk MACH_BOLFENK BOLFENK 449 at91rm9200kr MACH_AT91RM9200KR AT91RM9200KR 450 @@ -787,3 +793,79 @@ ez_ixp42x MACH_EZ_IXP42X EZ_IXP42X 778 tapwave_zodiac MACH_TAPWAVE_ZODIAC TAPWAVE_ZODIAC 779 universalmeter MACH_UNIVERSALMETER UNIVERSALMETER 780 hicoarm9 MACH_HICOARM9 HICOARM9 781 +pnx4008 MACH_PNX4008 PNX4008 782 +kws6000 MACH_KWS6000 KWS6000 783 +portux920t MACH_PORTUX920T PORTUX920T 784 +ez_x5 MACH_EZ_X5 EZ_X5 785 +omap_rudolph MACH_OMAP_RUDOLPH OMAP_RUDOLPH 786 +cpuat91 MACH_CPUAT91 CPUAT91 787 +rea9200 MACH_REA9200 REA9200 788 +acts_pune_sa1110 MACH_ACTS_PUNE_SA1110 ACTS_PUNE_SA1110 789 +ixp425 MACH_IXP425 IXP425 790 +argonplusodyssey MACH_ODYSSEY ODYSSEY 791 +perch MACH_PERCH PERCH 792 +eis05r1 MACH_EIS05R1 EIS05R1 793 +pepperpad MACH_PEPPERPAD PEPPERPAD 794 +sb3010 MACH_SB3010 SB3010 795 +rm9200 MACH_RM9200 RM9200 796 +dma03 MACH_DMA03 DMA03 797 +road_s101 MACH_ROAD_S101 ROAD_S101 798 +iq_nextgen_a MACH_IQ_NEXTGEN_A IQ_NEXTGEN_A 799 +iq_nextgen_b MACH_IQ_NEXTGEN_B IQ_NEXTGEN_B 800 +iq_nextgen_c MACH_IQ_NEXTGEN_C IQ_NEXTGEN_C 801 +iq_nextgen_d MACH_IQ_NEXTGEN_D IQ_NEXTGEN_D 802 +iq_nextgen_e MACH_IQ_NEXTGEN_E IQ_NEXTGEN_E 803 +mallow_at91 MACH_MALLOW_AT91 MALLOW_AT91 804 +cybertracker MACH_CYBERTRACKER CYBERTRACKER 805 +gesbc931x MACH_GESBC931X GESBC931X 806 +centipad MACH_CENTIPAD CENTIPAD 807 +armsoc MACH_ARMSOC ARMSOC 808 +se4200 MACH_SE4200 SE4200 809 +ems197a MACH_EMS197A EMS197A 810 +micro9 MACH_MICRO9 MICRO9 811 +micro9l MACH_MICRO9L MICRO9L 812 +uc5471dsp MACH_UC5471DSP UC5471DSP 813 +sj5471eng MACH_SJ5471ENG SJ5471ENG 814 +none MACH_CMPXA26X CMPXA26X 815 +nc MACH_NC NC 816 +omap_palmte MACH_OMAP_PALMTE OMAP_PALMTE 817 +ajax52x MACH_AJAX52X AJAX52X 818 +siriustar MACH_SIRIUSTAR SIRIUSTAR 819 +iodata_hdlg MACH_IODATA_HDLG IODATA_HDLG 820 +at91rm9200utl MACH_AT91RM9200UTL AT91RM9200UTL 821 +biosafe MACH_BIOSAFE BIOSAFE 822 +mp1000 MACH_MP1000 MP1000 823 +parsy MACH_PARSY PARSY 824 +ccxp270 MACH_CCXP CCXP 825 +omap_gsample MACH_OMAP_GSAMPLE OMAP_GSAMPLE 826 +realview_eb MACH_REALVIEW_EB REALVIEW_EB 827 +samoa MACH_SAMOA SAMOA 828 +t3xscale MACH_T3XSCALE T3XSCALE 829 +i878 MACH_I878 I878 830 +borzoi MACH_BORZOI BORZOI 831 +gecko MACH_GECKO GECKO 832 +ds101 MACH_DS101 DS101 833 +omap_palmtt2 MACH_OMAP_PALMTT2 OMAP_PALMTT2 834 +xscale_palmld MACH_XSCALE_PALMLD XSCALE_PALMLD 835 +cc9c MACH_CC9C CC9C 836 +sbc1670 MACH_SBC1670 SBC1670 837 +ixdp28x5 MACH_IXDP28X5 IXDP28X5 838 +omap_palmtt MACH_OMAP_PALMTT OMAP_PALMTT 839 +ml696k MACH_ML696K ML696K 840 +arcom_zeus MACH_ARCOM_ZEUS ARCOM_ZEUS 841 +osiris MACH_OSIRIS OSIRIS 842 +maestro MACH_MAESTRO MAESTRO 843 +tunge2 MACH_TUNGE2 TUNGE2 844 +ixbbm MACH_IXBBM IXBBM 845 +mx27 MACH_MX27 MX27 846 +ax8004 MACH_AX8004 AX8004 847 +at91sam9261ek MACH_AT91SAM9261EK AT91SAM9261EK 848 +loft MACH_LOFT LOFT 849 +magpie MACH_MAGPIE MAGPIE 850 +mx21 MACH_MX21 MX21 851 +mb87m3400 MACH_MB87M3400 MB87M3400 852 +mguard_delta MACH_MGUARD_DELTA MGUARD_DELTA 853 +davinci_dvdp MACH_DAVINCI_DVDP DAVINCI_DVDP 854 +htcuniversal MACH_HTCUNIVERSAL HTCUNIVERSAL 855 +tpad MACH_TPAD TPAD 856 +roverp3 MACH_ROVERP3 ROVERP3 857 -- cgit v1.2.3 From 86371d071bc38a181984b01d323b6172a4b7bb1f Mon Sep 17 00:00:00 2001 From: Sascha Hauer Date: Mon, 10 Oct 2005 10:17:42 +0100 Subject: [ARM] 2957/1: imx UART Error handling Patch from Sascha Hauer Fix error path in imx_startup. Signed-off-by: Giancarlo Formicuccia Signed-off-by: Sascha Hauer Signed-off-by: Russell King --- drivers/serial/imx.c | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/drivers/serial/imx.c b/drivers/serial/imx.c index 4e1e80adaf1..53e0323d4b8 100644 --- a/drivers/serial/imx.c +++ b/drivers/serial/imx.c @@ -383,11 +383,11 @@ static int imx_startup(struct uart_port *port) */ retval = request_irq(sport->rxirq, imx_rxint, 0, DRIVER_NAME, sport); - if (retval) goto error_out2; + if (retval) goto error_out1; retval = request_irq(sport->txirq, imx_txint, 0, "imx-uart", sport); - if (retval) goto error_out1; + if (retval) goto error_out2; /* * Finally, clear and enable interrupts @@ -406,10 +406,9 @@ static int imx_startup(struct uart_port *port) return 0; -error_out1: - free_irq(sport->rxirq, sport); error_out2: - free_irq(sport->txirq, sport); + free_irq(sport->rxirq, sport); +error_out1: return retval; } -- cgit v1.2.3 From 79d13b62ef9da84d3ba551caac42d6107e57208f Mon Sep 17 00:00:00 2001 From: Sascha Hauer Date: Mon, 10 Oct 2005 10:17:43 +0100 Subject: [ARM] 2958/1: fix definition in imx-regs.h Patch from Sascha Hauer Fix PD7_AF_UART2_DTR definition Signed-off-by: Giancarlo Formicuccia Signed-off-by: Sascha Hauer Signed-off-by: Russell King --- include/asm-arm/arch-imx/imx-regs.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/asm-arm/arch-imx/imx-regs.h b/include/asm-arm/arch-imx/imx-regs.h index 229f7008d74..a6912b3d867 100644 --- a/include/asm-arm/arch-imx/imx-regs.h +++ b/include/asm-arm/arch-imx/imx-regs.h @@ -215,7 +215,7 @@ #define PC31_AOUT_UART3_RX ( GPIO_GIUS | GPIO_PORTC | GPIO_IN | 31) #define PD6_PF_LSCLK ( GPIO_PORTD | GPIO_OUT | GPIO_PF | 6 ) #define PD7_PF_REV ( GPIO_PORTD | GPIO_PF | 7 ) -#define PD7_AF_UART2_DTR ( GPIO_PORTD | GPIO_IN | GPIO_AF | 7 ) +#define PD7_AF_UART2_DTR ( GPIO_GIUS | GPIO_PORTD | GPIO_IN | GPIO_AF | 7 ) #define PD7_AIN_SPI2_SCLK ( GPIO_GIUS | GPIO_PORTD | GPIO_AIN | 7 ) #define PD8_PF_CLS ( GPIO_PORTD | GPIO_PF | 8 ) #define PD8_AF_UART2_DCD ( GPIO_PORTD | GPIO_OUT | GPIO_AF | 8 ) -- cgit v1.2.3 From 19da83f632d235fff9f94671d2e2cf87d27a2446 Mon Sep 17 00:00:00 2001 From: "George G. Davis" Date: Mon, 10 Oct 2005 10:17:44 +0100 Subject: [ARM] 2959/1: Add test for invalid LDRD/STRD Rd cases in ARM alignment handler Patch from George G. Davis Add test for invalid LDRD/STRD Rd cases in ARM alignment handler and restore SWP printk KERN_ERR. Signed-off-by: Steve Longerbeam Signed-off-by: George G. Davis Signed-off-by: Russell King --- arch/arm/mm/alignment.c | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/arch/arm/mm/alignment.c b/arch/arm/mm/alignment.c index 4b39d867ac1..f35e69e9c65 100644 --- a/arch/arm/mm/alignment.c +++ b/arch/arm/mm/alignment.c @@ -330,6 +330,9 @@ do_alignment_ldrdstrd(unsigned long addr, unsigned long instr, { unsigned int rd = RD_BITS(instr); + if (((rd & 1) == 1) || (rd == 14)) + goto bad; + ai_dword += 1; if (user_mode(regs)) @@ -361,7 +364,8 @@ do_alignment_ldrdstrd(unsigned long addr, unsigned long instr, } return TYPE_LDST; - + bad: + return TYPE_ERROR; fault: return TYPE_FAULT; } @@ -663,6 +667,8 @@ do_alignment(unsigned long addr, unsigned int fsr, struct pt_regs *regs) else if ((instr & 0x001000f0) == 0x000000d0 || /* LDRD */ (instr & 0x001000f0) == 0x000000f0) /* STRD */ handler = do_alignment_ldrdstrd; + else if ((instr & 0x01f00ff0) == 0x01000090) /* SWP */ + goto swp; else goto bad; break; @@ -733,6 +739,9 @@ do_alignment(unsigned long addr, unsigned int fsr, struct pt_regs *regs) do_bad_area(current, current->mm, addr, fsr, regs); return 0; + swp: + printk(KERN_ERR "Alignment trap: not handling swp instruction\n"); + bad: /* * Oops, we didn't handle the instruction. -- cgit v1.2.3 From 97b8e00e8538c9eb23983545d665ffd7052ccedb Mon Sep 17 00:00:00 2001 From: Richard Purdie Date: Mon, 10 Oct 2005 10:17:44 +0100 Subject: [ARM] 2960/1: collie: Add missing scoop call parameters Patch from Richard Purdie Add some missing parameters from the scoop calls on collie. Signed-off-by: Richard Purdie Signed-off-by: Russell King --- arch/arm/mach-sa1100/collie.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/arch/arm/mach-sa1100/collie.c b/arch/arm/mach-sa1100/collie.c index 25d6a4e2753..6ecab7e2c23 100644 --- a/arch/arm/mach-sa1100/collie.c +++ b/arch/arm/mach-sa1100/collie.c @@ -111,11 +111,11 @@ static struct mtd_partition collie_partitions[] = { static void collie_set_vpp(int vpp) { - write_scoop_reg(&colliescoop_device.dev, SCOOP_GPCR, read_scoop_reg(SCOOP_GPCR) | COLLIE_SCP_VPEN); + write_scoop_reg(&colliescoop_device.dev, SCOOP_GPCR, read_scoop_reg(&colliescoop_device.dev, SCOOP_GPCR) | COLLIE_SCP_VPEN); if (vpp) - write_scoop_reg(&colliescoop_device.dev, SCOOP_GPWR, read_scoop_reg(SCOOP_GPWR) | COLLIE_SCP_VPEN); + write_scoop_reg(&colliescoop_device.dev, SCOOP_GPWR, read_scoop_reg(&colliescoop_device.dev, SCOOP_GPWR) | COLLIE_SCP_VPEN); else - write_scoop_reg(&colliescoop_device.dev, SCOOP_GPWR, read_scoop_reg(SCOOP_GPWR) & ~COLLIE_SCP_VPEN); + write_scoop_reg(&colliescoop_device.dev, SCOOP_GPWR, read_scoop_reg(&colliescoop_device.dev, SCOOP_GPWR) & ~COLLIE_SCP_VPEN); } static struct flash_platform_data collie_flash_data = { -- cgit v1.2.3 From 1036260e93a907a0143efa31bf05be1f3271eb90 Mon Sep 17 00:00:00 2001 From: Richard Purdie Date: Mon, 10 Oct 2005 10:17:45 +0100 Subject: [ARM] 2961/1: corgi: Add missing include Patch from Richard Purdie Add a missing include from corgi.c Signed-off-by: Richard Purdie Signed-off-by: Russell King --- arch/arm/mach-pxa/corgi.c | 1 + 1 file changed, 1 insertion(+) diff --git a/arch/arm/mach-pxa/corgi.c b/arch/arm/mach-pxa/corgi.c index be37586cb1b..60c8b9d8bb9 100644 --- a/arch/arm/mach-pxa/corgi.c +++ b/arch/arm/mach-pxa/corgi.c @@ -36,6 +36,7 @@ #include #include #include +#include #include #include -- cgit v1.2.3 From 7c3989885cfd37d237eca97832b712a7ffbbf40c Mon Sep 17 00:00:00 2001 From: Richard Purdie Date: Mon, 10 Oct 2005 10:20:06 +0100 Subject: [ARM] 2962/1: scoop: Allow GPIO pin suspend state to be specified Patch from Richard Purdie Allow the GPIO pin suspend states to be specified for SCOOP devices. This is needed for correct operation on the spitz platform. Signed-off-by: Richard Purdie Signed-off-by: Russell King --- arch/arm/common/scoop.c | 20 ++++++++++++++++++-- include/asm-arm/hardware/scoop.h | 2 ++ 2 files changed, 20 insertions(+), 2 deletions(-) diff --git a/arch/arm/common/scoop.c b/arch/arm/common/scoop.c index d3a04c2a2c8..9e5245c702d 100644 --- a/arch/arm/common/scoop.c +++ b/arch/arm/common/scoop.c @@ -26,6 +26,8 @@ struct scoop_pcmcia_dev *scoop_devs; struct scoop_dev { void *base; spinlock_t scoop_lock; + unsigned short suspend_clr; + unsigned short suspend_set; u32 scoop_gpwr; }; @@ -90,14 +92,24 @@ EXPORT_SYMBOL(reset_scoop); EXPORT_SYMBOL(read_scoop_reg); EXPORT_SYMBOL(write_scoop_reg); +static void check_scoop_reg(struct scoop_dev *sdev) +{ + unsigned short mcr; + + mcr = SCOOP_REG(sdev->base, SCOOP_MCR); + if ((mcr & 0x100) == 0) + SCOOP_REG(sdev->base, SCOOP_MCR) = 0x0101; +} + #ifdef CONFIG_PM static int scoop_suspend(struct device *dev, pm_message_t state, uint32_t level) { if (level == SUSPEND_POWER_DOWN) { struct scoop_dev *sdev = dev_get_drvdata(dev); - sdev->scoop_gpwr = SCOOP_REG(sdev->base,SCOOP_GPWR); - SCOOP_REG(sdev->base,SCOOP_GPWR) = 0; + check_scoop_reg(sdev); + sdev->scoop_gpwr = SCOOP_REG(sdev->base, SCOOP_GPWR); + SCOOP_REG(sdev->base, SCOOP_GPWR) = (sdev->scoop_gpwr & ~sdev->suspend_clr) | sdev->suspend_set; } return 0; } @@ -107,6 +119,7 @@ static int scoop_resume(struct device *dev, uint32_t level) if (level == RESUME_POWER_ON) { struct scoop_dev *sdev = dev_get_drvdata(dev); + check_scoop_reg(sdev); SCOOP_REG(sdev->base,SCOOP_GPWR) = sdev->scoop_gpwr; } return 0; @@ -151,6 +164,9 @@ int __init scoop_probe(struct device *dev) SCOOP_REG(devptr->base, SCOOP_GPCR) = inf->io_dir & 0xffff; SCOOP_REG(devptr->base, SCOOP_GPWR) = inf->io_out & 0xffff; + devptr->suspend_clr = inf->suspend_clr; + devptr->suspend_set = inf->suspend_set; + return 0; } diff --git a/include/asm-arm/hardware/scoop.h b/include/asm-arm/hardware/scoop.h index 527404b5a8d..a8f1013930e 100644 --- a/include/asm-arm/hardware/scoop.h +++ b/include/asm-arm/hardware/scoop.h @@ -38,6 +38,8 @@ struct scoop_config { unsigned short io_out; unsigned short io_dir; + unsigned short suspend_clr; + unsigned short suspend_set; }; /* Structure for linking scoop devices to PCMCIA sockets */ -- cgit v1.2.3 From cdfc8f5079fdd18f6cb8097aa4235704d1155ec5 Mon Sep 17 00:00:00 2001 From: Ben Dooks Date: Mon, 10 Oct 2005 10:20:06 +0100 Subject: [ARM] 2963/1: S3C2410 - add .owner field to device_driver Patch from Ben Dooks Add initialisation of .owner field so that the device driver can be referenced to the module that owns it. Signed-off-by: Ben Dooks Signed-off-by: Russell King --- drivers/char/s3c2410-rtc.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/char/s3c2410-rtc.c b/drivers/char/s3c2410-rtc.c index ed867db550a..e1a90d9a875 100644 --- a/drivers/char/s3c2410-rtc.c +++ b/drivers/char/s3c2410-rtc.c @@ -564,6 +564,7 @@ static int s3c2410_rtc_resume(struct device *dev, u32 level) static struct device_driver s3c2410_rtcdrv = { .name = "s3c2410-rtc", + .owner = THIS_MODULE, .bus = &platform_bus_type, .probe = s3c2410_rtc_probe, .remove = s3c2410_rtc_remove, -- cgit v1.2.3 From 7dead80cbee3259e3a9f25bfc65c8dc769a19e0e Mon Sep 17 00:00:00 2001 From: Ben Dooks Date: Mon, 10 Oct 2005 10:20:07 +0100 Subject: [ARM] 2964/1: S3C2410 - serial: add .owner to driver Patch from Ben Dooks Initialise the driver's .owner field so that the device driver can be referenced to the module that owns it Signed-off-by: Ben Dooks Signed-off-by: Russell King --- drivers/serial/s3c2410.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/serial/s3c2410.c b/drivers/serial/s3c2410.c index 50d7870d92b..eff2158024c 100644 --- a/drivers/serial/s3c2410.c +++ b/drivers/serial/s3c2410.c @@ -1235,6 +1235,7 @@ static int s3c2400_serial_probe(struct device *dev) static struct device_driver s3c2400_serial_drv = { .name = "s3c2400-uart", + .owner = THIS_MODULE, .bus = &platform_bus_type, .probe = s3c2400_serial_probe, .remove = s3c24xx_serial_remove, @@ -1338,6 +1339,7 @@ static int s3c2410_serial_probe(struct device *dev) static struct device_driver s3c2410_serial_drv = { .name = "s3c2410-uart", + .owner = THIS_MODULE, .bus = &platform_bus_type, .probe = s3c2410_serial_probe, .remove = s3c24xx_serial_remove, @@ -1499,6 +1501,7 @@ static int s3c2440_serial_probe(struct device *dev) static struct device_driver s3c2440_serial_drv = { .name = "s3c2440-uart", + .owner = THIS_MODULE, .bus = &platform_bus_type, .probe = s3c2440_serial_probe, .remove = s3c24xx_serial_remove, -- cgit v1.2.3 From 220ec0291130a932b32b2c66a10e9c5019dab702 Mon Sep 17 00:00:00 2001 From: Steven Rostedt Date: Mon, 10 Oct 2005 11:13:17 -0400 Subject: [PATCH] pcmcia: fix task state at pccard thread exit The pccardd thread has a race in it that it can shutdown in the TASK_INTERRUPTIBLE state. Make sure we mark ourselves runnable again as we remove ourselves from the wait queue. Signed-off-by: Steven Rostedt Signed-off-by: Linus Torvalds --- drivers/pcmcia/cs.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/pcmcia/cs.c b/drivers/pcmcia/cs.c index fabd3529ceb..d5e76423a0e 100644 --- a/drivers/pcmcia/cs.c +++ b/drivers/pcmcia/cs.c @@ -689,6 +689,9 @@ static int pccardd(void *__skt) schedule(); try_to_freeze(); } + /* make sure we are running before we exit */ + set_current_state(TASK_RUNNING); + remove_wait_queue(&skt->thread_wait, &wait); /* remove from the device core */ -- cgit v1.2.3 From 5cd10daa0c7fc1410e1c0d685cbc9622c769eb16 Mon Sep 17 00:00:00 2001 From: Paolo 'Blaisorblade' Giarrusso Date: Sun, 9 Oct 2005 21:37:05 +0200 Subject: [PATCH] Uml: hide commands when not being verbose Add a missing $(Q) to a "ln" invocation. Signed-off-by: Paolo 'Blaisorblade' Giarrusso Signed-off-by: Linus Torvalds --- arch/um/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/um/Makefile b/arch/um/Makefile index 7af37e342e3..e1ffad22460 100644 --- a/arch/um/Makefile +++ b/arch/um/Makefile @@ -152,7 +152,7 @@ archclean: $(SYMLINK_HEADERS): @echo ' SYMLINK $@' ifneq ($(KBUILD_SRC),) - ln -fsn $(srctree)/include/asm-um/$(basename $(notdir $@))-$(SUBARCH)$(suffix $@) $@ + $(Q)ln -fsn $(srctree)/include/asm-um/$(basename $(notdir $@))-$(SUBARCH)$(suffix $@) $@ else $(Q)cd $(TOPDIR)/$(dir $@) ; \ ln -sf $(basename $(notdir $@))-$(SUBARCH)$(suffix $@) $(notdir $@) -- cgit v1.2.3 From 9e3d862e5c341c59b673c9cadd64210ca03cb41e Mon Sep 17 00:00:00 2001 From: Paolo 'Blaisorblade' Giarrusso Date: Sun, 9 Oct 2005 21:37:18 +0200 Subject: [PATCH] uml: add mode=skas0 as a synonym of skas0 Too many people were confused by skas0 and tried using "mode=skas0". And after all, they are right - accept this. Signed-off-by: Paolo 'Blaisorblade' Giarrusso Signed-off-by: Linus Torvalds --- arch/um/os-Linux/start_up.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/arch/um/os-Linux/start_up.c b/arch/um/os-Linux/start_up.c index 6af83171ca4..b99ab414542 100644 --- a/arch/um/os-Linux/start_up.c +++ b/arch/um/os-Linux/start_up.c @@ -143,11 +143,22 @@ static int __init skas0_cmd_param(char *str, int* add) return 0; } +/* The two __uml_setup would conflict, without this stupid alias. */ + +static int __init mode_skas0_cmd_param(char *str, int* add) + __attribute__((alias("skas0_cmd_param"))); + __uml_setup("skas0", skas0_cmd_param, "skas0\n" " Disables SKAS3 usage, so that SKAS0 is used, unless \n" " you specify mode=tt.\n\n"); +__uml_setup("mode=skas0", mode_skas0_cmd_param, + "mode=skas0\n" + " Disables SKAS3 usage, so that SKAS0 is used, unless you \n" + " specify mode=tt. Note that this was recently added - on \n" + " older kernels you must use simply \"skas0\".\n\n"); + static int force_sysemu_disabled = 0; static int __init nosysemu_cmd_param(char *str, int* add) -- cgit v1.2.3 From 54a8a2220c936a47840c9a3d74910c5a56fae2ed Mon Sep 17 00:00:00 2001 From: Paolo 'Blaisorblade' Giarrusso Date: Sun, 9 Oct 2005 21:37:26 +0200 Subject: [PATCH] uml: allow building .s/.i/.lst files from userspace files For files which need to include glibc headers (i.e. userspace files), we specified the correct flags only for .o, not for .s/.lst/.i. Fix this. Signed-off-by: Paolo 'Blaisorblade' Giarrusso Signed-off-by: Linus Torvalds --- arch/um/scripts/Makefile.rules | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/arch/um/scripts/Makefile.rules b/arch/um/scripts/Makefile.rules index 59a1291f477..651d9d88b65 100644 --- a/arch/um/scripts/Makefile.rules +++ b/arch/um/scripts/Makefile.rules @@ -7,8 +7,8 @@ USER_SINGLE_OBJS := \ USER_OBJS += $(filter %_user.o,$(obj-y) $(obj-m) $(USER_SINGLE_OBJS)) USER_OBJS := $(foreach file,$(USER_OBJS),$(obj)/$(file)) -$(USER_OBJS) : c_flags = -Wp,-MD,$(depfile) $(USER_CFLAGS) \ - $(CFLAGS_$(notdir $@)) +$(USER_OBJS) $(USER_OBJS:.o=.i) $(USER_OBJS:.o=.s) $(USER_OBJS:.o=.lst): \ + c_flags = -Wp,-MD,$(depfile) $(USER_CFLAGS) $(CFLAGS_$(notdir $@)) $(USER_OBJS): cmd_checksrc = $(USER_OBJS): quiet_cmd_checksrc = $(USER_OBJS): cmd_force_checksrc = -- cgit v1.2.3 From 855ec613ca7e1953d96d7ea81af90392678788f5 Mon Sep 17 00:00:00 2001 From: Paolo 'Blaisorblade' Giarrusso Date: Sun, 9 Oct 2005 21:37:35 +0200 Subject: [PATCH] uml: restore include breakage, breaking binary format of COW driver Commit 44456d37b59d8e541936ed26d8b6e08d27e88ac1, between 2.6.13-rc3 and -rc4, was a "nice cleanup" which broke something. Revert the offending part. It broke because: a) because this part doesn't fall under the description b) the author didn't know what he was doing here c) the author didn't try to compile the existing code and see that it worked perfectly. d) the author didn't ask us what was happening e) you didn't either, and somebody there should have learned that UML is a bit different. In fact, UML is special in linking to host libc and using its includes. In particular, since host includes always define both __BIG_ENDIAN and __LITTLE_ENDIAN, ntohll() macros started thinking to be in a big-endian world; and on-disk compatibility was broken. Many thanks go to Nix for reporting the problem and correctly diagnosing an endianness problem. Btw, this patch restores the previous code, which worked; but the definitions would be uncorrect if used in kernelspace files. Next patch addresses that. Cc: Nix , Olaf Hering Signed-off-by: Paolo 'Blaisorblade' Giarrusso Signed-off-by: Linus Torvalds --- arch/um/drivers/cow.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/arch/um/drivers/cow.h b/arch/um/drivers/cow.h index 4fcf3a8d13f..4fcbe8b1b77 100644 --- a/arch/um/drivers/cow.h +++ b/arch/um/drivers/cow.h @@ -3,10 +3,10 @@ #include -#if defined(__BIG_ENDIAN) +#if __BYTE_ORDER == __BIG_ENDIAN # define ntohll(x) (x) # define htonll(x) (x) -#elif defined(__LITTLE_ENDIAN) +#elif __BYTE_ORDER == __LITTLE_ENDIAN # define ntohll(x) bswap_64(x) # define htonll(x) bswap_64(x) #else -- cgit v1.2.3 From 028c0cc16e429ae24d9b8aacc64f4438bdfac0cc Mon Sep 17 00:00:00 2001 From: Paolo 'Blaisorblade' Giarrusso Date: Sun, 9 Oct 2005 21:37:45 +0200 Subject: [PATCH] uml: cleanup byte order macros for COW driver After restoring the existing code, make it work also when included in kernelspace code (which isn't currently the case, but at least this will prevent people from "fixing" it as just happened). Whitespace is fixed in next patch - it cluttered the diff too much. Signed-off-by: Paolo 'Blaisorblade' Giarrusso Signed-off-by: Linus Torvalds --- arch/um/drivers/cow.h | 27 ++++++++++++++++++++++++++- arch/um/drivers/cow_user.c | 1 - 2 files changed, 26 insertions(+), 2 deletions(-) diff --git a/arch/um/drivers/cow.h b/arch/um/drivers/cow.h index 4fcbe8b1b77..c54e20a3d21 100644 --- a/arch/um/drivers/cow.h +++ b/arch/um/drivers/cow.h @@ -3,6 +3,26 @@ #include +#if defined(__KERNEL__) + +# include + +# if defined(__BIG_ENDIAN) +# define ntohll(x) (x) +# define htonll(x) (x) +# elif defined(__LITTLE_ENDIAN) +# define ntohll(x) be64_to_cpu(x) +# define htonll(x) cpu_to_be64(x) +# else +# error "Could not determine byte order" +# endif + +#else +/* For the definition of ntohl, htonl and __BYTE_ORDER */ +#include +#include +#if defined(__BYTE_ORDER) + #if __BYTE_ORDER == __BIG_ENDIAN # define ntohll(x) (x) # define htonll(x) (x) @@ -10,8 +30,13 @@ # define ntohll(x) bswap_64(x) # define htonll(x) bswap_64(x) #else -#error "__BYTE_ORDER not defined" +# error "Could not determine byte order: __BYTE_ORDER uncorrectly defined" +#endif + +#else /* ! defined(__BYTE_ORDER) */ +# error "Could not determine byte order: __BYTE_ORDER not defined" #endif +#endif /* ! defined(__KERNEL__) */ extern int init_cow_file(int fd, char *cow_file, char *backing_file, int sectorsize, int alignment, int *bitmap_offset_out, diff --git a/arch/um/drivers/cow_user.c b/arch/um/drivers/cow_user.c index a8ce6fc3ef2..fbe2217db5d 100644 --- a/arch/um/drivers/cow_user.c +++ b/arch/um/drivers/cow_user.c @@ -9,7 +9,6 @@ #include #include #include -#include #include "os.h" -- cgit v1.2.3 From 52a2d3e45e06012a662f627177729d3196ba8903 Mon Sep 17 00:00:00 2001 From: Paolo 'Blaisorblade' Giarrusso Date: Sun, 9 Oct 2005 21:37:53 +0200 Subject: [PATCH] uml: cleanup whitespace for COW driver Fix whitespace - I split this off the previous patch for easier review. Signed-off-by: Paolo 'Blaisorblade' Giarrusso Signed-off-by: Linus Torvalds --- arch/um/drivers/cow.h | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/arch/um/drivers/cow.h b/arch/um/drivers/cow.h index c54e20a3d21..dc36b222100 100644 --- a/arch/um/drivers/cow.h +++ b/arch/um/drivers/cow.h @@ -23,15 +23,15 @@ #include #if defined(__BYTE_ORDER) -#if __BYTE_ORDER == __BIG_ENDIAN -# define ntohll(x) (x) -# define htonll(x) (x) -#elif __BYTE_ORDER == __LITTLE_ENDIAN -# define ntohll(x) bswap_64(x) -# define htonll(x) bswap_64(x) -#else -# error "Could not determine byte order: __BYTE_ORDER uncorrectly defined" -#endif +# if __BYTE_ORDER == __BIG_ENDIAN +# define ntohll(x) (x) +# define htonll(x) (x) +# elif __BYTE_ORDER == __LITTLE_ENDIAN +# define ntohll(x) bswap_64(x) +# define htonll(x) bswap_64(x) +# else +# error "Could not determine byte order: __BYTE_ORDER uncorrectly defined" +# endif #else /* ! defined(__BYTE_ORDER) */ # error "Could not determine byte order: __BYTE_ORDER not defined" -- cgit v1.2.3 From 3dd083255ddcfa87751fa8e32f61a9547a15a541 Mon Sep 17 00:00:00 2001 From: "Rafael J. Wysocki" Date: Sun, 9 Oct 2005 21:19:40 +0200 Subject: [PATCH] x86_64: Set up safe page tables during resume The following patch makes swsusp avoid the possible temporary corruption of page translation tables during resume on x86-64. This is achieved by creating a copy of the relevant page tables that will not be modified by swsusp and can be safely used by it on resume. The problem is that during resume on x86-64 swsusp may temporarily corrupt the page tables used for the direct mapping of RAM. If that happens, a page fault occurs and cannot be handled properly, which leads to the solid hang of the affected system. This leads to the loss of the system's state from before suspend and may result in the loss of data or the corruption of filesystems, so it is a serious issue. Also, it appears to happen quite often (for me, as often as 50% of the time). The problem is related to the fact that (at least) one of the PMD entries used in the direct memory mapping (starting at PAGE_OFFSET) points to a page table the physical address of which is much greater than the physical address of the PMD entry itself. Moreover, unfortunately, the physical address of the page table before suspend (i.e. the one stored in the suspend image) happens to be different to the physical address of the corresponding page table used during resume (i.e. the one that is valid right before swsusp_arch_resume() in arch/x86_64/kernel/suspend_asm.S is executed). Thus while the image is restored, the "offending" PMD entry gets overwritten, so it does not point to the right physical address any more (i.e. there's no page table at the address pointed to by it, because it points to the address the page table has been at during suspend). Consequently, if the PMD entry is used later on, and it _is_ used in the process of copying the image pages, a page fault occurs, but it cannot be handled in the normal way and the system hangs. In principle we can call create_resume_mapping() from swsusp_arch_resume() (ie. from suspend_asm.S), but then the memory allocations in create_resume_mapping(), resume_pud_mapping(), and resume_pmd_mapping() must be made carefully so that we use _only_ NosaveFree pages in them (the other pages are overwritten by the loop in swsusp_arch_resume()). Additionally, we are in atomic context at that time, so we cannot use GFP_KERNEL. Moreover, if one of the allocations fails, we should free all of the allocated pages, so we need to trace them somehow. All of this is done in the appended patch, except that the functions populating the page tables are located in arch/x86_64/kernel/suspend.c rather than in init.c. It may be done in a more elegan way in the future, with the help of some swsusp patches that are in the works now. [AK: move some externs into headers, renamed a function] Signed-off-by: Rafael J. Wysocki Signed-off-by: Andi Kleen Signed-off-by: Linus Torvalds --- arch/x86_64/kernel/suspend.c | 127 +++++++++++++++++++++++++++++++++++++++ arch/x86_64/kernel/suspend_asm.S | 17 ++++-- include/linux/suspend.h | 2 + kernel/power/swsusp.c | 7 ++- 4 files changed, 144 insertions(+), 9 deletions(-) diff --git a/arch/x86_64/kernel/suspend.c b/arch/x86_64/kernel/suspend.c index ebb9abf3ce6..f066c6ab361 100644 --- a/arch/x86_64/kernel/suspend.c +++ b/arch/x86_64/kernel/suspend.c @@ -11,6 +11,8 @@ #include #include #include +#include +#include struct saved_context saved_context; @@ -140,4 +142,129 @@ void fix_processor_context(void) } +#ifdef CONFIG_SOFTWARE_SUSPEND +/* Defined in arch/x86_64/kernel/suspend_asm.S */ +extern int restore_image(void); +pgd_t *temp_level4_pgt; + +static void **pages; + +static inline void *__add_page(void) +{ + void **c; + + c = (void **)get_usable_page(GFP_ATOMIC); + if (c) { + *c = pages; + pages = c; + } + return c; +} + +static inline void *__next_page(void) +{ + void **c; + + c = pages; + if (c) { + pages = *c; + *c = NULL; + } + return c; +} + +/* + * Try to allocate as many usable pages as needed and daisy chain them. + * If one allocation fails, free the pages allocated so far + */ +static int alloc_usable_pages(unsigned long n) +{ + void *p; + + pages = NULL; + do + if (!__add_page()) + break; + while (--n); + if (n) { + p = __next_page(); + while (p) { + free_page((unsigned long)p); + p = __next_page(); + } + return -ENOMEM; + } + return 0; +} + +static void res_phys_pud_init(pud_t *pud, unsigned long address, unsigned long end) +{ + long i, j; + + i = pud_index(address); + pud = pud + i; + for (; i < PTRS_PER_PUD; pud++, i++) { + unsigned long paddr; + pmd_t *pmd; + + paddr = address + i*PUD_SIZE; + if (paddr >= end) + break; + + pmd = (pmd_t *)__next_page(); + set_pud(pud, __pud(__pa(pmd) | _KERNPG_TABLE)); + for (j = 0; j < PTRS_PER_PMD; pmd++, j++, paddr += PMD_SIZE) { + unsigned long pe; + + if (paddr >= end) + break; + pe = _PAGE_NX | _PAGE_PSE | _KERNPG_TABLE | paddr; + pe &= __supported_pte_mask; + set_pmd(pmd, __pmd(pe)); + } + } +} + +static void set_up_temporary_mappings(void) +{ + unsigned long start, end, next; + + temp_level4_pgt = (pgd_t *)__next_page(); + + /* It is safe to reuse the original kernel mapping */ + set_pgd(temp_level4_pgt + pgd_index(__START_KERNEL_map), + init_level4_pgt[pgd_index(__START_KERNEL_map)]); + + /* Set up the direct mapping from scratch */ + start = (unsigned long)pfn_to_kaddr(0); + end = (unsigned long)pfn_to_kaddr(end_pfn); + + for (; start < end; start = next) { + pud_t *pud = (pud_t *)__next_page(); + next = start + PGDIR_SIZE; + if (next > end) + next = end; + res_phys_pud_init(pud, __pa(start), __pa(next)); + set_pgd(temp_level4_pgt + pgd_index(start), + mk_kernel_pgd(__pa(pud))); + } +} + +int swsusp_arch_resume(void) +{ + unsigned long n; + + n = ((end_pfn << PAGE_SHIFT) + PUD_SIZE - 1) >> PUD_SHIFT; + n += (n + PTRS_PER_PUD - 1) / PTRS_PER_PUD + 1; + pr_debug("swsusp_arch_resume(): pages needed = %lu\n", n); + if (alloc_usable_pages(n)) { + free_eaten_memory(); + return -ENOMEM; + } + /* We have got enough memory and from now on we cannot recover */ + set_up_temporary_mappings(); + restore_image(); + return 0; +} +#endif /* CONFIG_SOFTWARE_SUSPEND */ diff --git a/arch/x86_64/kernel/suspend_asm.S b/arch/x86_64/kernel/suspend_asm.S index 4d659e97df1..320b6fb00cc 100644 --- a/arch/x86_64/kernel/suspend_asm.S +++ b/arch/x86_64/kernel/suspend_asm.S @@ -39,12 +39,13 @@ ENTRY(swsusp_arch_suspend) call swsusp_save ret -ENTRY(swsusp_arch_resume) - /* set up cr3 */ - leaq init_level4_pgt(%rip),%rax - subq $__START_KERNEL_map,%rax - movq %rax,%cr3 - +ENTRY(restore_image) + /* switch to temporary page tables */ + movq $__PAGE_OFFSET, %rdx + movq temp_level4_pgt(%rip), %rax + subq %rdx, %rax + movq %rax, %cr3 + /* Flush TLB */ movq mmu_cr4_features(%rip), %rax movq %rax, %rdx andq $~(1<<7), %rdx # PGE @@ -69,6 +70,10 @@ loop: movq pbe_next(%rdx), %rdx jmp loop done: + /* go back to the original page tables */ + leaq init_level4_pgt(%rip), %rax + subq $__START_KERNEL_map, %rax + movq %rax, %cr3 /* Flush TLB, including "global" things (vmalloc) */ movq mmu_cr4_features(%rip), %rax movq %rax, %rdx diff --git a/include/linux/suspend.h b/include/linux/suspend.h index f2e96fdfaae..ad15a54806d 100644 --- a/include/linux/suspend.h +++ b/include/linux/suspend.h @@ -71,5 +71,7 @@ void restore_processor_state(void); struct saved_context; void __save_processor_state(struct saved_context *ctxt); void __restore_processor_state(struct saved_context *ctxt); +extern unsigned long get_usable_page(unsigned gfp_mask); +extern void free_eaten_memory(void); #endif /* _LINUX_SWSUSP_H */ diff --git a/kernel/power/swsusp.c b/kernel/power/swsusp.c index acf79ac1cb6..2d5c4567644 100644 --- a/kernel/power/swsusp.c +++ b/kernel/power/swsusp.c @@ -1095,7 +1095,7 @@ static inline void eat_page(void *page) *eaten_memory = c; } -static unsigned long get_usable_page(unsigned gfp_mask) +unsigned long get_usable_page(unsigned gfp_mask) { unsigned long m; @@ -1109,7 +1109,7 @@ static unsigned long get_usable_page(unsigned gfp_mask) return m; } -static void free_eaten_memory(void) +void free_eaten_memory(void) { unsigned long m; void **c; @@ -1481,11 +1481,12 @@ static int read_suspend_image(void) /* Allocate memory for the image and read the data from swap */ error = check_pagedir(pagedir_nosave); - free_eaten_memory(); + if (!error) error = data_read(pagedir_nosave); if (error) { /* We fail cleanly */ + free_eaten_memory(); for_each_pbe (p, pagedir_nosave) if (p->address) { free_page(p->address); -- cgit v1.2.3 From 50f72b57946d565db74fae71bac23f3f319311c8 Mon Sep 17 00:00:00 2001 From: Jeff Dike Date: Sun, 9 Oct 2005 16:11:44 -0400 Subject: [PATCH] uml: fix x86_64 with !CONFIG_FRAME_POINTER UML/x86_64 doesn't run when built with frame pointers disabled. There was an implicit frame pointer assumption in the stub segfault handler. With frame pointers disabled, UML dies on handling its first page fault. The container-of part of this is from Paolo Giarrusso . Signed-off-by: Jeff Dike Signed-off-by: Linus Torvalds --- arch/um/sys-x86_64/stub_segv.c | 37 ++++++++++++++++++++++++++++--------- 1 file changed, 28 insertions(+), 9 deletions(-) diff --git a/arch/um/sys-x86_64/stub_segv.c b/arch/um/sys-x86_64/stub_segv.c index 65a131b362b..d1e53bdf2e8 100644 --- a/arch/um/sys-x86_64/stub_segv.c +++ b/arch/um/sys-x86_64/stub_segv.c @@ -10,6 +10,22 @@ #include "uml-config.h" #include "sysdep/sigcontext.h" #include "sysdep/faultinfo.h" +#include + +/* Copied from sys-x86_64/signal.c - Can't find an equivalent definition + * in the libc headers anywhere. + */ +struct rt_sigframe +{ + char *pretcode; + struct ucontext uc; + struct siginfo info; +}; + +/* Copied here from - we're userspace. */ +#define container_of(ptr, type, member) ({ \ + const typeof( ((type *)0)->member ) *__mptr = (ptr); \ + (type *)( (char *)__mptr - offsetof(type,member) );}) void __attribute__ ((__section__ (".__syscall_stub"))) stub_segv_handler(int sig) @@ -17,16 +33,19 @@ stub_segv_handler(int sig) struct ucontext *uc; __asm__("movq %%rdx, %0" : "=g" (uc) :); - GET_FAULTINFO_FROM_SC(*((struct faultinfo *) UML_CONFIG_STUB_DATA), - &uc->uc_mcontext); + GET_FAULTINFO_FROM_SC(*((struct faultinfo *) UML_CONFIG_STUB_DATA), + &uc->uc_mcontext); - __asm__("movq %0, %%rax ; syscall": : "g" (__NR_getpid)); + __asm__("movq %0, %%rax ; syscall": : "g" (__NR_getpid)); __asm__("movq %%rax, %%rdi ; movq %0, %%rax ; movq %1, %%rsi ;" - "syscall": : "g" (__NR_kill), "g" (SIGUSR1)); - /* Two popqs to restore the stack to the state just before entering - * the handler, one pops the return address, the other pops the frame - * pointer. + "syscall": : "g" (__NR_kill), "g" (SIGUSR1) : + "%rdi", "%rax", "%rsi"); + /* sys_sigreturn expects that the stack pointer will be 8 bytes into + * the signal frame. So, we use the ucontext pointer, which we know + * already, to get the signal frame pointer, and add 8 to that. */ - __asm__("popq %%rax ; popq %%rax ; movq %0, %%rax ; syscall" : : "g" - (__NR_rt_sigreturn)); + __asm__("movq %0, %%rsp": : + "g" ((unsigned long) container_of(uc, struct rt_sigframe, + uc) + 8)); + __asm__("movq %0, %%rax ; syscall" : : "g" (__NR_rt_sigreturn)); } -- cgit v1.2.3 From 1cc956e12aedfdc6baf6312bc36a6b5a71af3c9d Mon Sep 17 00:00:00 2001 From: Tom Zanussi Date: Sun, 9 Oct 2005 10:41:32 -0500 Subject: [PATCH] relayfs: fix bogus param value in call to vmap The third param in this call to vmap shouldn't be GFP_KERNEL, which makes no sense, but rather VM_MAP. Thanks to Al Viro for spotting this. Signed-off-by: Tom Zanussi Signed-off-by: Linus Torvalds --- fs/relayfs/buffers.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/fs/relayfs/buffers.c b/fs/relayfs/buffers.c index 2aa8e271999..84e21ffa5ca 100644 --- a/fs/relayfs/buffers.c +++ b/fs/relayfs/buffers.c @@ -109,7 +109,7 @@ static void *relay_alloc_buf(struct rchan_buf *buf, unsigned long size) if (unlikely(!buf->page_array[i])) goto depopulate; } - mem = vmap(buf->page_array, n_pages, GFP_KERNEL, PAGE_KERNEL); + mem = vmap(buf->page_array, n_pages, VM_MAP, PAGE_KERNEL); if (!mem) goto depopulate; -- cgit v1.2.3 From 867f8b4e47a17c5d68c98dc6eee12739c4490056 Mon Sep 17 00:00:00 2001 From: Benjamin Herrenschmidt Date: Sun, 9 Oct 2005 10:37:47 +1000 Subject: [PATCH] ide: Workaround PM problem The logic in ide_do_request() doesn't guarantee that both drives will be serviced after a call. It may "forget" to service one in some circumstances, including when one of the drive is suspended (it will eventually fail to service the slave when the master is suspended for example). This prevents the wakeup requests that gets queued on wakeup from sleep from beeing serviced in some cases when 2 drives are sharing an IDE bus. The problem is deep enough in the way this code works (and there are probably a few other problematic but rare corner cases) and fixing it would require some major rethinking of the way IDE decides which channel to service. This is not 2.6.14 material. However, in the meantime, Bart has accepted this simple workaround that will fix the crash on wakeup from sleep since this specific corner case is actually hitting users to get into 2.6.14. Signed-off-by: Benjamin Herrenschmidt Signed-off-by: Linus Torvalds --- drivers/ide/ide-io.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/drivers/ide/ide-io.c b/drivers/ide/ide-io.c index 9e9cf140731..5275cbb1afe 100644 --- a/drivers/ide/ide-io.c +++ b/drivers/ide/ide-io.c @@ -1101,6 +1101,7 @@ static void ide_do_request (ide_hwgroup_t *hwgroup, int masked_irq) ide_hwif_t *hwif; struct request *rq; ide_startstop_t startstop; + int loops = 0; /* for atari only: POSSIBLY BROKEN HERE(?) */ ide_get_lock(ide_intr, hwgroup); @@ -1153,6 +1154,7 @@ static void ide_do_request (ide_hwgroup_t *hwgroup, int masked_irq) /* no more work for this hwgroup (for now) */ return; } + again: hwif = HWIF(drive); if (hwgroup->hwif->sharing_irq && hwif != hwgroup->hwif && @@ -1192,8 +1194,14 @@ static void ide_do_request (ide_hwgroup_t *hwgroup, int masked_irq) * though. I hope that doesn't happen too much, hopefully not * unless the subdriver triggers such a thing in its own PM * state machine. + * + * We count how many times we loop here to make sure we service + * all drives in the hwgroup without looping for ever */ if (drive->blocked && !blk_pm_request(rq) && !(rq->flags & REQ_PREEMPT)) { + drive = drive->next ? drive->next : hwgroup->drive; + if (loops++ < 4 && !blk_queue_plugged(drive->queue)) + goto again; /* We clear busy, there should be no pending ATA command at this point. */ hwgroup->busy = 0; break; -- cgit v1.2.3 From d347f372273c2b3d86a66e2e1c94c790c208e166 Mon Sep 17 00:00:00 2001 From: "Markus F.X.J. Oberhumer" Date: Sun, 9 Oct 2005 18:54:23 +0200 Subject: [PATCH] i386: fix stack alignment for signal handlers This fixes the setup of the alignment of the signal frame, so that all signal handlers are run with a properly aligned stack frame. The current code "over-aligns" the stack pointer so that the stack frame is effectively always mis-aligned by 4 bytes. But what we really want is that on function entry ((sp + 4) & 15) == 0, which matches what would happen if the stack were aligned before a "call" instruction. Signed-off-by: Markus F.X.J. Oberhumer Signed-off-by: Linus Torvalds --- arch/i386/kernel/signal.c | 6 +++++- arch/x86_64/ia32/ia32_signal.c | 6 +++++- 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/arch/i386/kernel/signal.c b/arch/i386/kernel/signal.c index 61eb0c8a6e4..adcd069db91 100644 --- a/arch/i386/kernel/signal.c +++ b/arch/i386/kernel/signal.c @@ -338,7 +338,11 @@ get_sigframe(struct k_sigaction *ka, struct pt_regs * regs, size_t frame_size) esp = (unsigned long) ka->sa.sa_restorer; } - return (void __user *)((esp - frame_size) & -8ul); + esp -= frame_size; + /* Align the stack pointer according to the i386 ABI, + * i.e. so that on function entry ((sp + 4) & 15) == 0. */ + esp = ((esp + 4) & -16ul) - 4; + return (void __user *) esp; } /* These symbols are defined with the addresses in the vsyscall page. diff --git a/arch/x86_64/ia32/ia32_signal.c b/arch/x86_64/ia32/ia32_signal.c index 66e2821533d..0903cc1faef 100644 --- a/arch/x86_64/ia32/ia32_signal.c +++ b/arch/x86_64/ia32/ia32_signal.c @@ -425,7 +425,11 @@ get_sigframe(struct k_sigaction *ka, struct pt_regs * regs, size_t frame_size) rsp = (unsigned long) ka->sa.sa_restorer; } - return (void __user *)((rsp - frame_size) & -8UL); + rsp -= frame_size; + /* Align the stack pointer according to the i386 ABI, + * i.e. so that on function entry ((sp + 4) & 15) == 0. */ + rsp = ((rsp + 4) & -16ul) - 4; + return (void __user *) rsp; } int ia32_setup_frame(int sig, struct k_sigaction *ka, -- cgit v1.2.3 From 585f54575d832506bbe9b5a2f435f37b81efc849 Mon Sep 17 00:00:00 2001 From: Nicolas Pitre Date: Mon, 10 Oct 2005 18:22:17 +0100 Subject: [ARM] 2956/1: fix the "Fix gcc4 build errors in ucb1x00-core.c" Patch from Nicolas Pitre drivers/mfd/ucb1x00-core.c: In function 'ucb1x00_probe': drivers/mfd/ucb1x00-core.c:482: error: 'ucb1x00_class' undeclared (first use in this function) Signed-off-by: Nicolas Pitre Signed-off-by: Russell King --- drivers/mfd/ucb1x00-core.c | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/drivers/mfd/ucb1x00-core.c b/drivers/mfd/ucb1x00-core.c index 612564ac6f7..e335d54c465 100644 --- a/drivers/mfd/ucb1x00-core.c +++ b/drivers/mfd/ucb1x00-core.c @@ -457,6 +457,17 @@ static int ucb1x00_detect_irq(struct ucb1x00 *ucb) return probe_irq_off(mask); } +static void ucb1x00_release(struct class_device *dev) +{ + struct ucb1x00 *ucb = classdev_to_ucb1x00(dev); + kfree(ucb); +} + +static struct class ucb1x00_class = { + .name = "ucb1x00", + .release = ucb1x00_release, +}; + static int ucb1x00_probe(struct mcp *mcp) { struct ucb1x00 *ucb; @@ -546,17 +557,6 @@ static void ucb1x00_remove(struct mcp *mcp) class_device_unregister(&ucb->cdev); } -static void ucb1x00_release(struct class_device *dev) -{ - struct ucb1x00 *ucb = classdev_to_ucb1x00(dev); - kfree(ucb); -} - -static struct class ucb1x00_class = { - .name = "ucb1x00", - .release = ucb1x00_release, -}; - int ucb1x00_register_driver(struct ucb1x00_driver *drv) { struct ucb1x00 *ucb; -- cgit v1.2.3 From 86b324874f571297237c0c940bfe7e5f0f9ca5d2 Mon Sep 17 00:00:00 2001 From: Vincent Sanders Date: Mon, 10 Oct 2005 18:24:06 +0100 Subject: [ARM] 2965/1: defconfig for the ARM Spitz platform Patch from Vincent Sanders Add a defconfig for the ARM Spitz Zarus platform Signed-off-by: Richard Purdie Signed-off-by: Vincent Sanders Signed-off-by: Russell King --- arch/arm/configs/spitz_defconfig | 1401 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 1401 insertions(+) create mode 100644 arch/arm/configs/spitz_defconfig diff --git a/arch/arm/configs/spitz_defconfig b/arch/arm/configs/spitz_defconfig new file mode 100644 index 00000000000..900e04f8e38 --- /dev/null +++ b/arch/arm/configs/spitz_defconfig @@ -0,0 +1,1401 @@ +# +# Automatically generated make config: don't edit +# Linux kernel version: 2.6.14-rc3 +# Sun Oct 9 17:11:19 2005 +# +CONFIG_ARM=y +CONFIG_MMU=y +CONFIG_UID16=y +CONFIG_RWSEM_GENERIC_SPINLOCK=y +CONFIG_GENERIC_CALIBRATE_DELAY=y + +# +# Code maturity level options +# +CONFIG_EXPERIMENTAL=y +CONFIG_CLEAN_COMPILE=y +CONFIG_BROKEN_ON_SMP=y +CONFIG_LOCK_KERNEL=y +CONFIG_INIT_ENV_ARG_LIMIT=32 + +# +# General setup +# +CONFIG_LOCALVERSION="" +CONFIG_LOCALVERSION_AUTO=y +CONFIG_SWAP=y +CONFIG_SYSVIPC=y +# CONFIG_POSIX_MQUEUE is not set +CONFIG_BSD_PROCESS_ACCT=y +# CONFIG_BSD_PROCESS_ACCT_V3 is not set +CONFIG_SYSCTL=y +# CONFIG_AUDIT is not set +CONFIG_HOTPLUG=y +CONFIG_KOBJECT_UEVENT=y +# CONFIG_IKCONFIG is not set +CONFIG_INITRAMFS_SOURCE="" +CONFIG_EMBEDDED=y +CONFIG_KALLSYMS=y +# CONFIG_KALLSYMS_ALL is not set +# CONFIG_KALLSYMS_EXTRA_PASS is not set +CONFIG_PRINTK=y +CONFIG_BUG=y +CONFIG_BASE_FULL=y +CONFIG_FUTEX=y +CONFIG_EPOLL=y +# CONFIG_CC_OPTIMIZE_FOR_SIZE is not set +CONFIG_SHMEM=y +CONFIG_CC_ALIGN_FUNCTIONS=0 +CONFIG_CC_ALIGN_LABELS=0 +CONFIG_CC_ALIGN_LOOPS=0 +CONFIG_CC_ALIGN_JUMPS=0 +# CONFIG_TINY_SHMEM is not set +CONFIG_BASE_SMALL=0 + +# +# Loadable module support +# +CONFIG_MODULES=y +CONFIG_MODULE_UNLOAD=y +CONFIG_MODULE_FORCE_UNLOAD=y +CONFIG_OBSOLETE_MODPARM=y +# CONFIG_MODVERSIONS is not set +# CONFIG_MODULE_SRCVERSION_ALL is not set +CONFIG_KMOD=y + +# +# System Type +# +# CONFIG_ARCH_CLPS7500 is not set +# CONFIG_ARCH_CLPS711X is not set +# CONFIG_ARCH_CO285 is not set +# CONFIG_ARCH_EBSA110 is not set +# CONFIG_ARCH_CAMELOT is not set +# CONFIG_ARCH_FOOTBRIDGE is not set +# CONFIG_ARCH_INTEGRATOR is not set +# CONFIG_ARCH_IOP3XX is not set +# CONFIG_ARCH_IXP4XX is not set +# CONFIG_ARCH_IXP2000 is not set +# CONFIG_ARCH_L7200 is not set +CONFIG_ARCH_PXA=y +# CONFIG_ARCH_RPC is not set +# CONFIG_ARCH_SA1100 is not set +# CONFIG_ARCH_S3C2410 is not set +# CONFIG_ARCH_SHARK is not set +# CONFIG_ARCH_LH7A40X is not set +# CONFIG_ARCH_OMAP is not set +# CONFIG_ARCH_VERSATILE is not set +# CONFIG_ARCH_IMX is not set +# CONFIG_ARCH_H720X is not set +# CONFIG_ARCH_AAEC2000 is not set + +# +# Intel PXA2xx Implementations +# +# CONFIG_ARCH_LUBBOCK is not set +# CONFIG_MACH_MAINSTONE is not set +# CONFIG_ARCH_PXA_IDP is not set +CONFIG_PXA_SHARPSL=y +# CONFIG_PXA_SHARPSL_25x is not set +CONFIG_PXA_SHARPSL_27x=y +CONFIG_MACH_SPITZ=y +CONFIG_MACH_BORZOI=y +CONFIG_PXA27x=y +CONFIG_PXA_SHARP_Cxx00=y + +# +# Processor Type +# +CONFIG_CPU_32=y +CONFIG_CPU_XSCALE=y +CONFIG_CPU_32v5=y +CONFIG_CPU_ABRT_EV5T=y +CONFIG_CPU_CACHE_VIVT=y +CONFIG_CPU_TLB_V4WBI=y + +# +# Processor Features +# +CONFIG_ARM_THUMB=y +CONFIG_XSCALE_PMU=y +CONFIG_SHARP_PARAM=y +CONFIG_SHARP_SCOOP=y + +# +# Bus support +# +CONFIG_ISA_DMA_API=y + +# +# PCCARD (PCMCIA/CardBus) support +# +CONFIG_PCCARD=y +# CONFIG_PCMCIA_DEBUG is not set +CONFIG_PCMCIA=y +CONFIG_PCMCIA_LOAD_CIS=y +CONFIG_PCMCIA_IOCTL=y + +# +# PC-card bridges +# +CONFIG_PCMCIA_PXA2XX=y + +# +# Kernel Features +# +CONFIG_PREEMPT=y +# CONFIG_NO_IDLE_HZ is not set +# CONFIG_ARCH_DISCONTIGMEM_ENABLE is not set +CONFIG_SELECT_MEMORY_MODEL=y +CONFIG_FLATMEM_MANUAL=y +# CONFIG_DISCONTIGMEM_MANUAL is not set +# CONFIG_SPARSEMEM_MANUAL is not set +CONFIG_FLATMEM=y +CONFIG_FLAT_NODE_MEM_MAP=y +# CONFIG_SPARSEMEM_STATIC is not set +CONFIG_ALIGNMENT_TRAP=y + +# +# Boot options +# +CONFIG_ZBOOT_ROM_TEXT=0x0 +CONFIG_ZBOOT_ROM_BSS=0x0 +CONFIG_CMDLINE="console=ttyS0,115200n8 console=tty1 noinitrd root=/dev/mtdblock2 rootfstype=jffs2 debug" +# CONFIG_XIP_KERNEL is not set + +# +# Floating point emulation +# + +# +# At least one emulation must be selected +# +CONFIG_FPE_NWFPE=y +# CONFIG_FPE_NWFPE_XP is not set +# CONFIG_FPE_FASTFPE is not set + +# +# Userspace binary formats +# +CONFIG_BINFMT_ELF=y +CONFIG_BINFMT_AOUT=m +CONFIG_BINFMT_MISC=m +# CONFIG_ARTHUR is not set + +# +# Power management options +# +CONFIG_PM=y +CONFIG_APM=y + +# +# Networking +# +CONFIG_NET=y + +# +# Networking options +# +CONFIG_PACKET=y +CONFIG_PACKET_MMAP=y +CONFIG_UNIX=y +CONFIG_XFRM=y +# CONFIG_XFRM_USER is not set +# CONFIG_NET_KEY is not set +CONFIG_INET=y +# CONFIG_IP_MULTICAST is not set +# CONFIG_IP_ADVANCED_ROUTER is not set +CONFIG_IP_FIB_HASH=y +# CONFIG_IP_PNP is not set +# CONFIG_NET_IPIP is not set +# CONFIG_NET_IPGRE is not set +# CONFIG_ARPD is not set +CONFIG_SYN_COOKIES=y +# CONFIG_INET_AH is not set +# CONFIG_INET_ESP is not set +# CONFIG_INET_IPCOMP is not set +# CONFIG_INET_TUNNEL is not set +CONFIG_INET_DIAG=y +CONFIG_INET_TCP_DIAG=y +# CONFIG_TCP_CONG_ADVANCED is not set +CONFIG_TCP_CONG_BIC=y + +# +# IP: Virtual Server Configuration +# +# CONFIG_IP_VS is not set +CONFIG_IPV6=m +# CONFIG_IPV6_PRIVACY is not set +CONFIG_INET6_AH=m +CONFIG_INET6_ESP=m +CONFIG_INET6_IPCOMP=m +CONFIG_INET6_TUNNEL=m +CONFIG_IPV6_TUNNEL=m +CONFIG_NETFILTER=y +# CONFIG_NETFILTER_DEBUG is not set +# CONFIG_NETFILTER_NETLINK is not set + +# +# IP: Netfilter Configuration +# +CONFIG_IP_NF_CONNTRACK=m +# CONFIG_IP_NF_CT_ACCT is not set +# CONFIG_IP_NF_CONNTRACK_MARK is not set +# CONFIG_IP_NF_CONNTRACK_EVENTS is not set +CONFIG_IP_NF_CT_PROTO_SCTP=m +CONFIG_IP_NF_FTP=m +CONFIG_IP_NF_IRC=m +# CONFIG_IP_NF_NETBIOS_NS is not set +CONFIG_IP_NF_TFTP=m +CONFIG_IP_NF_AMANDA=m +# CONFIG_IP_NF_PPTP is not set +CONFIG_IP_NF_QUEUE=m +CONFIG_IP_NF_IPTABLES=m +CONFIG_IP_NF_MATCH_LIMIT=m +CONFIG_IP_NF_MATCH_IPRANGE=m +CONFIG_IP_NF_MATCH_MAC=m +CONFIG_IP_NF_MATCH_PKTTYPE=m +CONFIG_IP_NF_MATCH_MARK=m +CONFIG_IP_NF_MATCH_MULTIPORT=m +CONFIG_IP_NF_MATCH_TOS=m +CONFIG_IP_NF_MATCH_RECENT=m +CONFIG_IP_NF_MATCH_ECN=m +CONFIG_IP_NF_MATCH_DSCP=m +CONFIG_IP_NF_MATCH_AH_ESP=m +CONFIG_IP_NF_MATCH_LENGTH=m +CONFIG_IP_NF_MATCH_TTL=m +CONFIG_IP_NF_MATCH_TCPMSS=m +CONFIG_IP_NF_MATCH_HELPER=m +CONFIG_IP_NF_MATCH_STATE=m +CONFIG_IP_NF_MATCH_CONNTRACK=m +CONFIG_IP_NF_MATCH_OWNER=m +CONFIG_IP_NF_MATCH_ADDRTYPE=m +CONFIG_IP_NF_MATCH_REALM=m +CONFIG_IP_NF_MATCH_SCTP=m +# CONFIG_IP_NF_MATCH_DCCP is not set +CONFIG_IP_NF_MATCH_COMMENT=m +CONFIG_IP_NF_MATCH_HASHLIMIT=m +# CONFIG_IP_NF_MATCH_STRING is not set +CONFIG_IP_NF_FILTER=m +# CONFIG_IP_NF_TARGET_REJECT is not set +CONFIG_IP_NF_TARGET_LOG=m +CONFIG_IP_NF_TARGET_ULOG=m +CONFIG_IP_NF_TARGET_TCPMSS=m +# CONFIG_IP_NF_TARGET_NFQUEUE is not set +CONFIG_IP_NF_NAT=m +CONFIG_IP_NF_NAT_NEEDED=y +# CONFIG_IP_NF_TARGET_MASQUERADE is not set +# CONFIG_IP_NF_TARGET_REDIRECT is not set +# CONFIG_IP_NF_TARGET_NETMAP is not set +# CONFIG_IP_NF_TARGET_SAME is not set +# CONFIG_IP_NF_NAT_SNMP_BASIC is not set +CONFIG_IP_NF_NAT_IRC=m +CONFIG_IP_NF_NAT_FTP=m +CONFIG_IP_NF_NAT_TFTP=m +CONFIG_IP_NF_NAT_AMANDA=m +CONFIG_IP_NF_MANGLE=m +# CONFIG_IP_NF_TARGET_TOS is not set +# CONFIG_IP_NF_TARGET_ECN is not set +# CONFIG_IP_NF_TARGET_DSCP is not set +# CONFIG_IP_NF_TARGET_MARK is not set +# CONFIG_IP_NF_TARGET_CLASSIFY is not set +# CONFIG_IP_NF_TARGET_TTL is not set +CONFIG_IP_NF_RAW=m +# CONFIG_IP_NF_TARGET_NOTRACK is not set +CONFIG_IP_NF_ARPTABLES=m +CONFIG_IP_NF_ARPFILTER=m +CONFIG_IP_NF_ARP_MANGLE=m + +# +# IPv6: Netfilter Configuration (EXPERIMENTAL) +# +CONFIG_IP6_NF_QUEUE=m +CONFIG_IP6_NF_IPTABLES=m +CONFIG_IP6_NF_MATCH_LIMIT=m +CONFIG_IP6_NF_MATCH_MAC=m +CONFIG_IP6_NF_MATCH_RT=m +CONFIG_IP6_NF_MATCH_OPTS=m +CONFIG_IP6_NF_MATCH_FRAG=m +CONFIG_IP6_NF_MATCH_HL=m +CONFIG_IP6_NF_MATCH_MULTIPORT=m +CONFIG_IP6_NF_MATCH_OWNER=m +CONFIG_IP6_NF_MATCH_MARK=m +CONFIG_IP6_NF_MATCH_IPV6HEADER=m +CONFIG_IP6_NF_MATCH_AHESP=m +CONFIG_IP6_NF_MATCH_LENGTH=m +CONFIG_IP6_NF_MATCH_EUI64=m +CONFIG_IP6_NF_FILTER=m +# CONFIG_IP6_NF_TARGET_LOG is not set +# CONFIG_IP6_NF_TARGET_REJECT is not set +# CONFIG_IP6_NF_TARGET_NFQUEUE is not set +CONFIG_IP6_NF_MANGLE=m +# CONFIG_IP6_NF_TARGET_MARK is not set +# CONFIG_IP6_NF_TARGET_HL is not set +CONFIG_IP6_NF_RAW=m + +# +# DCCP Configuration (EXPERIMENTAL) +# +# CONFIG_IP_DCCP is not set + +# +# SCTP Configuration (EXPERIMENTAL) +# +# CONFIG_IP_SCTP is not set +# CONFIG_ATM is not set +# CONFIG_BRIDGE is not set +# CONFIG_VLAN_8021Q is not set +# CONFIG_DECNET is not set +# CONFIG_LLC2 is not set +# CONFIG_IPX is not set +# CONFIG_ATALK is not set +# CONFIG_X25 is not set +# CONFIG_LAPB is not set +# CONFIG_NET_DIVERT is not set +# CONFIG_ECONET is not set +# CONFIG_WAN_ROUTER is not set +# CONFIG_NET_SCHED is not set +CONFIG_NET_CLS_ROUTE=y + +# +# Network testing +# +# CONFIG_NET_PKTGEN is not set +# CONFIG_HAMRADIO is not set +CONFIG_IRDA=m + +# +# IrDA protocols +# +CONFIG_IRLAN=m +CONFIG_IRNET=m +CONFIG_IRCOMM=m +# CONFIG_IRDA_ULTRA is not set + +# +# IrDA options +# +# CONFIG_IRDA_CACHE_LAST_LSAP is not set +# CONFIG_IRDA_FAST_RR is not set +# CONFIG_IRDA_DEBUG is not set + +# +# Infrared-port device drivers +# + +# +# SIR device drivers +# +# CONFIG_IRTTY_SIR is not set + +# +# Dongle support +# + +# +# Old SIR device drivers +# +# CONFIG_IRPORT_SIR is not set + +# +# Old Serial dongle support +# + +# +# FIR device drivers +# +# CONFIG_USB_IRDA is not set +# CONFIG_SIGMATEL_FIR is not set +# CONFIG_NSC_FIR is not set +# CONFIG_WINBOND_FIR is not set +# CONFIG_SMC_IRCC_FIR is not set +# CONFIG_ALI_FIR is not set +# CONFIG_VIA_FIR is not set +CONFIG_BT=m +CONFIG_BT_L2CAP=m +CONFIG_BT_SCO=m +CONFIG_BT_RFCOMM=m +CONFIG_BT_RFCOMM_TTY=y +CONFIG_BT_BNEP=m +CONFIG_BT_BNEP_MC_FILTER=y +CONFIG_BT_BNEP_PROTO_FILTER=y +CONFIG_BT_HIDP=m + +# +# Bluetooth device drivers +# +CONFIG_BT_HCIUSB=m +# CONFIG_BT_HCIUSB_SCO is not set +CONFIG_BT_HCIUART=m +CONFIG_BT_HCIUART_H4=y +CONFIG_BT_HCIUART_BCSP=y +CONFIG_BT_HCIUART_BCSP_TXCRC=y +CONFIG_BT_HCIBCM203X=m +CONFIG_BT_HCIBPA10X=m +CONFIG_BT_HCIBFUSB=m +CONFIG_BT_HCIDTL1=m +CONFIG_BT_HCIBT3C=m +CONFIG_BT_HCIBLUECARD=m +CONFIG_BT_HCIBTUART=m +CONFIG_BT_HCIVHCI=m +CONFIG_IEEE80211=m +# CONFIG_IEEE80211_DEBUG is not set +CONFIG_IEEE80211_CRYPT_WEP=m +# CONFIG_IEEE80211_CRYPT_CCMP is not set +# CONFIG_IEEE80211_CRYPT_TKIP is not set + +# +# Device Drivers +# + +# +# Generic Driver Options +# +CONFIG_STANDALONE=y +CONFIG_PREVENT_FIRMWARE_BUILD=y +CONFIG_FW_LOADER=y +# CONFIG_DEBUG_DRIVER is not set + +# +# Memory Technology Devices (MTD) +# +CONFIG_MTD=y +# CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_CONCAT is not set +CONFIG_MTD_PARTITIONS=y +# CONFIG_MTD_REDBOOT_PARTS is not set +CONFIG_MTD_CMDLINE_PARTS=y +# CONFIG_MTD_AFS_PARTS is not set + +# +# User Modules And Translation Layers +# +CONFIG_MTD_CHAR=y +CONFIG_MTD_BLOCK=y +# CONFIG_FTL is not set +# CONFIG_NFTL is not set +# CONFIG_INFTL is not set + +# +# RAM/ROM/Flash chip drivers +# +# CONFIG_MTD_CFI is not set +# CONFIG_MTD_JEDECPROBE is not set +CONFIG_MTD_MAP_BANK_WIDTH_1=y +CONFIG_MTD_MAP_BANK_WIDTH_2=y +CONFIG_MTD_MAP_BANK_WIDTH_4=y +# CONFIG_MTD_MAP_BANK_WIDTH_8 is not set +# CONFIG_MTD_MAP_BANK_WIDTH_16 is not set +# CONFIG_MTD_MAP_BANK_WIDTH_32 is not set +CONFIG_MTD_CFI_I1=y +CONFIG_MTD_CFI_I2=y +# CONFIG_MTD_CFI_I4 is not set +# CONFIG_MTD_CFI_I8 is not set +# CONFIG_MTD_RAM is not set +CONFIG_MTD_ROM=y +# CONFIG_MTD_ABSENT is not set + +# +# Mapping drivers for chip access +# +CONFIG_MTD_COMPLEX_MAPPINGS=y +CONFIG_MTD_SHARP_SL=y +# CONFIG_MTD_PLATRAM is not set + +# +# Self-contained MTD device drivers +# +# CONFIG_MTD_SLRAM is not set +# CONFIG_MTD_PHRAM is not set +# CONFIG_MTD_MTDRAM is not set +# CONFIG_MTD_BLKMTD is not set +# CONFIG_MTD_BLOCK2MTD is not set + +# +# Disk-On-Chip Device Drivers +# +# CONFIG_MTD_DOC2000 is not set +# CONFIG_MTD_DOC2001 is not set +# CONFIG_MTD_DOC2001PLUS is not set + +# +# NAND Flash Device Drivers +# +CONFIG_MTD_NAND=y +CONFIG_MTD_NAND_VERIFY_WRITE=y +# CONFIG_MTD_NAND_H1900 is not set +CONFIG_MTD_NAND_IDS=y +# CONFIG_MTD_NAND_DISKONCHIP is not set +CONFIG_MTD_NAND_SHARPSL=y +# CONFIG_MTD_NAND_NANDSIM is not set + +# +# Parallel port support +# +# CONFIG_PARPORT is not set + +# +# Plug and Play support +# + +# +# Block devices +# +# CONFIG_BLK_DEV_COW_COMMON is not set +CONFIG_BLK_DEV_LOOP=y +# CONFIG_BLK_DEV_CRYPTOLOOP is not set +# CONFIG_BLK_DEV_NBD is not set +# CONFIG_BLK_DEV_UB is not set +# CONFIG_BLK_DEV_RAM is not set +CONFIG_BLK_DEV_RAM_COUNT=16 +# CONFIG_CDROM_PKTCDVD is not set + +# +# IO Schedulers +# +CONFIG_IOSCHED_NOOP=y +CONFIG_IOSCHED_AS=y +CONFIG_IOSCHED_DEADLINE=y +CONFIG_IOSCHED_CFQ=y +# CONFIG_ATA_OVER_ETH is not set + +# +# ATA/ATAPI/MFM/RLL support +# +CONFIG_IDE=y +CONFIG_BLK_DEV_IDE=y + +# +# Please see Documentation/ide.txt for help/info on IDE drives +# +# CONFIG_BLK_DEV_IDE_SATA is not set +CONFIG_BLK_DEV_IDEDISK=y +# CONFIG_IDEDISK_MULTI_MODE is not set +CONFIG_BLK_DEV_IDECS=y +# CONFIG_BLK_DEV_IDECD is not set +# CONFIG_BLK_DEV_IDETAPE is not set +# CONFIG_BLK_DEV_IDEFLOPPY is not set +# CONFIG_BLK_DEV_IDESCSI is not set +# CONFIG_IDE_TASK_IOCTL is not set + +# +# IDE chipset support/bugfixes +# +CONFIG_IDE_GENERIC=y +# CONFIG_IDE_ARM is not set +# CONFIG_BLK_DEV_IDEDMA is not set +# CONFIG_IDEDMA_AUTO is not set +# CONFIG_BLK_DEV_HD is not set + +# +# SCSI device support +# +# CONFIG_RAID_ATTRS is not set +CONFIG_SCSI=m +CONFIG_SCSI_PROC_FS=y + +# +# SCSI support type (disk, tape, CD-ROM) +# +CONFIG_BLK_DEV_SD=m +CONFIG_CHR_DEV_ST=m +CONFIG_CHR_DEV_OSST=m +CONFIG_BLK_DEV_SR=m +# CONFIG_BLK_DEV_SR_VENDOR is not set +CONFIG_CHR_DEV_SG=m +# CONFIG_CHR_DEV_SCH is not set + +# +# Some SCSI devices (e.g. CD jukebox) support multiple LUNs +# +CONFIG_SCSI_MULTI_LUN=y +# CONFIG_SCSI_CONSTANTS is not set +# CONFIG_SCSI_LOGGING is not set + +# +# SCSI Transport Attributes +# +# CONFIG_SCSI_SPI_ATTRS is not set +# CONFIG_SCSI_FC_ATTRS is not set +# CONFIG_SCSI_ISCSI_ATTRS is not set +# CONFIG_SCSI_SAS_ATTRS is not set + +# +# SCSI low-level drivers +# +# CONFIG_SCSI_SATA is not set +# CONFIG_SCSI_DEBUG is not set + +# +# PCMCIA SCSI adapter support +# +# CONFIG_PCMCIA_AHA152X is not set +# CONFIG_PCMCIA_FDOMAIN is not set +# CONFIG_PCMCIA_NINJA_SCSI is not set +# CONFIG_PCMCIA_QLOGIC is not set +# CONFIG_PCMCIA_SYM53C500 is not set + +# +# Multi-device support (RAID and LVM) +# +# CONFIG_MD is not set + +# +# Fusion MPT device support +# +# CONFIG_FUSION is not set + +# +# IEEE 1394 (FireWire) support +# + +# +# I2O device support +# + +# +# Network device support +# +CONFIG_NETDEVICES=y +# CONFIG_DUMMY is not set +# CONFIG_BONDING is not set +# CONFIG_EQUALIZER is not set +# CONFIG_TUN is not set + +# +# PHY device support +# +# CONFIG_PHYLIB is not set + +# +# Ethernet (10 or 100Mbit) +# +CONFIG_NET_ETHERNET=y +CONFIG_MII=m +# CONFIG_SMC91X is not set +# CONFIG_DM9000 is not set + +# +# Ethernet (1000 Mbit) +# + +# +# Ethernet (10000 Mbit) +# + +# +# Token Ring devices +# + +# +# Wireless LAN (non-hamradio) +# +CONFIG_NET_RADIO=y + +# +# Obsolete Wireless cards support (pre-802.11) +# +# CONFIG_STRIP is not set +# CONFIG_PCMCIA_WAVELAN is not set +# CONFIG_PCMCIA_NETWAVE is not set + +# +# Wireless 802.11 Frequency Hopping cards support +# +# CONFIG_PCMCIA_RAYCS is not set + +# +# Wireless 802.11b ISA/PCI cards support +# +CONFIG_HERMES=m +# CONFIG_ATMEL is not set + +# +# Wireless 802.11b Pcmcia/Cardbus cards support +# +CONFIG_PCMCIA_HERMES=m +CONFIG_PCMCIA_SPECTRUM=m +# CONFIG_AIRO_CS is not set +# CONFIG_PCMCIA_WL3501 is not set +CONFIG_HOSTAP=m +CONFIG_HOSTAP_FIRMWARE=y +CONFIG_HOSTAP_CS=m +CONFIG_NET_WIRELESS=y + +# +# PCMCIA network device support +# +CONFIG_NET_PCMCIA=y +# CONFIG_PCMCIA_3C589 is not set +# CONFIG_PCMCIA_3C574 is not set +# CONFIG_PCMCIA_FMVJ18X is not set +CONFIG_PCMCIA_PCNET=m +# CONFIG_PCMCIA_NMCLAN is not set +# CONFIG_PCMCIA_SMC91C92 is not set +# CONFIG_PCMCIA_XIRC2PS is not set +# CONFIG_PCMCIA_AXNET is not set + +# +# Wan interfaces +# +# CONFIG_WAN is not set +CONFIG_PPP=m +# CONFIG_PPP_MULTILINK is not set +# CONFIG_PPP_FILTER is not set +CONFIG_PPP_ASYNC=m +# CONFIG_PPP_SYNC_TTY is not set +# CONFIG_PPP_DEFLATE is not set +CONFIG_PPP_BSDCOMP=m +# CONFIG_PPPOE is not set +# CONFIG_SLIP is not set +# CONFIG_SHAPER is not set +# CONFIG_NETCONSOLE is not set +# CONFIG_NETPOLL is not set +# CONFIG_NET_POLL_CONTROLLER is not set + +# +# ISDN subsystem +# +# CONFIG_ISDN is not set + +# +# Input device support +# +CONFIG_INPUT=y + +# +# Userland interfaces +# +# CONFIG_INPUT_MOUSEDEV is not set +# CONFIG_INPUT_JOYDEV is not set +# CONFIG_INPUT_TSDEV is not set +CONFIG_INPUT_EVDEV=y +# CONFIG_INPUT_EVBUG is not set + +# +# Input Device Drivers +# +CONFIG_INPUT_KEYBOARD=y +# CONFIG_KEYBOARD_ATKBD is not set +# CONFIG_KEYBOARD_SUNKBD is not set +# CONFIG_KEYBOARD_LKKBD is not set +# CONFIG_KEYBOARD_XTKBD is not set +# CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_KEYBOARD_CORGI is not set +CONFIG_KEYBOARD_SPITZ=y +# CONFIG_INPUT_MOUSE is not set +# CONFIG_INPUT_JOYSTICK is not set +CONFIG_INPUT_TOUCHSCREEN=y +CONFIG_TOUCHSCREEN_CORGI=y +# CONFIG_TOUCHSCREEN_GUNZE is not set +# CONFIG_TOUCHSCREEN_ELO is not set +# CONFIG_TOUCHSCREEN_MTOUCH is not set +# CONFIG_TOUCHSCREEN_MK712 is not set +CONFIG_INPUT_MISC=y +CONFIG_INPUT_UINPUT=m + +# +# Hardware I/O ports +# +# CONFIG_SERIO is not set +# CONFIG_GAMEPORT is not set + +# +# Character devices +# +CONFIG_VT=y +CONFIG_VT_CONSOLE=y +CONFIG_HW_CONSOLE=y +# CONFIG_SERIAL_NONSTANDARD is not set + +# +# Serial drivers +# +CONFIG_SERIAL_8250=m +CONFIG_SERIAL_8250_CS=m +CONFIG_SERIAL_8250_NR_UARTS=4 +# CONFIG_SERIAL_8250_EXTENDED is not set + +# +# Non-8250 serial port support +# +CONFIG_SERIAL_PXA=y +CONFIG_SERIAL_PXA_CONSOLE=y +CONFIG_SERIAL_CORE=y +CONFIG_SERIAL_CORE_CONSOLE=y +CONFIG_UNIX98_PTYS=y +# CONFIG_LEGACY_PTYS is not set + +# +# IPMI +# +# CONFIG_IPMI_HANDLER is not set + +# +# Watchdog Cards +# +# CONFIG_WATCHDOG is not set +# CONFIG_NVRAM is not set +# CONFIG_RTC is not set +# CONFIG_DTLK is not set +# CONFIG_R3964 is not set + +# +# Ftape, the floppy tape device driver +# + +# +# PCMCIA character devices +# +# CONFIG_SYNCLINK_CS is not set +# CONFIG_RAW_DRIVER is not set + +# +# TPM devices +# + +# +# I2C support +# +# CONFIG_I2C is not set + +# +# Hardware Monitoring support +# +CONFIG_HWMON=y +# CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Misc devices +# + +# +# Multimedia Capabilities Port drivers +# + +# +# Multimedia devices +# +# CONFIG_VIDEO_DEV is not set + +# +# Digital Video Broadcasting Devices +# +# CONFIG_DVB is not set + +# +# Graphics support +# +CONFIG_FB=y +CONFIG_FB_CFB_FILLRECT=y +CONFIG_FB_CFB_COPYAREA=y +CONFIG_FB_CFB_IMAGEBLIT=y +CONFIG_FB_SOFT_CURSOR=y +# CONFIG_FB_MACMODES is not set +# CONFIG_FB_MODE_HELPERS is not set +# CONFIG_FB_TILEBLITTING is not set +CONFIG_FB_PXA=y +# CONFIG_FB_W100 is not set +# CONFIG_FB_PXA_PARAMETERS is not set +# CONFIG_FB_S1D13XXX is not set +# CONFIG_FB_VIRTUAL is not set + +# +# Console display driver support +# +# CONFIG_VGA_CONSOLE is not set +CONFIG_DUMMY_CONSOLE=y +CONFIG_FRAMEBUFFER_CONSOLE=y +CONFIG_FONTS=y +CONFIG_FONT_8x8=y +CONFIG_FONT_8x16=y +# CONFIG_FONT_6x11 is not set +# CONFIG_FONT_7x14 is not set +# CONFIG_FONT_PEARL_8x8 is not set +# CONFIG_FONT_ACORN_8x8 is not set +# CONFIG_FONT_MINI_4x6 is not set +# CONFIG_FONT_SUN8x16 is not set +# CONFIG_FONT_SUN12x22 is not set +# CONFIG_FONT_10x18 is not set + +# +# Logo configuration +# +# CONFIG_LOGO is not set +CONFIG_BACKLIGHT_LCD_SUPPORT=y +CONFIG_BACKLIGHT_CLASS_DEVICE=y +CONFIG_BACKLIGHT_DEVICE=y +CONFIG_LCD_CLASS_DEVICE=y +CONFIG_LCD_DEVICE=y +CONFIG_BACKLIGHT_CORGI=y + +# +# Sound +# +# CONFIG_SOUND is not set + +# +# USB support +# +CONFIG_USB_ARCH_HAS_HCD=y +CONFIG_USB_ARCH_HAS_OHCI=y +CONFIG_USB=m +# CONFIG_USB_DEBUG is not set + +# +# Miscellaneous USB options +# +CONFIG_USB_DEVICEFS=y +# CONFIG_USB_BANDWIDTH is not set +# CONFIG_USB_DYNAMIC_MINORS is not set +# CONFIG_USB_SUSPEND is not set +# CONFIG_USB_OTG is not set + +# +# USB Host Controller Drivers +# +# CONFIG_USB_ISP116X_HCD is not set +CONFIG_USB_OHCI_HCD=m +# CONFIG_USB_OHCI_BIG_ENDIAN is not set +CONFIG_USB_OHCI_LITTLE_ENDIAN=y +CONFIG_USB_SL811_HCD=m +CONFIG_USB_SL811_CS=m + +# +# USB Device Class drivers +# + +# +# USB Bluetooth TTY can only be used with disabled Bluetooth subsystem +# +CONFIG_USB_ACM=m +CONFIG_USB_PRINTER=m + +# +# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' may also be needed; see USB_STORAGE Help for more information +# +CONFIG_USB_STORAGE=m +# CONFIG_USB_STORAGE_DEBUG is not set +# CONFIG_USB_STORAGE_DATAFAB is not set +# CONFIG_USB_STORAGE_FREECOM is not set +# CONFIG_USB_STORAGE_ISD200 is not set +# CONFIG_USB_STORAGE_DPCM is not set +# CONFIG_USB_STORAGE_USBAT is not set +# CONFIG_USB_STORAGE_SDDR09 is not set +# CONFIG_USB_STORAGE_SDDR55 is not set +# CONFIG_USB_STORAGE_JUMPSHOT is not set +# CONFIG_USB_STORAGE_ONETOUCH is not set + +# +# USB Input Devices +# +CONFIG_USB_HID=m +CONFIG_USB_HIDINPUT=y +# CONFIG_HID_FF is not set +# CONFIG_USB_HIDDEV is not set + +# +# USB HID Boot Protocol drivers +# +CONFIG_USB_KBD=m +CONFIG_USB_MOUSE=m +CONFIG_USB_AIPTEK=m +CONFIG_USB_WACOM=m +# CONFIG_USB_ACECAD is not set +CONFIG_USB_KBTAB=m +CONFIG_USB_POWERMATE=m +CONFIG_USB_MTOUCH=m +# CONFIG_USB_ITMTOUCH is not set +CONFIG_USB_EGALAX=m +# CONFIG_USB_YEALINK is not set +CONFIG_USB_XPAD=m +CONFIG_USB_ATI_REMOTE=m +# CONFIG_USB_KEYSPAN_REMOTE is not set +# CONFIG_USB_APPLETOUCH is not set + +# +# USB Imaging devices +# +CONFIG_USB_MDC800=m +CONFIG_USB_MICROTEK=m + +# +# USB Multimedia devices +# +CONFIG_USB_DABUSB=m + +# +# Video4Linux support is needed for USB Multimedia device support +# + +# +# USB Network Adapters +# +CONFIG_USB_CATC=m +CONFIG_USB_KAWETH=m +CONFIG_USB_PEGASUS=m +CONFIG_USB_RTL8150=m +CONFIG_USB_USBNET=m +CONFIG_USB_NET_AX8817X=m +CONFIG_USB_NET_CDCETHER=m +# CONFIG_USB_NET_GL620A is not set +CONFIG_USB_NET_NET1080=m +# CONFIG_USB_NET_PLUSB is not set +# CONFIG_USB_NET_RNDIS_HOST is not set +# CONFIG_USB_NET_CDC_SUBSET is not set +CONFIG_USB_NET_ZAURUS=m +# CONFIG_USB_ZD1201 is not set +CONFIG_USB_MON=y + +# +# USB port drivers +# + +# +# USB Serial Converter support +# +CONFIG_USB_SERIAL=m +CONFIG_USB_SERIAL_GENERIC=y +# CONFIG_USB_SERIAL_AIRPRIME is not set +CONFIG_USB_SERIAL_BELKIN=m +# CONFIG_USB_SERIAL_WHITEHEAT is not set +CONFIG_USB_SERIAL_DIGI_ACCELEPORT=m +# CONFIG_USB_SERIAL_CP2101 is not set +CONFIG_USB_SERIAL_CYPRESS_M8=m +CONFIG_USB_SERIAL_EMPEG=m +CONFIG_USB_SERIAL_FTDI_SIO=m +CONFIG_USB_SERIAL_VISOR=m +CONFIG_USB_SERIAL_IPAQ=m +CONFIG_USB_SERIAL_IR=m +CONFIG_USB_SERIAL_EDGEPORT=m +CONFIG_USB_SERIAL_EDGEPORT_TI=m +CONFIG_USB_SERIAL_GARMIN=m +CONFIG_USB_SERIAL_IPW=m +CONFIG_USB_SERIAL_KEYSPAN_PDA=m +CONFIG_USB_SERIAL_KEYSPAN=m +# CONFIG_USB_SERIAL_KEYSPAN_MPR is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA28 is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA28X is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA28XA is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA28XB is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA19 is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA18X is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA19W is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA19QW is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA19QI is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA49W is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA49WLC is not set +CONFIG_USB_SERIAL_KLSI=m +CONFIG_USB_SERIAL_KOBIL_SCT=m +CONFIG_USB_SERIAL_MCT_U232=m +CONFIG_USB_SERIAL_PL2303=m +# CONFIG_USB_SERIAL_HP4X is not set +CONFIG_USB_SERIAL_SAFE=m +# CONFIG_USB_SERIAL_SAFE_PADDED is not set +CONFIG_USB_SERIAL_TI=m +CONFIG_USB_SERIAL_CYBERJACK=m +CONFIG_USB_SERIAL_XIRCOM=m +# CONFIG_USB_SERIAL_OPTION is not set +CONFIG_USB_SERIAL_OMNINET=m +CONFIG_USB_EZUSB=y + +# +# USB Miscellaneous drivers +# +CONFIG_USB_EMI62=m +CONFIG_USB_EMI26=m +CONFIG_USB_AUERSWALD=m +CONFIG_USB_RIO500=m +CONFIG_USB_LEGOTOWER=m +CONFIG_USB_LCD=m +CONFIG_USB_LED=m +CONFIG_USB_CYTHERM=m +CONFIG_USB_PHIDGETKIT=m +CONFIG_USB_PHIDGETSERVO=m +CONFIG_USB_IDMOUSE=m +# CONFIG_USB_LD is not set +# CONFIG_USB_TEST is not set + +# +# USB DSL modem support +# + +# +# USB Gadget Support +# +CONFIG_USB_GADGET=m +# CONFIG_USB_GADGET_DEBUG_FILES is not set +CONFIG_USB_GADGET_SELECTED=y +# CONFIG_USB_GADGET_NET2280 is not set +# CONFIG_USB_GADGET_PXA2XX is not set +# CONFIG_USB_GADGET_GOKU is not set +# CONFIG_USB_GADGET_LH7A40X is not set +# CONFIG_USB_GADGET_OMAP is not set +CONFIG_USB_GADGET_DUMMY_HCD=y +CONFIG_USB_DUMMY_HCD=m +CONFIG_USB_GADGET_DUALSPEED=y +CONFIG_USB_ZERO=m +CONFIG_USB_ETH=m +CONFIG_USB_ETH_RNDIS=y +CONFIG_USB_GADGETFS=m +CONFIG_USB_FILE_STORAGE=m +# CONFIG_USB_FILE_STORAGE_TEST is not set +CONFIG_USB_G_SERIAL=m + +# +# MMC/SD Card support +# +CONFIG_MMC=y +# CONFIG_MMC_DEBUG is not set +CONFIG_MMC_BLOCK=y +CONFIG_MMC_PXA=y +# CONFIG_MMC_WBSD is not set + +# +# File systems +# +CONFIG_EXT2_FS=y +CONFIG_EXT2_FS_XATTR=y +CONFIG_EXT2_FS_POSIX_ACL=y +CONFIG_EXT2_FS_SECURITY=y +# CONFIG_EXT2_FS_XIP is not set +CONFIG_EXT3_FS=y +# CONFIG_EXT3_FS_XATTR is not set +CONFIG_JBD=y +# CONFIG_JBD_DEBUG is not set +CONFIG_FS_MBCACHE=y +# CONFIG_REISERFS_FS is not set +# CONFIG_JFS_FS is not set +CONFIG_FS_POSIX_ACL=y +# CONFIG_XFS_FS is not set +# CONFIG_MINIX_FS is not set +# CONFIG_ROMFS_FS is not set +CONFIG_INOTIFY=y +# CONFIG_QUOTA is not set +CONFIG_DNOTIFY=y +# CONFIG_AUTOFS_FS is not set +# CONFIG_AUTOFS4_FS is not set +# CONFIG_FUSE_FS is not set + +# +# CD-ROM/DVD Filesystems +# +# CONFIG_ISO9660_FS is not set +# CONFIG_UDF_FS is not set + +# +# DOS/FAT/NT Filesystems +# +CONFIG_FAT_FS=y +CONFIG_MSDOS_FS=y +CONFIG_VFAT_FS=y +CONFIG_FAT_DEFAULT_CODEPAGE=437 +CONFIG_FAT_DEFAULT_IOCHARSET="iso8859-1" +# CONFIG_NTFS_FS is not set + +# +# Pseudo filesystems +# +CONFIG_PROC_FS=y +CONFIG_SYSFS=y +CONFIG_TMPFS=y +# CONFIG_HUGETLB_PAGE is not set +CONFIG_RAMFS=y +# CONFIG_RELAYFS_FS is not set + +# +# Miscellaneous filesystems +# +# CONFIG_ADFS_FS is not set +# CONFIG_AFFS_FS is not set +# CONFIG_HFS_FS is not set +# CONFIG_HFSPLUS_FS is not set +# CONFIG_BEFS_FS is not set +# CONFIG_BFS_FS is not set +# CONFIG_EFS_FS is not set +# CONFIG_JFFS_FS is not set +CONFIG_JFFS2_FS=y +CONFIG_JFFS2_FS_DEBUG=0 +CONFIG_JFFS2_FS_WRITEBUFFER=y +CONFIG_JFFS2_COMPRESSION_OPTIONS=y +CONFIG_JFFS2_ZLIB=y +CONFIG_JFFS2_RTIME=y +CONFIG_JFFS2_RUBIN=y +# CONFIG_JFFS2_CMODE_NONE is not set +CONFIG_JFFS2_CMODE_PRIORITY=y +# CONFIG_JFFS2_CMODE_SIZE is not set +CONFIG_CRAMFS=m +# CONFIG_VXFS_FS is not set +# CONFIG_HPFS_FS is not set +# CONFIG_QNX4FS_FS is not set +# CONFIG_SYSV_FS is not set +# CONFIG_UFS_FS is not set + +# +# Network File Systems +# +CONFIG_NFS_FS=m +CONFIG_NFS_V3=y +# CONFIG_NFS_V3_ACL is not set +CONFIG_NFS_V4=y +# CONFIG_NFS_DIRECTIO is not set +# CONFIG_NFSD is not set +CONFIG_LOCKD=m +CONFIG_LOCKD_V4=y +CONFIG_NFS_COMMON=y +CONFIG_SUNRPC=m +CONFIG_SUNRPC_GSS=m +CONFIG_RPCSEC_GSS_KRB5=m +# CONFIG_RPCSEC_GSS_SPKM3 is not set +CONFIG_SMB_FS=m +CONFIG_SMB_NLS_DEFAULT=y +CONFIG_SMB_NLS_REMOTE="cp437" +# CONFIG_CIFS is not set +# CONFIG_NCP_FS is not set +# CONFIG_CODA_FS is not set +# CONFIG_AFS_FS is not set +# CONFIG_9P_FS is not set + +# +# Partition Types +# +CONFIG_PARTITION_ADVANCED=y +# CONFIG_ACORN_PARTITION is not set +# CONFIG_OSF_PARTITION is not set +# CONFIG_AMIGA_PARTITION is not set +# CONFIG_ATARI_PARTITION is not set +# CONFIG_MAC_PARTITION is not set +CONFIG_MSDOS_PARTITION=y +# CONFIG_BSD_DISKLABEL is not set +# CONFIG_MINIX_SUBPARTITION is not set +# CONFIG_SOLARIS_X86_PARTITION is not set +# CONFIG_UNIXWARE_DISKLABEL is not set +# CONFIG_LDM_PARTITION is not set +# CONFIG_SGI_PARTITION is not set +# CONFIG_ULTRIX_PARTITION is not set +# CONFIG_SUN_PARTITION is not set +# CONFIG_EFI_PARTITION is not set + +# +# Native Language Support +# +CONFIG_NLS=y +CONFIG_NLS_DEFAULT="cp437" +CONFIG_NLS_CODEPAGE_437=y +# CONFIG_NLS_CODEPAGE_737 is not set +# CONFIG_NLS_CODEPAGE_775 is not set +# CONFIG_NLS_CODEPAGE_850 is not set +# CONFIG_NLS_CODEPAGE_852 is not set +# CONFIG_NLS_CODEPAGE_855 is not set +# CONFIG_NLS_CODEPAGE_857 is not set +# CONFIG_NLS_CODEPAGE_860 is not set +# CONFIG_NLS_CODEPAGE_861 is not set +# CONFIG_NLS_CODEPAGE_862 is not set +# CONFIG_NLS_CODEPAGE_863 is not set +# CONFIG_NLS_CODEPAGE_864 is not set +# CONFIG_NLS_CODEPAGE_865 is not set +# CONFIG_NLS_CODEPAGE_866 is not set +# CONFIG_NLS_CODEPAGE_869 is not set +# CONFIG_NLS_CODEPAGE_936 is not set +# CONFIG_NLS_CODEPAGE_950 is not set +# CONFIG_NLS_CODEPAGE_932 is not set +# CONFIG_NLS_CODEPAGE_949 is not set +# CONFIG_NLS_CODEPAGE_874 is not set +# CONFIG_NLS_ISO8859_8 is not set +# CONFIG_NLS_CODEPAGE_1250 is not set +# CONFIG_NLS_CODEPAGE_1251 is not set +# CONFIG_NLS_ASCII is not set +CONFIG_NLS_ISO8859_1=y +# CONFIG_NLS_ISO8859_2 is not set +# CONFIG_NLS_ISO8859_3 is not set +# CONFIG_NLS_ISO8859_4 is not set +# CONFIG_NLS_ISO8859_5 is not set +# CONFIG_NLS_ISO8859_6 is not set +# CONFIG_NLS_ISO8859_7 is not set +# CONFIG_NLS_ISO8859_9 is not set +# CONFIG_NLS_ISO8859_13 is not set +# CONFIG_NLS_ISO8859_14 is not set +# CONFIG_NLS_ISO8859_15 is not set +# CONFIG_NLS_KOI8_R is not set +# CONFIG_NLS_KOI8_U is not set +CONFIG_NLS_UTF8=y + +# +# Profiling support +# +CONFIG_PROFILING=y +CONFIG_OPROFILE=m + +# +# Kernel hacking +# +# CONFIG_PRINTK_TIME is not set +CONFIG_DEBUG_KERNEL=y +CONFIG_MAGIC_SYSRQ=y +CONFIG_LOG_BUF_SHIFT=14 +CONFIG_DETECT_SOFTLOCKUP=y +# CONFIG_SCHEDSTATS is not set +# CONFIG_DEBUG_SLAB is not set +# CONFIG_DEBUG_PREEMPT is not set +# CONFIG_DEBUG_SPINLOCK is not set +# CONFIG_DEBUG_SPINLOCK_SLEEP is not set +# CONFIG_DEBUG_KOBJECT is not set +CONFIG_DEBUG_BUGVERBOSE=y +# CONFIG_DEBUG_INFO is not set +# CONFIG_DEBUG_FS is not set +CONFIG_FRAME_POINTER=y +# CONFIG_DEBUG_USER is not set +# CONFIG_DEBUG_WAITQ is not set +CONFIG_DEBUG_ERRORS=y +CONFIG_DEBUG_LL=y +# CONFIG_DEBUG_ICEDCC is not set + +# +# Security options +# +# CONFIG_KEYS is not set +# CONFIG_SECURITY is not set + +# +# Cryptographic options +# +CONFIG_CRYPTO=y +CONFIG_CRYPTO_HMAC=y +CONFIG_CRYPTO_NULL=m +CONFIG_CRYPTO_MD4=m +CONFIG_CRYPTO_MD5=m +CONFIG_CRYPTO_SHA1=m +CONFIG_CRYPTO_SHA256=m +CONFIG_CRYPTO_SHA512=m +CONFIG_CRYPTO_WP512=m +# CONFIG_CRYPTO_TGR192 is not set +CONFIG_CRYPTO_DES=m +CONFIG_CRYPTO_BLOWFISH=m +CONFIG_CRYPTO_TWOFISH=m +CONFIG_CRYPTO_SERPENT=m +CONFIG_CRYPTO_AES=m +CONFIG_CRYPTO_CAST5=m +CONFIG_CRYPTO_CAST6=m +CONFIG_CRYPTO_TEA=m +CONFIG_CRYPTO_ARC4=m +CONFIG_CRYPTO_KHAZAD=m +CONFIG_CRYPTO_ANUBIS=m +CONFIG_CRYPTO_DEFLATE=m +CONFIG_CRYPTO_MICHAEL_MIC=m +CONFIG_CRYPTO_CRC32C=m +CONFIG_CRYPTO_TEST=m + +# +# Hardware crypto devices +# + +# +# Library routines +# +CONFIG_CRC_CCITT=y +# CONFIG_CRC16 is not set +CONFIG_CRC32=y +CONFIG_LIBCRC32C=m +CONFIG_ZLIB_INFLATE=y +CONFIG_ZLIB_DEFLATE=y -- cgit v1.2.3 From b0bdc7be78931dfbfaec8bd0da44a5f4e158ca8f Mon Sep 17 00:00:00 2001 From: Vincent Sanders Date: Mon, 10 Oct 2005 18:24:07 +0100 Subject: [ARM] 2966/1: defconfig for the ARM Poodle platform Patch from Vincent Sanders Add a defconfig for the ARM Poodle Zarus platform Signed-off-by: Richard Purdie Signed-off-by: Vincent Sanders Signed-off-by: Russell King --- arch/arm/configs/poodle_defconfig | 1015 +++++++++++++++++++++++++++++++++++++ 1 file changed, 1015 insertions(+) create mode 100644 arch/arm/configs/poodle_defconfig diff --git a/arch/arm/configs/poodle_defconfig b/arch/arm/configs/poodle_defconfig new file mode 100644 index 00000000000..72822907759 --- /dev/null +++ b/arch/arm/configs/poodle_defconfig @@ -0,0 +1,1015 @@ +# +# Automatically generated make config: don't edit +# Linux kernel version: 2.6.14-rc3 +# Sun Oct 9 17:04:29 2005 +# +CONFIG_ARM=y +CONFIG_MMU=y +CONFIG_UID16=y +CONFIG_RWSEM_GENERIC_SPINLOCK=y +CONFIG_GENERIC_CALIBRATE_DELAY=y + +# +# Code maturity level options +# +CONFIG_EXPERIMENTAL=y +CONFIG_CLEAN_COMPILE=y +CONFIG_BROKEN_ON_SMP=y +CONFIG_LOCK_KERNEL=y +CONFIG_INIT_ENV_ARG_LIMIT=32 + +# +# General setup +# +CONFIG_LOCALVERSION="" +CONFIG_LOCALVERSION_AUTO=y +CONFIG_SWAP=y +CONFIG_SYSVIPC=y +# CONFIG_POSIX_MQUEUE is not set +CONFIG_BSD_PROCESS_ACCT=y +# CONFIG_BSD_PROCESS_ACCT_V3 is not set +CONFIG_SYSCTL=y +# CONFIG_AUDIT is not set +CONFIG_HOTPLUG=y +CONFIG_KOBJECT_UEVENT=y +# CONFIG_IKCONFIG is not set +CONFIG_INITRAMFS_SOURCE="" +CONFIG_EMBEDDED=y +CONFIG_KALLSYMS=y +# CONFIG_KALLSYMS_ALL is not set +# CONFIG_KALLSYMS_EXTRA_PASS is not set +CONFIG_PRINTK=y +CONFIG_BUG=y +CONFIG_BASE_FULL=y +CONFIG_FUTEX=y +CONFIG_EPOLL=y +# CONFIG_CC_OPTIMIZE_FOR_SIZE is not set +CONFIG_SHMEM=y +CONFIG_CC_ALIGN_FUNCTIONS=0 +CONFIG_CC_ALIGN_LABELS=0 +CONFIG_CC_ALIGN_LOOPS=0 +CONFIG_CC_ALIGN_JUMPS=0 +# CONFIG_TINY_SHMEM is not set +CONFIG_BASE_SMALL=0 + +# +# Loadable module support +# +CONFIG_MODULES=y +CONFIG_MODULE_UNLOAD=y +CONFIG_MODULE_FORCE_UNLOAD=y +CONFIG_OBSOLETE_MODPARM=y +CONFIG_MODVERSIONS=y +# CONFIG_MODULE_SRCVERSION_ALL is not set +CONFIG_KMOD=y + +# +# System Type +# +# CONFIG_ARCH_CLPS7500 is not set +# CONFIG_ARCH_CLPS711X is not set +# CONFIG_ARCH_CO285 is not set +# CONFIG_ARCH_EBSA110 is not set +# CONFIG_ARCH_CAMELOT is not set +# CONFIG_ARCH_FOOTBRIDGE is not set +# CONFIG_ARCH_INTEGRATOR is not set +# CONFIG_ARCH_IOP3XX is not set +# CONFIG_ARCH_IXP4XX is not set +# CONFIG_ARCH_IXP2000 is not set +# CONFIG_ARCH_L7200 is not set +CONFIG_ARCH_PXA=y +# CONFIG_ARCH_RPC is not set +# CONFIG_ARCH_SA1100 is not set +# CONFIG_ARCH_S3C2410 is not set +# CONFIG_ARCH_SHARK is not set +# CONFIG_ARCH_LH7A40X is not set +# CONFIG_ARCH_OMAP is not set +# CONFIG_ARCH_VERSATILE is not set +# CONFIG_ARCH_IMX is not set +# CONFIG_ARCH_H720X is not set +# CONFIG_ARCH_AAEC2000 is not set + +# +# Intel PXA2xx Implementations +# +# CONFIG_ARCH_LUBBOCK is not set +# CONFIG_MACH_MAINSTONE is not set +# CONFIG_ARCH_PXA_IDP is not set +CONFIG_PXA_SHARPSL=y +CONFIG_PXA_SHARPSL_25x=y +# CONFIG_PXA_SHARPSL_27x is not set +CONFIG_MACH_POODLE=y +# CONFIG_MACH_CORGI is not set +# CONFIG_MACH_SHEPHERD is not set +# CONFIG_MACH_HUSKY is not set +CONFIG_PXA25x=y + +# +# Processor Type +# +CONFIG_CPU_32=y +CONFIG_CPU_XSCALE=y +CONFIG_CPU_32v5=y +CONFIG_CPU_ABRT_EV5T=y +CONFIG_CPU_CACHE_VIVT=y +CONFIG_CPU_TLB_V4WBI=y + +# +# Processor Features +# +CONFIG_ARM_THUMB=y +CONFIG_XSCALE_PMU=y +CONFIG_SHARP_LOCOMO=y +CONFIG_SHARP_PARAM=y +CONFIG_SHARP_SCOOP=y + +# +# Bus support +# +CONFIG_ISA_DMA_API=y + +# +# PCCARD (PCMCIA/CardBus) support +# +CONFIG_PCCARD=y +# CONFIG_PCMCIA_DEBUG is not set +CONFIG_PCMCIA=y +CONFIG_PCMCIA_LOAD_CIS=y +CONFIG_PCMCIA_IOCTL=y + +# +# PC-card bridges +# +CONFIG_PCMCIA_PXA2XX=y + +# +# Kernel Features +# +CONFIG_PREEMPT=y +# CONFIG_NO_IDLE_HZ is not set +# CONFIG_ARCH_DISCONTIGMEM_ENABLE is not set +CONFIG_SELECT_MEMORY_MODEL=y +CONFIG_FLATMEM_MANUAL=y +# CONFIG_DISCONTIGMEM_MANUAL is not set +# CONFIG_SPARSEMEM_MANUAL is not set +CONFIG_FLATMEM=y +CONFIG_FLAT_NODE_MEM_MAP=y +# CONFIG_SPARSEMEM_STATIC is not set +CONFIG_ALIGNMENT_TRAP=y + +# +# Boot options +# +CONFIG_ZBOOT_ROM_TEXT=0x0 +CONFIG_ZBOOT_ROM_BSS=0x0 +CONFIG_CMDLINE="console=ttyS0,115200n8 console=tty1 noinitrd root=/dev/mtdblock2 rootfstype=jffs2 debug" +# CONFIG_XIP_KERNEL is not set + +# +# Floating point emulation +# + +# +# At least one emulation must be selected +# +CONFIG_FPE_NWFPE=y +# CONFIG_FPE_NWFPE_XP is not set +# CONFIG_FPE_FASTFPE is not set + +# +# Userspace binary formats +# +CONFIG_BINFMT_ELF=y +CONFIG_BINFMT_AOUT=m +CONFIG_BINFMT_MISC=m +# CONFIG_ARTHUR is not set + +# +# Power management options +# +CONFIG_PM=y +CONFIG_APM=y + +# +# Networking +# +CONFIG_NET=y + +# +# Networking options +# +CONFIG_PACKET=y +CONFIG_PACKET_MMAP=y +CONFIG_UNIX=y +# CONFIG_NET_KEY is not set +CONFIG_INET=y +# CONFIG_IP_MULTICAST is not set +# CONFIG_IP_ADVANCED_ROUTER is not set +CONFIG_IP_FIB_HASH=y +# CONFIG_IP_PNP is not set +# CONFIG_NET_IPIP is not set +# CONFIG_NET_IPGRE is not set +# CONFIG_ARPD is not set +CONFIG_SYN_COOKIES=y +# CONFIG_INET_AH is not set +# CONFIG_INET_ESP is not set +# CONFIG_INET_IPCOMP is not set +# CONFIG_INET_TUNNEL is not set +CONFIG_INET_DIAG=y +CONFIG_INET_TCP_DIAG=y +# CONFIG_TCP_CONG_ADVANCED is not set +CONFIG_TCP_CONG_BIC=y +# CONFIG_IPV6 is not set +# CONFIG_NETFILTER is not set + +# +# DCCP Configuration (EXPERIMENTAL) +# +# CONFIG_IP_DCCP is not set + +# +# SCTP Configuration (EXPERIMENTAL) +# +# CONFIG_IP_SCTP is not set +# CONFIG_ATM is not set +# CONFIG_BRIDGE is not set +# CONFIG_VLAN_8021Q is not set +# CONFIG_DECNET is not set +# CONFIG_LLC2 is not set +# CONFIG_IPX is not set +# CONFIG_ATALK is not set +# CONFIG_X25 is not set +# CONFIG_LAPB is not set +# CONFIG_NET_DIVERT is not set +# CONFIG_ECONET is not set +# CONFIG_WAN_ROUTER is not set +# CONFIG_NET_SCHED is not set +# CONFIG_NET_CLS_ROUTE is not set + +# +# Network testing +# +# CONFIG_NET_PKTGEN is not set +# CONFIG_HAMRADIO is not set +# CONFIG_IRDA is not set +# CONFIG_BT is not set +# CONFIG_IEEE80211 is not set + +# +# Device Drivers +# + +# +# Generic Driver Options +# +CONFIG_STANDALONE=y +CONFIG_PREVENT_FIRMWARE_BUILD=y +CONFIG_FW_LOADER=y +# CONFIG_DEBUG_DRIVER is not set + +# +# Memory Technology Devices (MTD) +# +CONFIG_MTD=y +# CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_CONCAT is not set +CONFIG_MTD_PARTITIONS=y +# CONFIG_MTD_REDBOOT_PARTS is not set +# CONFIG_MTD_CMDLINE_PARTS is not set +# CONFIG_MTD_AFS_PARTS is not set + +# +# User Modules And Translation Layers +# +CONFIG_MTD_CHAR=y +CONFIG_MTD_BLOCK=y +# CONFIG_FTL is not set +# CONFIG_NFTL is not set +# CONFIG_INFTL is not set + +# +# RAM/ROM/Flash chip drivers +# +# CONFIG_MTD_CFI is not set +# CONFIG_MTD_JEDECPROBE is not set +CONFIG_MTD_MAP_BANK_WIDTH_1=y +CONFIG_MTD_MAP_BANK_WIDTH_2=y +CONFIG_MTD_MAP_BANK_WIDTH_4=y +# CONFIG_MTD_MAP_BANK_WIDTH_8 is not set +# CONFIG_MTD_MAP_BANK_WIDTH_16 is not set +# CONFIG_MTD_MAP_BANK_WIDTH_32 is not set +CONFIG_MTD_CFI_I1=y +CONFIG_MTD_CFI_I2=y +# CONFIG_MTD_CFI_I4 is not set +# CONFIG_MTD_CFI_I8 is not set +# CONFIG_MTD_RAM is not set +# CONFIG_MTD_ROM is not set +# CONFIG_MTD_ABSENT is not set + +# +# Mapping drivers for chip access +# +CONFIG_MTD_COMPLEX_MAPPINGS=y +CONFIG_MTD_SHARP_SL=y +# CONFIG_MTD_PLATRAM is not set + +# +# Self-contained MTD device drivers +# +# CONFIG_MTD_SLRAM is not set +# CONFIG_MTD_PHRAM is not set +# CONFIG_MTD_MTDRAM is not set +# CONFIG_MTD_BLKMTD is not set +# CONFIG_MTD_BLOCK2MTD is not set + +# +# Disk-On-Chip Device Drivers +# +# CONFIG_MTD_DOC2000 is not set +# CONFIG_MTD_DOC2001 is not set +# CONFIG_MTD_DOC2001PLUS is not set + +# +# NAND Flash Device Drivers +# +CONFIG_MTD_NAND=y +CONFIG_MTD_NAND_VERIFY_WRITE=y +# CONFIG_MTD_NAND_H1900 is not set +CONFIG_MTD_NAND_IDS=y +# CONFIG_MTD_NAND_DISKONCHIP is not set +CONFIG_MTD_NAND_SHARPSL=y +# CONFIG_MTD_NAND_NANDSIM is not set + +# +# Parallel port support +# +# CONFIG_PARPORT is not set + +# +# Plug and Play support +# + +# +# Block devices +# +# CONFIG_BLK_DEV_COW_COMMON is not set +CONFIG_BLK_DEV_LOOP=y +# CONFIG_BLK_DEV_CRYPTOLOOP is not set +# CONFIG_BLK_DEV_NBD is not set +# CONFIG_BLK_DEV_RAM is not set +CONFIG_BLK_DEV_RAM_COUNT=16 +# CONFIG_CDROM_PKTCDVD is not set + +# +# IO Schedulers +# +CONFIG_IOSCHED_NOOP=y +CONFIG_IOSCHED_AS=y +CONFIG_IOSCHED_DEADLINE=y +CONFIG_IOSCHED_CFQ=y +# CONFIG_ATA_OVER_ETH is not set + +# +# ATA/ATAPI/MFM/RLL support +# +CONFIG_IDE=y +CONFIG_BLK_DEV_IDE=y + +# +# Please see Documentation/ide.txt for help/info on IDE drives +# +# CONFIG_BLK_DEV_IDE_SATA is not set +CONFIG_BLK_DEV_IDEDISK=y +# CONFIG_IDEDISK_MULTI_MODE is not set +CONFIG_BLK_DEV_IDECS=y +# CONFIG_BLK_DEV_IDECD is not set +# CONFIG_BLK_DEV_IDETAPE is not set +# CONFIG_BLK_DEV_IDEFLOPPY is not set +# CONFIG_IDE_TASK_IOCTL is not set + +# +# IDE chipset support/bugfixes +# +CONFIG_IDE_GENERIC=y +# CONFIG_IDE_ARM is not set +# CONFIG_BLK_DEV_IDEDMA is not set +# CONFIG_IDEDMA_AUTO is not set +# CONFIG_BLK_DEV_HD is not set + +# +# SCSI device support +# +# CONFIG_RAID_ATTRS is not set +# CONFIG_SCSI is not set + +# +# Multi-device support (RAID and LVM) +# +# CONFIG_MD is not set + +# +# Fusion MPT device support +# +# CONFIG_FUSION is not set + +# +# IEEE 1394 (FireWire) support +# + +# +# I2O device support +# + +# +# Network device support +# +CONFIG_NETDEVICES=y +# CONFIG_DUMMY is not set +# CONFIG_BONDING is not set +# CONFIG_EQUALIZER is not set +# CONFIG_TUN is not set + +# +# PHY device support +# +# CONFIG_PHYLIB is not set + +# +# Ethernet (10 or 100Mbit) +# +CONFIG_NET_ETHERNET=y +# CONFIG_MII is not set +# CONFIG_SMC91X is not set +# CONFIG_DM9000 is not set + +# +# Ethernet (1000 Mbit) +# + +# +# Ethernet (10000 Mbit) +# + +# +# Token Ring devices +# + +# +# Wireless LAN (non-hamradio) +# +CONFIG_NET_RADIO=y + +# +# Obsolete Wireless cards support (pre-802.11) +# +# CONFIG_STRIP is not set +# CONFIG_PCMCIA_WAVELAN is not set +# CONFIG_PCMCIA_NETWAVE is not set + +# +# Wireless 802.11 Frequency Hopping cards support +# +# CONFIG_PCMCIA_RAYCS is not set + +# +# Wireless 802.11b ISA/PCI cards support +# +# CONFIG_HERMES is not set +# CONFIG_ATMEL is not set + +# +# Wireless 802.11b Pcmcia/Cardbus cards support +# +# CONFIG_AIRO_CS is not set +# CONFIG_PCMCIA_WL3501 is not set +# CONFIG_HOSTAP is not set +CONFIG_NET_WIRELESS=y + +# +# PCMCIA network device support +# +CONFIG_NET_PCMCIA=y +# CONFIG_PCMCIA_3C589 is not set +# CONFIG_PCMCIA_3C574 is not set +# CONFIG_PCMCIA_FMVJ18X is not set +CONFIG_PCMCIA_PCNET=y +# CONFIG_PCMCIA_NMCLAN is not set +# CONFIG_PCMCIA_SMC91C92 is not set +# CONFIG_PCMCIA_XIRC2PS is not set +# CONFIG_PCMCIA_AXNET is not set + +# +# Wan interfaces +# +# CONFIG_WAN is not set +CONFIG_PPP=m +# CONFIG_PPP_MULTILINK is not set +# CONFIG_PPP_FILTER is not set +CONFIG_PPP_ASYNC=m +# CONFIG_PPP_SYNC_TTY is not set +# CONFIG_PPP_DEFLATE is not set +CONFIG_PPP_BSDCOMP=m +# CONFIG_PPPOE is not set +# CONFIG_SLIP is not set +# CONFIG_SHAPER is not set +# CONFIG_NETCONSOLE is not set +# CONFIG_NETPOLL is not set +# CONFIG_NET_POLL_CONTROLLER is not set + +# +# ISDN subsystem +# +# CONFIG_ISDN is not set + +# +# Input device support +# +CONFIG_INPUT=y + +# +# Userland interfaces +# +# CONFIG_INPUT_MOUSEDEV is not set +# CONFIG_INPUT_JOYDEV is not set +CONFIG_INPUT_TSDEV=y +CONFIG_INPUT_TSDEV_SCREEN_X=240 +CONFIG_INPUT_TSDEV_SCREEN_Y=320 +CONFIG_INPUT_EVDEV=y +CONFIG_INPUT_EVBUG=y + +# +# Input Device Drivers +# +CONFIG_INPUT_KEYBOARD=y +# CONFIG_KEYBOARD_ATKBD is not set +# CONFIG_KEYBOARD_SUNKBD is not set +# CONFIG_KEYBOARD_LKKBD is not set +CONFIG_KEYBOARD_LOCOMO=y +# CONFIG_KEYBOARD_XTKBD is not set +# CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_KEYBOARD_CORGI is not set +CONFIG_KEYBOARD_SPITZ=y +# CONFIG_INPUT_MOUSE is not set +# CONFIG_INPUT_JOYSTICK is not set +# CONFIG_INPUT_TOUCHSCREEN is not set +# CONFIG_INPUT_MISC is not set + +# +# Hardware I/O ports +# +# CONFIG_SERIO is not set +# CONFIG_GAMEPORT is not set + +# +# Character devices +# +CONFIG_VT=y +CONFIG_VT_CONSOLE=y +CONFIG_HW_CONSOLE=y +# CONFIG_SERIAL_NONSTANDARD is not set + +# +# Serial drivers +# +# CONFIG_SERIAL_8250 is not set + +# +# Non-8250 serial port support +# +CONFIG_SERIAL_PXA=y +CONFIG_SERIAL_PXA_CONSOLE=y +CONFIG_SERIAL_CORE=y +CONFIG_SERIAL_CORE_CONSOLE=y +CONFIG_UNIX98_PTYS=y +# CONFIG_LEGACY_PTYS is not set + +# +# IPMI +# +# CONFIG_IPMI_HANDLER is not set + +# +# Watchdog Cards +# +# CONFIG_WATCHDOG is not set +# CONFIG_NVRAM is not set +# CONFIG_RTC is not set +# CONFIG_DTLK is not set +# CONFIG_R3964 is not set + +# +# Ftape, the floppy tape device driver +# + +# +# PCMCIA character devices +# +# CONFIG_SYNCLINK_CS is not set +# CONFIG_RAW_DRIVER is not set + +# +# TPM devices +# + +# +# I2C support +# +CONFIG_I2C=y +# CONFIG_I2C_CHARDEV is not set + +# +# I2C Algorithms +# +CONFIG_I2C_ALGOBIT=y +# CONFIG_I2C_ALGOPCF is not set +# CONFIG_I2C_ALGOPCA is not set + +# +# I2C Hardware Bus support +# +# CONFIG_I2C_PXA is not set +# CONFIG_I2C_PARPORT_LIGHT is not set +# CONFIG_I2C_STUB is not set +# CONFIG_I2C_PCA_ISA is not set + +# +# Miscellaneous I2C Chip support +# +# CONFIG_SENSORS_DS1337 is not set +# CONFIG_SENSORS_DS1374 is not set +# CONFIG_SENSORS_EEPROM is not set +# CONFIG_SENSORS_PCF8574 is not set +# CONFIG_SENSORS_PCA9539 is not set +# CONFIG_SENSORS_PCF8591 is not set +# CONFIG_SENSORS_RTC8564 is not set +# CONFIG_SENSORS_MAX6875 is not set +CONFIG_I2C_DEBUG_CORE=y +CONFIG_I2C_DEBUG_ALGO=y +CONFIG_I2C_DEBUG_BUS=y +# CONFIG_I2C_DEBUG_CHIP is not set + +# +# Hardware Monitoring support +# +CONFIG_HWMON=y +# CONFIG_HWMON_VID is not set +# CONFIG_SENSORS_ADM1021 is not set +# CONFIG_SENSORS_ADM1025 is not set +# CONFIG_SENSORS_ADM1026 is not set +# CONFIG_SENSORS_ADM1031 is not set +# CONFIG_SENSORS_ADM9240 is not set +# CONFIG_SENSORS_ASB100 is not set +# CONFIG_SENSORS_ATXP1 is not set +# CONFIG_SENSORS_DS1621 is not set +# CONFIG_SENSORS_FSCHER is not set +# CONFIG_SENSORS_FSCPOS is not set +# CONFIG_SENSORS_GL518SM is not set +# CONFIG_SENSORS_GL520SM is not set +# CONFIG_SENSORS_IT87 is not set +# CONFIG_SENSORS_LM63 is not set +# CONFIG_SENSORS_LM75 is not set +# CONFIG_SENSORS_LM77 is not set +# CONFIG_SENSORS_LM78 is not set +# CONFIG_SENSORS_LM80 is not set +# CONFIG_SENSORS_LM83 is not set +# CONFIG_SENSORS_LM85 is not set +# CONFIG_SENSORS_LM87 is not set +# CONFIG_SENSORS_LM90 is not set +# CONFIG_SENSORS_LM92 is not set +# CONFIG_SENSORS_MAX1619 is not set +# CONFIG_SENSORS_PC87360 is not set +# CONFIG_SENSORS_SMSC47M1 is not set +# CONFIG_SENSORS_SMSC47B397 is not set +# CONFIG_SENSORS_W83781D is not set +# CONFIG_SENSORS_W83792D is not set +# CONFIG_SENSORS_W83L785TS is not set +# CONFIG_SENSORS_W83627HF is not set +# CONFIG_SENSORS_W83627EHF is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Misc devices +# + +# +# Multimedia Capabilities Port drivers +# + +# +# Multimedia devices +# +CONFIG_VIDEO_DEV=m + +# +# Video For Linux +# + +# +# Video Adapters +# +# CONFIG_VIDEO_CPIA is not set +# CONFIG_VIDEO_SAA5246A is not set +# CONFIG_VIDEO_SAA5249 is not set +# CONFIG_TUNER_3036 is not set +# CONFIG_VIDEO_OVCAMCHIP is not set + +# +# Radio Adapters +# +# CONFIG_RADIO_MAESTRO is not set + +# +# Digital Video Broadcasting Devices +# +# CONFIG_DVB is not set + +# +# Graphics support +# +CONFIG_FB=y +CONFIG_FB_CFB_FILLRECT=y +CONFIG_FB_CFB_COPYAREA=y +CONFIG_FB_CFB_IMAGEBLIT=y +CONFIG_FB_SOFT_CURSOR=y +# CONFIG_FB_MACMODES is not set +CONFIG_FB_MODE_HELPERS=y +# CONFIG_FB_TILEBLITTING is not set +CONFIG_FB_PXA=y +# CONFIG_FB_W100 is not set +# CONFIG_FB_PXA_PARAMETERS is not set +# CONFIG_FB_S1D13XXX is not set +# CONFIG_FB_VIRTUAL is not set + +# +# Console display driver support +# +# CONFIG_VGA_CONSOLE is not set +CONFIG_DUMMY_CONSOLE=y +CONFIG_FRAMEBUFFER_CONSOLE=y +CONFIG_FONTS=y +CONFIG_FONT_8x8=y +# CONFIG_FONT_8x16 is not set +# CONFIG_FONT_6x11 is not set +# CONFIG_FONT_7x14 is not set +# CONFIG_FONT_PEARL_8x8 is not set +# CONFIG_FONT_ACORN_8x8 is not set +# CONFIG_FONT_MINI_4x6 is not set +# CONFIG_FONT_SUN8x16 is not set +# CONFIG_FONT_SUN12x22 is not set +# CONFIG_FONT_10x18 is not set + +# +# Logo configuration +# +# CONFIG_LOGO is not set +# CONFIG_BACKLIGHT_LCD_SUPPORT is not set + +# +# Sound +# +# CONFIG_SOUND is not set + +# +# USB support +# +CONFIG_USB_ARCH_HAS_HCD=y +# CONFIG_USB_ARCH_HAS_OHCI is not set +# CONFIG_USB is not set + +# +# USB Gadget Support +# +CONFIG_USB_GADGET=y +# CONFIG_USB_GADGET_DEBUG_FILES is not set +CONFIG_USB_GADGET_SELECTED=y +# CONFIG_USB_GADGET_NET2280 is not set +CONFIG_USB_GADGET_PXA2XX=y +CONFIG_USB_PXA2XX=y +# CONFIG_USB_PXA2XX_SMALL is not set +# CONFIG_USB_GADGET_GOKU is not set +# CONFIG_USB_GADGET_LH7A40X is not set +# CONFIG_USB_GADGET_OMAP is not set +# CONFIG_USB_GADGET_DUMMY_HCD is not set +# CONFIG_USB_GADGET_DUALSPEED is not set +# CONFIG_USB_ZERO is not set +CONFIG_USB_ETH=y +CONFIG_USB_ETH_RNDIS=y +# CONFIG_USB_GADGETFS is not set +# CONFIG_USB_FILE_STORAGE is not set +# CONFIG_USB_G_SERIAL is not set + +# +# MMC/SD Card support +# +CONFIG_MMC=y +CONFIG_MMC_DEBUG=y +CONFIG_MMC_BLOCK=y +CONFIG_MMC_PXA=y +# CONFIG_MMC_WBSD is not set + +# +# File systems +# +CONFIG_EXT2_FS=y +CONFIG_EXT2_FS_XATTR=y +CONFIG_EXT2_FS_POSIX_ACL=y +CONFIG_EXT2_FS_SECURITY=y +# CONFIG_EXT2_FS_XIP is not set +# CONFIG_EXT3_FS is not set +# CONFIG_JBD is not set +CONFIG_FS_MBCACHE=y +# CONFIG_REISERFS_FS is not set +# CONFIG_JFS_FS is not set +CONFIG_FS_POSIX_ACL=y +# CONFIG_XFS_FS is not set +# CONFIG_MINIX_FS is not set +# CONFIG_ROMFS_FS is not set +CONFIG_INOTIFY=y +# CONFIG_QUOTA is not set +CONFIG_DNOTIFY=y +# CONFIG_AUTOFS_FS is not set +# CONFIG_AUTOFS4_FS is not set +# CONFIG_FUSE_FS is not set + +# +# CD-ROM/DVD Filesystems +# +# CONFIG_ISO9660_FS is not set +# CONFIG_UDF_FS is not set + +# +# DOS/FAT/NT Filesystems +# +CONFIG_FAT_FS=y +CONFIG_MSDOS_FS=y +CONFIG_VFAT_FS=y +CONFIG_FAT_DEFAULT_CODEPAGE=437 +CONFIG_FAT_DEFAULT_IOCHARSET="iso8859-1" +# CONFIG_NTFS_FS is not set + +# +# Pseudo filesystems +# +CONFIG_PROC_FS=y +CONFIG_SYSFS=y +CONFIG_TMPFS=y +# CONFIG_HUGETLB_PAGE is not set +CONFIG_RAMFS=y +# CONFIG_RELAYFS_FS is not set + +# +# Miscellaneous filesystems +# +# CONFIG_ADFS_FS is not set +# CONFIG_AFFS_FS is not set +# CONFIG_HFS_FS is not set +# CONFIG_HFSPLUS_FS is not set +# CONFIG_BEFS_FS is not set +# CONFIG_BFS_FS is not set +# CONFIG_EFS_FS is not set +# CONFIG_JFFS_FS is not set +CONFIG_JFFS2_FS=y +CONFIG_JFFS2_FS_DEBUG=0 +CONFIG_JFFS2_FS_WRITEBUFFER=y +CONFIG_JFFS2_COMPRESSION_OPTIONS=y +CONFIG_JFFS2_ZLIB=y +CONFIG_JFFS2_RTIME=y +CONFIG_JFFS2_RUBIN=y +# CONFIG_JFFS2_CMODE_NONE is not set +CONFIG_JFFS2_CMODE_PRIORITY=y +# CONFIG_JFFS2_CMODE_SIZE is not set +CONFIG_CRAMFS=m +# CONFIG_VXFS_FS is not set +# CONFIG_HPFS_FS is not set +# CONFIG_QNX4FS_FS is not set +# CONFIG_SYSV_FS is not set +# CONFIG_UFS_FS is not set + +# +# Network File Systems +# +# CONFIG_NFS_FS is not set +# CONFIG_NFSD is not set +# CONFIG_SMB_FS is not set +# CONFIG_CIFS is not set +# CONFIG_NCP_FS is not set +# CONFIG_CODA_FS is not set +# CONFIG_AFS_FS is not set +# CONFIG_9P_FS is not set + +# +# Partition Types +# +CONFIG_PARTITION_ADVANCED=y +# CONFIG_ACORN_PARTITION is not set +# CONFIG_OSF_PARTITION is not set +# CONFIG_AMIGA_PARTITION is not set +# CONFIG_ATARI_PARTITION is not set +# CONFIG_MAC_PARTITION is not set +CONFIG_MSDOS_PARTITION=y +# CONFIG_BSD_DISKLABEL is not set +# CONFIG_MINIX_SUBPARTITION is not set +# CONFIG_SOLARIS_X86_PARTITION is not set +# CONFIG_UNIXWARE_DISKLABEL is not set +# CONFIG_LDM_PARTITION is not set +# CONFIG_SGI_PARTITION is not set +# CONFIG_ULTRIX_PARTITION is not set +# CONFIG_SUN_PARTITION is not set +# CONFIG_EFI_PARTITION is not set + +# +# Native Language Support +# +CONFIG_NLS=y +CONFIG_NLS_DEFAULT="cp437" +CONFIG_NLS_CODEPAGE_437=y +# CONFIG_NLS_CODEPAGE_737 is not set +# CONFIG_NLS_CODEPAGE_775 is not set +# CONFIG_NLS_CODEPAGE_850 is not set +# CONFIG_NLS_CODEPAGE_852 is not set +# CONFIG_NLS_CODEPAGE_855 is not set +# CONFIG_NLS_CODEPAGE_857 is not set +# CONFIG_NLS_CODEPAGE_860 is not set +# CONFIG_NLS_CODEPAGE_861 is not set +# CONFIG_NLS_CODEPAGE_862 is not set +# CONFIG_NLS_CODEPAGE_863 is not set +# CONFIG_NLS_CODEPAGE_864 is not set +# CONFIG_NLS_CODEPAGE_865 is not set +# CONFIG_NLS_CODEPAGE_866 is not set +# CONFIG_NLS_CODEPAGE_869 is not set +# CONFIG_NLS_CODEPAGE_936 is not set +# CONFIG_NLS_CODEPAGE_950 is not set +# CONFIG_NLS_CODEPAGE_932 is not set +# CONFIG_NLS_CODEPAGE_949 is not set +# CONFIG_NLS_CODEPAGE_874 is not set +# CONFIG_NLS_ISO8859_8 is not set +# CONFIG_NLS_CODEPAGE_1250 is not set +# CONFIG_NLS_CODEPAGE_1251 is not set +CONFIG_NLS_ASCII=y +CONFIG_NLS_ISO8859_1=y +# CONFIG_NLS_ISO8859_2 is not set +# CONFIG_NLS_ISO8859_3 is not set +# CONFIG_NLS_ISO8859_4 is not set +# CONFIG_NLS_ISO8859_5 is not set +# CONFIG_NLS_ISO8859_6 is not set +# CONFIG_NLS_ISO8859_7 is not set +# CONFIG_NLS_ISO8859_9 is not set +# CONFIG_NLS_ISO8859_13 is not set +# CONFIG_NLS_ISO8859_14 is not set +# CONFIG_NLS_ISO8859_15 is not set +# CONFIG_NLS_KOI8_R is not set +# CONFIG_NLS_KOI8_U is not set +CONFIG_NLS_UTF8=y + +# +# Profiling support +# +# CONFIG_PROFILING is not set + +# +# Kernel hacking +# +# CONFIG_PRINTK_TIME is not set +CONFIG_DEBUG_KERNEL=y +CONFIG_MAGIC_SYSRQ=y +CONFIG_LOG_BUF_SHIFT=14 +CONFIG_DETECT_SOFTLOCKUP=y +# CONFIG_SCHEDSTATS is not set +# CONFIG_DEBUG_SLAB is not set +CONFIG_DEBUG_PREEMPT=y +# CONFIG_DEBUG_SPINLOCK is not set +# CONFIG_DEBUG_SPINLOCK_SLEEP is not set +# CONFIG_DEBUG_KOBJECT is not set +# CONFIG_DEBUG_BUGVERBOSE is not set +# CONFIG_DEBUG_INFO is not set +# CONFIG_DEBUG_FS is not set +CONFIG_FRAME_POINTER=y +# CONFIG_DEBUG_USER is not set +# CONFIG_DEBUG_WAITQ is not set +CONFIG_DEBUG_ERRORS=y +# CONFIG_DEBUG_LL is not set + +# +# Security options +# +# CONFIG_KEYS is not set +# CONFIG_SECURITY is not set + +# +# Cryptographic options +# +# CONFIG_CRYPTO is not set + +# +# Hardware crypto devices +# + +# +# Library routines +# +CONFIG_CRC_CCITT=y +# CONFIG_CRC16 is not set +CONFIG_CRC32=y +# CONFIG_LIBCRC32C is not set +CONFIG_ZLIB_INFLATE=y +CONFIG_ZLIB_DEFLATE=y -- cgit v1.2.3 From 36e5ea67590707a069ce3bcc179b38cdabebcfdd Mon Sep 17 00:00:00 2001 From: Vincent Sanders Date: Mon, 10 Oct 2005 18:24:08 +0100 Subject: [ARM] 2967/1: defconfig for the ARM Corgi platform Patch from Vincent Sanders Add a defconfig for the ARM Corgi Zarus platform Signed-off-by: Richard Purdie Signed-off-by: Vincent Sanders Signed-off-by: Russell King --- arch/arm/configs/corgi_defconfig | 1523 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 1523 insertions(+) create mode 100644 arch/arm/configs/corgi_defconfig diff --git a/arch/arm/configs/corgi_defconfig b/arch/arm/configs/corgi_defconfig new file mode 100644 index 00000000000..24987c89609 --- /dev/null +++ b/arch/arm/configs/corgi_defconfig @@ -0,0 +1,1523 @@ +# +# Automatically generated make config: don't edit +# Linux kernel version: 2.6.14-rc3 +# Sun Oct 9 15:46:42 2005 +# +CONFIG_ARM=y +CONFIG_MMU=y +CONFIG_UID16=y +CONFIG_RWSEM_GENERIC_SPINLOCK=y +CONFIG_GENERIC_CALIBRATE_DELAY=y + +# +# Code maturity level options +# +CONFIG_EXPERIMENTAL=y +CONFIG_CLEAN_COMPILE=y +CONFIG_BROKEN_ON_SMP=y +CONFIG_LOCK_KERNEL=y +CONFIG_INIT_ENV_ARG_LIMIT=32 + +# +# General setup +# +CONFIG_LOCALVERSION="" +CONFIG_LOCALVERSION_AUTO=y +CONFIG_SWAP=y +CONFIG_SYSVIPC=y +# CONFIG_POSIX_MQUEUE is not set +CONFIG_BSD_PROCESS_ACCT=y +# CONFIG_BSD_PROCESS_ACCT_V3 is not set +CONFIG_SYSCTL=y +# CONFIG_AUDIT is not set +CONFIG_HOTPLUG=y +CONFIG_KOBJECT_UEVENT=y +# CONFIG_IKCONFIG is not set +CONFIG_INITRAMFS_SOURCE="" +CONFIG_EMBEDDED=y +CONFIG_KALLSYMS=y +# CONFIG_KALLSYMS_ALL is not set +# CONFIG_KALLSYMS_EXTRA_PASS is not set +CONFIG_PRINTK=y +CONFIG_BUG=y +CONFIG_BASE_FULL=y +CONFIG_FUTEX=y +CONFIG_EPOLL=y +# CONFIG_CC_OPTIMIZE_FOR_SIZE is not set +CONFIG_SHMEM=y +CONFIG_CC_ALIGN_FUNCTIONS=0 +CONFIG_CC_ALIGN_LABELS=0 +CONFIG_CC_ALIGN_LOOPS=0 +CONFIG_CC_ALIGN_JUMPS=0 +# CONFIG_TINY_SHMEM is not set +CONFIG_BASE_SMALL=0 + +# +# Loadable module support +# +CONFIG_MODULES=y +CONFIG_MODULE_UNLOAD=y +CONFIG_MODULE_FORCE_UNLOAD=y +CONFIG_OBSOLETE_MODPARM=y +# CONFIG_MODVERSIONS is not set +# CONFIG_MODULE_SRCVERSION_ALL is not set +CONFIG_KMOD=y + +# +# System Type +# +# CONFIG_ARCH_CLPS7500 is not set +# CONFIG_ARCH_CLPS711X is not set +# CONFIG_ARCH_CO285 is not set +# CONFIG_ARCH_EBSA110 is not set +# CONFIG_ARCH_CAMELOT is not set +# CONFIG_ARCH_FOOTBRIDGE is not set +# CONFIG_ARCH_INTEGRATOR is not set +# CONFIG_ARCH_IOP3XX is not set +# CONFIG_ARCH_IXP4XX is not set +# CONFIG_ARCH_IXP2000 is not set +# CONFIG_ARCH_L7200 is not set +CONFIG_ARCH_PXA=y +# CONFIG_ARCH_RPC is not set +# CONFIG_ARCH_SA1100 is not set +# CONFIG_ARCH_S3C2410 is not set +# CONFIG_ARCH_SHARK is not set +# CONFIG_ARCH_LH7A40X is not set +# CONFIG_ARCH_OMAP is not set +# CONFIG_ARCH_VERSATILE is not set +# CONFIG_ARCH_IMX is not set +# CONFIG_ARCH_H720X is not set +# CONFIG_ARCH_AAEC2000 is not set + +# +# Intel PXA2xx Implementations +# +# CONFIG_ARCH_LUBBOCK is not set +# CONFIG_MACH_MAINSTONE is not set +# CONFIG_ARCH_PXA_IDP is not set +CONFIG_PXA_SHARPSL=y +CONFIG_PXA_SHARPSL_25x=y +# CONFIG_PXA_SHARPSL_27x is not set +# CONFIG_MACH_POODLE is not set +CONFIG_MACH_CORGI=y +CONFIG_MACH_SHEPHERD=y +CONFIG_MACH_HUSKY=y +CONFIG_PXA25x=y +CONFIG_PXA_SHARP_C7xx=y + +# +# Processor Type +# +CONFIG_CPU_32=y +CONFIG_CPU_XSCALE=y +CONFIG_CPU_32v5=y +CONFIG_CPU_ABRT_EV5T=y +CONFIG_CPU_CACHE_VIVT=y +CONFIG_CPU_TLB_V4WBI=y + +# +# Processor Features +# +CONFIG_ARM_THUMB=y +CONFIG_XSCALE_PMU=y +CONFIG_SHARP_PARAM=y +CONFIG_SHARP_SCOOP=y + +# +# Bus support +# +CONFIG_ISA_DMA_API=y + +# +# PCCARD (PCMCIA/CardBus) support +# +CONFIG_PCCARD=y +# CONFIG_PCMCIA_DEBUG is not set +CONFIG_PCMCIA=y +CONFIG_PCMCIA_LOAD_CIS=y +CONFIG_PCMCIA_IOCTL=y + +# +# PC-card bridges +# +CONFIG_PCMCIA_PXA2XX=y + +# +# Kernel Features +# +CONFIG_PREEMPT=y +# CONFIG_NO_IDLE_HZ is not set +# CONFIG_ARCH_DISCONTIGMEM_ENABLE is not set +CONFIG_SELECT_MEMORY_MODEL=y +CONFIG_FLATMEM_MANUAL=y +# CONFIG_DISCONTIGMEM_MANUAL is not set +# CONFIG_SPARSEMEM_MANUAL is not set +CONFIG_FLATMEM=y +CONFIG_FLAT_NODE_MEM_MAP=y +# CONFIG_SPARSEMEM_STATIC is not set +CONFIG_ALIGNMENT_TRAP=y + +# +# Boot options +# +CONFIG_ZBOOT_ROM_TEXT=0x0 +CONFIG_ZBOOT_ROM_BSS=0x0 +CONFIG_CMDLINE="console=ttyS0,115200n8 console=tty1 noinitrd root=/dev/mtdblock2 rootfstype=jffs2 debug" +# CONFIG_XIP_KERNEL is not set + +# +# Floating point emulation +# + +# +# At least one emulation must be selected +# +CONFIG_FPE_NWFPE=y +# CONFIG_FPE_NWFPE_XP is not set +# CONFIG_FPE_FASTFPE is not set + +# +# Userspace binary formats +# +CONFIG_BINFMT_ELF=y +CONFIG_BINFMT_AOUT=m +CONFIG_BINFMT_MISC=m +# CONFIG_ARTHUR is not set + +# +# Power management options +# +CONFIG_PM=y +CONFIG_APM=y + +# +# Networking +# +CONFIG_NET=y + +# +# Networking options +# +CONFIG_PACKET=y +CONFIG_PACKET_MMAP=y +CONFIG_UNIX=y +CONFIG_XFRM=y +CONFIG_XFRM_USER=m +# CONFIG_NET_KEY is not set +CONFIG_INET=y +# CONFIG_IP_MULTICAST is not set +# CONFIG_IP_ADVANCED_ROUTER is not set +CONFIG_IP_FIB_HASH=y +# CONFIG_IP_PNP is not set +# CONFIG_NET_IPIP is not set +# CONFIG_NET_IPGRE is not set +# CONFIG_ARPD is not set +CONFIG_SYN_COOKIES=y +# CONFIG_INET_AH is not set +# CONFIG_INET_ESP is not set +# CONFIG_INET_IPCOMP is not set +# CONFIG_INET_TUNNEL is not set +CONFIG_INET_DIAG=y +CONFIG_INET_TCP_DIAG=y +# CONFIG_TCP_CONG_ADVANCED is not set +CONFIG_TCP_CONG_BIC=y + +# +# IP: Virtual Server Configuration +# +# CONFIG_IP_VS is not set +CONFIG_IPV6=m +# CONFIG_IPV6_PRIVACY is not set +CONFIG_INET6_AH=m +CONFIG_INET6_ESP=m +CONFIG_INET6_IPCOMP=m +CONFIG_INET6_TUNNEL=m +CONFIG_IPV6_TUNNEL=m +CONFIG_NETFILTER=y +# CONFIG_NETFILTER_DEBUG is not set +# CONFIG_NETFILTER_NETLINK is not set + +# +# IP: Netfilter Configuration +# +CONFIG_IP_NF_CONNTRACK=m +# CONFIG_IP_NF_CT_ACCT is not set +# CONFIG_IP_NF_CONNTRACK_MARK is not set +# CONFIG_IP_NF_CONNTRACK_EVENTS is not set +CONFIG_IP_NF_CT_PROTO_SCTP=m +CONFIG_IP_NF_FTP=m +CONFIG_IP_NF_IRC=m +# CONFIG_IP_NF_NETBIOS_NS is not set +CONFIG_IP_NF_TFTP=m +CONFIG_IP_NF_AMANDA=m +# CONFIG_IP_NF_PPTP is not set +CONFIG_IP_NF_QUEUE=m +CONFIG_IP_NF_IPTABLES=m +CONFIG_IP_NF_MATCH_LIMIT=m +CONFIG_IP_NF_MATCH_IPRANGE=m +CONFIG_IP_NF_MATCH_MAC=m +CONFIG_IP_NF_MATCH_PKTTYPE=m +CONFIG_IP_NF_MATCH_MARK=m +CONFIG_IP_NF_MATCH_MULTIPORT=m +CONFIG_IP_NF_MATCH_TOS=m +CONFIG_IP_NF_MATCH_RECENT=m +CONFIG_IP_NF_MATCH_ECN=m +CONFIG_IP_NF_MATCH_DSCP=m +CONFIG_IP_NF_MATCH_AH_ESP=m +CONFIG_IP_NF_MATCH_LENGTH=m +CONFIG_IP_NF_MATCH_TTL=m +CONFIG_IP_NF_MATCH_TCPMSS=m +CONFIG_IP_NF_MATCH_HELPER=m +CONFIG_IP_NF_MATCH_STATE=m +CONFIG_IP_NF_MATCH_CONNTRACK=m +CONFIG_IP_NF_MATCH_OWNER=m +CONFIG_IP_NF_MATCH_ADDRTYPE=m +CONFIG_IP_NF_MATCH_REALM=m +CONFIG_IP_NF_MATCH_SCTP=m +# CONFIG_IP_NF_MATCH_DCCP is not set +CONFIG_IP_NF_MATCH_COMMENT=m +CONFIG_IP_NF_MATCH_HASHLIMIT=m +# CONFIG_IP_NF_MATCH_STRING is not set +CONFIG_IP_NF_FILTER=m +# CONFIG_IP_NF_TARGET_REJECT is not set +CONFIG_IP_NF_TARGET_LOG=m +CONFIG_IP_NF_TARGET_ULOG=m +CONFIG_IP_NF_TARGET_TCPMSS=m +# CONFIG_IP_NF_TARGET_NFQUEUE is not set +CONFIG_IP_NF_NAT=m +CONFIG_IP_NF_NAT_NEEDED=y +# CONFIG_IP_NF_TARGET_MASQUERADE is not set +# CONFIG_IP_NF_TARGET_REDIRECT is not set +# CONFIG_IP_NF_TARGET_NETMAP is not set +# CONFIG_IP_NF_TARGET_SAME is not set +# CONFIG_IP_NF_NAT_SNMP_BASIC is not set +CONFIG_IP_NF_NAT_IRC=m +CONFIG_IP_NF_NAT_FTP=m +CONFIG_IP_NF_NAT_TFTP=m +CONFIG_IP_NF_NAT_AMANDA=m +CONFIG_IP_NF_MANGLE=m +# CONFIG_IP_NF_TARGET_TOS is not set +# CONFIG_IP_NF_TARGET_ECN is not set +# CONFIG_IP_NF_TARGET_DSCP is not set +# CONFIG_IP_NF_TARGET_MARK is not set +# CONFIG_IP_NF_TARGET_CLASSIFY is not set +# CONFIG_IP_NF_TARGET_TTL is not set +CONFIG_IP_NF_RAW=m +# CONFIG_IP_NF_TARGET_NOTRACK is not set +CONFIG_IP_NF_ARPTABLES=m +CONFIG_IP_NF_ARPFILTER=m +CONFIG_IP_NF_ARP_MANGLE=m + +# +# IPv6: Netfilter Configuration (EXPERIMENTAL) +# +CONFIG_IP6_NF_QUEUE=m +CONFIG_IP6_NF_IPTABLES=m +CONFIG_IP6_NF_MATCH_LIMIT=m +CONFIG_IP6_NF_MATCH_MAC=m +CONFIG_IP6_NF_MATCH_RT=m +CONFIG_IP6_NF_MATCH_OPTS=m +CONFIG_IP6_NF_MATCH_FRAG=m +CONFIG_IP6_NF_MATCH_HL=m +CONFIG_IP6_NF_MATCH_MULTIPORT=m +CONFIG_IP6_NF_MATCH_OWNER=m +CONFIG_IP6_NF_MATCH_MARK=m +CONFIG_IP6_NF_MATCH_IPV6HEADER=m +CONFIG_IP6_NF_MATCH_AHESP=m +CONFIG_IP6_NF_MATCH_LENGTH=m +CONFIG_IP6_NF_MATCH_EUI64=m +CONFIG_IP6_NF_FILTER=m +# CONFIG_IP6_NF_TARGET_LOG is not set +# CONFIG_IP6_NF_TARGET_REJECT is not set +# CONFIG_IP6_NF_TARGET_NFQUEUE is not set +CONFIG_IP6_NF_MANGLE=m +# CONFIG_IP6_NF_TARGET_MARK is not set +# CONFIG_IP6_NF_TARGET_HL is not set +CONFIG_IP6_NF_RAW=m + +# +# DCCP Configuration (EXPERIMENTAL) +# +# CONFIG_IP_DCCP is not set + +# +# SCTP Configuration (EXPERIMENTAL) +# +# CONFIG_IP_SCTP is not set +# CONFIG_ATM is not set +# CONFIG_BRIDGE is not set +# CONFIG_VLAN_8021Q is not set +# CONFIG_DECNET is not set +# CONFIG_LLC2 is not set +# CONFIG_IPX is not set +# CONFIG_ATALK is not set +# CONFIG_X25 is not set +# CONFIG_LAPB is not set +# CONFIG_NET_DIVERT is not set +# CONFIG_ECONET is not set +# CONFIG_WAN_ROUTER is not set +# CONFIG_NET_SCHED is not set +CONFIG_NET_CLS_ROUTE=y + +# +# Network testing +# +# CONFIG_NET_PKTGEN is not set +# CONFIG_HAMRADIO is not set +CONFIG_IRDA=m + +# +# IrDA protocols +# +CONFIG_IRLAN=m +CONFIG_IRNET=m +CONFIG_IRCOMM=m +# CONFIG_IRDA_ULTRA is not set + +# +# IrDA options +# +# CONFIG_IRDA_CACHE_LAST_LSAP is not set +# CONFIG_IRDA_FAST_RR is not set +# CONFIG_IRDA_DEBUG is not set + +# +# Infrared-port device drivers +# + +# +# SIR device drivers +# +# CONFIG_IRTTY_SIR is not set + +# +# Dongle support +# + +# +# Old SIR device drivers +# +# CONFIG_IRPORT_SIR is not set + +# +# Old Serial dongle support +# + +# +# FIR device drivers +# +# CONFIG_USB_IRDA is not set +# CONFIG_SIGMATEL_FIR is not set +# CONFIG_NSC_FIR is not set +# CONFIG_WINBOND_FIR is not set +# CONFIG_SMC_IRCC_FIR is not set +# CONFIG_ALI_FIR is not set +# CONFIG_VIA_FIR is not set +CONFIG_BT=m +CONFIG_BT_L2CAP=m +CONFIG_BT_SCO=m +CONFIG_BT_RFCOMM=m +CONFIG_BT_RFCOMM_TTY=y +CONFIG_BT_BNEP=m +CONFIG_BT_BNEP_MC_FILTER=y +CONFIG_BT_BNEP_PROTO_FILTER=y +CONFIG_BT_HIDP=m + +# +# Bluetooth device drivers +# +CONFIG_BT_HCIUSB=m +# CONFIG_BT_HCIUSB_SCO is not set +CONFIG_BT_HCIUART=m +CONFIG_BT_HCIUART_H4=y +CONFIG_BT_HCIUART_BCSP=y +CONFIG_BT_HCIUART_BCSP_TXCRC=y +CONFIG_BT_HCIBCM203X=m +CONFIG_BT_HCIBPA10X=m +CONFIG_BT_HCIBFUSB=m +CONFIG_BT_HCIDTL1=m +CONFIG_BT_HCIBT3C=m +CONFIG_BT_HCIBLUECARD=m +CONFIG_BT_HCIBTUART=m +CONFIG_BT_HCIVHCI=m +CONFIG_IEEE80211=m +# CONFIG_IEEE80211_DEBUG is not set +CONFIG_IEEE80211_CRYPT_WEP=m +# CONFIG_IEEE80211_CRYPT_CCMP is not set +# CONFIG_IEEE80211_CRYPT_TKIP is not set + +# +# Device Drivers +# + +# +# Generic Driver Options +# +CONFIG_STANDALONE=y +CONFIG_PREVENT_FIRMWARE_BUILD=y +CONFIG_FW_LOADER=y +# CONFIG_DEBUG_DRIVER is not set + +# +# Memory Technology Devices (MTD) +# +CONFIG_MTD=y +# CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_CONCAT is not set +CONFIG_MTD_PARTITIONS=y +# CONFIG_MTD_REDBOOT_PARTS is not set +CONFIG_MTD_CMDLINE_PARTS=y +# CONFIG_MTD_AFS_PARTS is not set + +# +# User Modules And Translation Layers +# +CONFIG_MTD_CHAR=y +CONFIG_MTD_BLOCK=y +# CONFIG_FTL is not set +# CONFIG_NFTL is not set +# CONFIG_INFTL is not set + +# +# RAM/ROM/Flash chip drivers +# +# CONFIG_MTD_CFI is not set +# CONFIG_MTD_JEDECPROBE is not set +CONFIG_MTD_MAP_BANK_WIDTH_1=y +CONFIG_MTD_MAP_BANK_WIDTH_2=y +CONFIG_MTD_MAP_BANK_WIDTH_4=y +# CONFIG_MTD_MAP_BANK_WIDTH_8 is not set +# CONFIG_MTD_MAP_BANK_WIDTH_16 is not set +# CONFIG_MTD_MAP_BANK_WIDTH_32 is not set +CONFIG_MTD_CFI_I1=y +CONFIG_MTD_CFI_I2=y +# CONFIG_MTD_CFI_I4 is not set +# CONFIG_MTD_CFI_I8 is not set +# CONFIG_MTD_RAM is not set +CONFIG_MTD_ROM=y +# CONFIG_MTD_ABSENT is not set + +# +# Mapping drivers for chip access +# +CONFIG_MTD_COMPLEX_MAPPINGS=y +CONFIG_MTD_SHARP_SL=y +# CONFIG_MTD_PLATRAM is not set + +# +# Self-contained MTD device drivers +# +# CONFIG_MTD_SLRAM is not set +# CONFIG_MTD_PHRAM is not set +# CONFIG_MTD_MTDRAM is not set +# CONFIG_MTD_BLKMTD is not set +# CONFIG_MTD_BLOCK2MTD is not set + +# +# Disk-On-Chip Device Drivers +# +# CONFIG_MTD_DOC2000 is not set +# CONFIG_MTD_DOC2001 is not set +# CONFIG_MTD_DOC2001PLUS is not set + +# +# NAND Flash Device Drivers +# +CONFIG_MTD_NAND=y +CONFIG_MTD_NAND_VERIFY_WRITE=y +# CONFIG_MTD_NAND_H1900 is not set +CONFIG_MTD_NAND_IDS=y +# CONFIG_MTD_NAND_DISKONCHIP is not set +CONFIG_MTD_NAND_SHARPSL=y +# CONFIG_MTD_NAND_NANDSIM is not set + +# +# Parallel port support +# +# CONFIG_PARPORT is not set + +# +# Plug and Play support +# + +# +# Block devices +# +# CONFIG_BLK_DEV_COW_COMMON is not set +CONFIG_BLK_DEV_LOOP=y +# CONFIG_BLK_DEV_CRYPTOLOOP is not set +# CONFIG_BLK_DEV_NBD is not set +# CONFIG_BLK_DEV_UB is not set +# CONFIG_BLK_DEV_RAM is not set +CONFIG_BLK_DEV_RAM_COUNT=16 +# CONFIG_CDROM_PKTCDVD is not set + +# +# IO Schedulers +# +CONFIG_IOSCHED_NOOP=y +CONFIG_IOSCHED_AS=y +CONFIG_IOSCHED_DEADLINE=y +CONFIG_IOSCHED_CFQ=y +# CONFIG_ATA_OVER_ETH is not set + +# +# ATA/ATAPI/MFM/RLL support +# +CONFIG_IDE=y +CONFIG_BLK_DEV_IDE=y + +# +# Please see Documentation/ide.txt for help/info on IDE drives +# +# CONFIG_BLK_DEV_IDE_SATA is not set +CONFIG_BLK_DEV_IDEDISK=y +# CONFIG_IDEDISK_MULTI_MODE is not set +CONFIG_BLK_DEV_IDECS=y +# CONFIG_BLK_DEV_IDECD is not set +# CONFIG_BLK_DEV_IDETAPE is not set +# CONFIG_BLK_DEV_IDEFLOPPY is not set +# CONFIG_BLK_DEV_IDESCSI is not set +# CONFIG_IDE_TASK_IOCTL is not set + +# +# IDE chipset support/bugfixes +# +CONFIG_IDE_GENERIC=y +# CONFIG_IDE_ARM is not set +# CONFIG_BLK_DEV_IDEDMA is not set +# CONFIG_IDEDMA_AUTO is not set +# CONFIG_BLK_DEV_HD is not set + +# +# SCSI device support +# +# CONFIG_RAID_ATTRS is not set +CONFIG_SCSI=m +CONFIG_SCSI_PROC_FS=y + +# +# SCSI support type (disk, tape, CD-ROM) +# +CONFIG_BLK_DEV_SD=m +CONFIG_CHR_DEV_ST=m +CONFIG_CHR_DEV_OSST=m +CONFIG_BLK_DEV_SR=m +# CONFIG_BLK_DEV_SR_VENDOR is not set +CONFIG_CHR_DEV_SG=m +# CONFIG_CHR_DEV_SCH is not set + +# +# Some SCSI devices (e.g. CD jukebox) support multiple LUNs +# +CONFIG_SCSI_MULTI_LUN=y +# CONFIG_SCSI_CONSTANTS is not set +# CONFIG_SCSI_LOGGING is not set + +# +# SCSI Transport Attributes +# +# CONFIG_SCSI_SPI_ATTRS is not set +# CONFIG_SCSI_FC_ATTRS is not set +# CONFIG_SCSI_ISCSI_ATTRS is not set +# CONFIG_SCSI_SAS_ATTRS is not set + +# +# SCSI low-level drivers +# +# CONFIG_SCSI_SATA is not set +# CONFIG_SCSI_DEBUG is not set + +# +# PCMCIA SCSI adapter support +# +# CONFIG_PCMCIA_AHA152X is not set +# CONFIG_PCMCIA_FDOMAIN is not set +# CONFIG_PCMCIA_NINJA_SCSI is not set +# CONFIG_PCMCIA_QLOGIC is not set +# CONFIG_PCMCIA_SYM53C500 is not set + +# +# Multi-device support (RAID and LVM) +# +# CONFIG_MD is not set + +# +# Fusion MPT device support +# +# CONFIG_FUSION is not set + +# +# IEEE 1394 (FireWire) support +# + +# +# I2O device support +# + +# +# Network device support +# +CONFIG_NETDEVICES=y +# CONFIG_DUMMY is not set +# CONFIG_BONDING is not set +# CONFIG_EQUALIZER is not set +# CONFIG_TUN is not set + +# +# PHY device support +# +# CONFIG_PHYLIB is not set + +# +# Ethernet (10 or 100Mbit) +# +CONFIG_NET_ETHERNET=y +CONFIG_MII=m +# CONFIG_SMC91X is not set +# CONFIG_DM9000 is not set + +# +# Ethernet (1000 Mbit) +# + +# +# Ethernet (10000 Mbit) +# + +# +# Token Ring devices +# + +# +# Wireless LAN (non-hamradio) +# +CONFIG_NET_RADIO=y + +# +# Obsolete Wireless cards support (pre-802.11) +# +# CONFIG_STRIP is not set +# CONFIG_PCMCIA_WAVELAN is not set +# CONFIG_PCMCIA_NETWAVE is not set + +# +# Wireless 802.11 Frequency Hopping cards support +# +# CONFIG_PCMCIA_RAYCS is not set + +# +# Wireless 802.11b ISA/PCI cards support +# +CONFIG_HERMES=m +# CONFIG_ATMEL is not set + +# +# Wireless 802.11b Pcmcia/Cardbus cards support +# +CONFIG_PCMCIA_HERMES=m +CONFIG_PCMCIA_SPECTRUM=m +# CONFIG_AIRO_CS is not set +# CONFIG_PCMCIA_WL3501 is not set +CONFIG_HOSTAP=m +CONFIG_HOSTAP_FIRMWARE=y +CONFIG_HOSTAP_CS=m +CONFIG_NET_WIRELESS=y + +# +# PCMCIA network device support +# +CONFIG_NET_PCMCIA=y +# CONFIG_PCMCIA_3C589 is not set +# CONFIG_PCMCIA_3C574 is not set +# CONFIG_PCMCIA_FMVJ18X is not set +CONFIG_PCMCIA_PCNET=m +# CONFIG_PCMCIA_NMCLAN is not set +# CONFIG_PCMCIA_SMC91C92 is not set +# CONFIG_PCMCIA_XIRC2PS is not set +# CONFIG_PCMCIA_AXNET is not set + +# +# Wan interfaces +# +# CONFIG_WAN is not set +CONFIG_PPP=m +# CONFIG_PPP_MULTILINK is not set +# CONFIG_PPP_FILTER is not set +CONFIG_PPP_ASYNC=m +# CONFIG_PPP_SYNC_TTY is not set +# CONFIG_PPP_DEFLATE is not set +CONFIG_PPP_BSDCOMP=m +# CONFIG_PPPOE is not set +# CONFIG_SLIP is not set +# CONFIG_SHAPER is not set +# CONFIG_NETCONSOLE is not set +# CONFIG_NETPOLL is not set +# CONFIG_NET_POLL_CONTROLLER is not set + +# +# ISDN subsystem +# +# CONFIG_ISDN is not set + +# +# Input device support +# +CONFIG_INPUT=y + +# +# Userland interfaces +# +# CONFIG_INPUT_MOUSEDEV is not set +# CONFIG_INPUT_JOYDEV is not set +# CONFIG_INPUT_TSDEV is not set +CONFIG_INPUT_EVDEV=y +# CONFIG_INPUT_EVBUG is not set + +# +# Input Device Drivers +# +CONFIG_INPUT_KEYBOARD=y +# CONFIG_KEYBOARD_ATKBD is not set +# CONFIG_KEYBOARD_SUNKBD is not set +# CONFIG_KEYBOARD_LKKBD is not set +# CONFIG_KEYBOARD_XTKBD is not set +# CONFIG_KEYBOARD_NEWTON is not set +CONFIG_KEYBOARD_CORGI=y +CONFIG_KEYBOARD_SPITZ=y +# CONFIG_INPUT_MOUSE is not set +# CONFIG_INPUT_JOYSTICK is not set +CONFIG_INPUT_TOUCHSCREEN=y +CONFIG_TOUCHSCREEN_CORGI=y +# CONFIG_TOUCHSCREEN_GUNZE is not set +# CONFIG_TOUCHSCREEN_ELO is not set +# CONFIG_TOUCHSCREEN_MTOUCH is not set +# CONFIG_TOUCHSCREEN_MK712 is not set +CONFIG_INPUT_MISC=y +CONFIG_INPUT_UINPUT=m + +# +# Hardware I/O ports +# +# CONFIG_SERIO is not set +# CONFIG_GAMEPORT is not set + +# +# Character devices +# +CONFIG_VT=y +CONFIG_VT_CONSOLE=y +CONFIG_HW_CONSOLE=y +# CONFIG_SERIAL_NONSTANDARD is not set + +# +# Serial drivers +# +CONFIG_SERIAL_8250=m +CONFIG_SERIAL_8250_CS=m +CONFIG_SERIAL_8250_NR_UARTS=4 +# CONFIG_SERIAL_8250_EXTENDED is not set + +# +# Non-8250 serial port support +# +CONFIG_SERIAL_PXA=y +CONFIG_SERIAL_PXA_CONSOLE=y +CONFIG_SERIAL_CORE=y +CONFIG_SERIAL_CORE_CONSOLE=y +CONFIG_UNIX98_PTYS=y +# CONFIG_LEGACY_PTYS is not set + +# +# IPMI +# +# CONFIG_IPMI_HANDLER is not set + +# +# Watchdog Cards +# +# CONFIG_WATCHDOG is not set +# CONFIG_NVRAM is not set +# CONFIG_RTC is not set +# CONFIG_DTLK is not set +# CONFIG_R3964 is not set + +# +# Ftape, the floppy tape device driver +# + +# +# PCMCIA character devices +# +# CONFIG_SYNCLINK_CS is not set +# CONFIG_RAW_DRIVER is not set + +# +# TPM devices +# + +# +# I2C support +# +CONFIG_I2C=y +# CONFIG_I2C_CHARDEV is not set + +# +# I2C Algorithms +# +CONFIG_I2C_ALGOBIT=y +# CONFIG_I2C_ALGOPCF is not set +# CONFIG_I2C_ALGOPCA is not set + +# +# I2C Hardware Bus support +# +CONFIG_I2C_PXA=y +# CONFIG_I2C_PXA_SLAVE is not set +# CONFIG_I2C_PARPORT_LIGHT is not set +# CONFIG_I2C_STUB is not set +# CONFIG_I2C_PCA_ISA is not set + +# +# Miscellaneous I2C Chip support +# +# CONFIG_SENSORS_DS1337 is not set +# CONFIG_SENSORS_DS1374 is not set +# CONFIG_SENSORS_EEPROM is not set +# CONFIG_SENSORS_PCF8574 is not set +# CONFIG_SENSORS_PCA9539 is not set +# CONFIG_SENSORS_PCF8591 is not set +# CONFIG_SENSORS_RTC8564 is not set +# CONFIG_SENSORS_MAX6875 is not set +# CONFIG_I2C_DEBUG_CORE is not set +# CONFIG_I2C_DEBUG_ALGO is not set +# CONFIG_I2C_DEBUG_BUS is not set +# CONFIG_I2C_DEBUG_CHIP is not set + +# +# Hardware Monitoring support +# +CONFIG_HWMON=y +# CONFIG_HWMON_VID is not set +# CONFIG_SENSORS_ADM1021 is not set +# CONFIG_SENSORS_ADM1025 is not set +# CONFIG_SENSORS_ADM1026 is not set +# CONFIG_SENSORS_ADM1031 is not set +# CONFIG_SENSORS_ADM9240 is not set +# CONFIG_SENSORS_ASB100 is not set +# CONFIG_SENSORS_ATXP1 is not set +# CONFIG_SENSORS_DS1621 is not set +# CONFIG_SENSORS_FSCHER is not set +# CONFIG_SENSORS_FSCPOS is not set +# CONFIG_SENSORS_GL518SM is not set +# CONFIG_SENSORS_GL520SM is not set +# CONFIG_SENSORS_IT87 is not set +# CONFIG_SENSORS_LM63 is not set +# CONFIG_SENSORS_LM75 is not set +# CONFIG_SENSORS_LM77 is not set +# CONFIG_SENSORS_LM78 is not set +# CONFIG_SENSORS_LM80 is not set +# CONFIG_SENSORS_LM83 is not set +# CONFIG_SENSORS_LM85 is not set +# CONFIG_SENSORS_LM87 is not set +# CONFIG_SENSORS_LM90 is not set +# CONFIG_SENSORS_LM92 is not set +# CONFIG_SENSORS_MAX1619 is not set +# CONFIG_SENSORS_PC87360 is not set +# CONFIG_SENSORS_SMSC47M1 is not set +# CONFIG_SENSORS_SMSC47B397 is not set +# CONFIG_SENSORS_W83781D is not set +# CONFIG_SENSORS_W83792D is not set +# CONFIG_SENSORS_W83L785TS is not set +# CONFIG_SENSORS_W83627HF is not set +# CONFIG_SENSORS_W83627EHF is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Misc devices +# + +# +# Multimedia Capabilities Port drivers +# + +# +# Multimedia devices +# +CONFIG_VIDEO_DEV=m + +# +# Video For Linux +# + +# +# Video Adapters +# +# CONFIG_VIDEO_CPIA is not set +# CONFIG_VIDEO_SAA5246A is not set +# CONFIG_VIDEO_SAA5249 is not set +# CONFIG_TUNER_3036 is not set +# CONFIG_VIDEO_OVCAMCHIP is not set + +# +# Radio Adapters +# +# CONFIG_RADIO_MAESTRO is not set + +# +# Digital Video Broadcasting Devices +# +# CONFIG_DVB is not set + +# +# Graphics support +# +CONFIG_FB=y +CONFIG_FB_CFB_FILLRECT=y +CONFIG_FB_CFB_COPYAREA=y +CONFIG_FB_CFB_IMAGEBLIT=y +CONFIG_FB_SOFT_CURSOR=y +# CONFIG_FB_MACMODES is not set +# CONFIG_FB_MODE_HELPERS is not set +# CONFIG_FB_TILEBLITTING is not set +# CONFIG_FB_PXA is not set +CONFIG_FB_W100=y +# CONFIG_FB_S1D13XXX is not set +# CONFIG_FB_VIRTUAL is not set + +# +# Console display driver support +# +# CONFIG_VGA_CONSOLE is not set +CONFIG_DUMMY_CONSOLE=y +CONFIG_FRAMEBUFFER_CONSOLE=y +CONFIG_FONTS=y +CONFIG_FONT_8x8=y +CONFIG_FONT_8x16=y +# CONFIG_FONT_6x11 is not set +# CONFIG_FONT_7x14 is not set +# CONFIG_FONT_PEARL_8x8 is not set +# CONFIG_FONT_ACORN_8x8 is not set +# CONFIG_FONT_MINI_4x6 is not set +# CONFIG_FONT_SUN8x16 is not set +# CONFIG_FONT_SUN12x22 is not set +# CONFIG_FONT_10x18 is not set + +# +# Logo configuration +# +# CONFIG_LOGO is not set +CONFIG_BACKLIGHT_LCD_SUPPORT=y +CONFIG_BACKLIGHT_CLASS_DEVICE=y +CONFIG_BACKLIGHT_DEVICE=y +# CONFIG_LCD_CLASS_DEVICE is not set +CONFIG_BACKLIGHT_CORGI=y + +# +# Sound +# +CONFIG_SOUND=y + +# +# Advanced Linux Sound Architecture +# +# CONFIG_SND is not set + +# +# Open Sound System +# +CONFIG_SOUND_PRIME=y +# CONFIG_SOUND_MSNDCLAS is not set +# CONFIG_SOUND_MSNDPIN is not set +CONFIG_SOUND_OSS=y +# CONFIG_SOUND_TRACEINIT is not set +# CONFIG_SOUND_DMAP is not set +# CONFIG_SOUND_AD1816 is not set +# CONFIG_SOUND_SGALAXY is not set +# CONFIG_SOUND_ADLIB is not set +# CONFIG_SOUND_ACI_MIXER is not set +# CONFIG_SOUND_CS4232 is not set +# CONFIG_SOUND_SSCAPE is not set +# CONFIG_SOUND_GUS is not set +# CONFIG_SOUND_VMIDI is not set +# CONFIG_SOUND_TRIX is not set +# CONFIG_SOUND_MSS is not set +# CONFIG_SOUND_MPU401 is not set +# CONFIG_SOUND_NM256 is not set +# CONFIG_SOUND_MAD16 is not set +# CONFIG_SOUND_PAS is not set +# CONFIG_SOUND_PSS is not set +# CONFIG_SOUND_SB is not set +# CONFIG_SOUND_AWE32_SYNTH is not set +# CONFIG_SOUND_WAVEFRONT is not set +# CONFIG_SOUND_MAUI is not set +# CONFIG_SOUND_YM3812 is not set +# CONFIG_SOUND_OPL3SA1 is not set +# CONFIG_SOUND_OPL3SA2 is not set +# CONFIG_SOUND_UART6850 is not set +# CONFIG_SOUND_AEDSP16 is not set +# CONFIG_SOUND_TVMIXER is not set +# CONFIG_SOUND_AD1980 is not set + +# +# USB support +# +CONFIG_USB_ARCH_HAS_HCD=y +# CONFIG_USB_ARCH_HAS_OHCI is not set +CONFIG_USB=m +# CONFIG_USB_DEBUG is not set + +# +# Miscellaneous USB options +# +CONFIG_USB_DEVICEFS=y +# CONFIG_USB_BANDWIDTH is not set +# CONFIG_USB_DYNAMIC_MINORS is not set +# CONFIG_USB_SUSPEND is not set +# CONFIG_USB_OTG is not set + +# +# USB Host Controller Drivers +# +# CONFIG_USB_ISP116X_HCD is not set +CONFIG_USB_SL811_HCD=m +CONFIG_USB_SL811_CS=m + +# +# USB Device Class drivers +# +# CONFIG_OBSOLETE_OSS_USB_DRIVER is not set + +# +# USB Bluetooth TTY can only be used with disabled Bluetooth subsystem +# +CONFIG_USB_ACM=m +CONFIG_USB_PRINTER=m + +# +# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' may also be needed; see USB_STORAGE Help for more information +# +CONFIG_USB_STORAGE=m +# CONFIG_USB_STORAGE_DEBUG is not set +# CONFIG_USB_STORAGE_DATAFAB is not set +# CONFIG_USB_STORAGE_FREECOM is not set +# CONFIG_USB_STORAGE_ISD200 is not set +# CONFIG_USB_STORAGE_DPCM is not set +# CONFIG_USB_STORAGE_USBAT is not set +# CONFIG_USB_STORAGE_SDDR09 is not set +# CONFIG_USB_STORAGE_SDDR55 is not set +# CONFIG_USB_STORAGE_JUMPSHOT is not set +# CONFIG_USB_STORAGE_ONETOUCH is not set + +# +# USB Input Devices +# +CONFIG_USB_HID=m +CONFIG_USB_HIDINPUT=y +# CONFIG_HID_FF is not set +# CONFIG_USB_HIDDEV is not set + +# +# USB HID Boot Protocol drivers +# +CONFIG_USB_KBD=m +CONFIG_USB_MOUSE=m +CONFIG_USB_AIPTEK=m +CONFIG_USB_WACOM=m +# CONFIG_USB_ACECAD is not set +CONFIG_USB_KBTAB=m +CONFIG_USB_POWERMATE=m +CONFIG_USB_MTOUCH=m +# CONFIG_USB_ITMTOUCH is not set +CONFIG_USB_EGALAX=m +# CONFIG_USB_YEALINK is not set +CONFIG_USB_XPAD=m +CONFIG_USB_ATI_REMOTE=m +# CONFIG_USB_KEYSPAN_REMOTE is not set +# CONFIG_USB_APPLETOUCH is not set + +# +# USB Imaging devices +# +CONFIG_USB_MDC800=m +CONFIG_USB_MICROTEK=m + +# +# USB Multimedia devices +# +CONFIG_USB_DABUSB=m +CONFIG_USB_VICAM=m +CONFIG_USB_DSBR=m +CONFIG_USB_IBMCAM=m +CONFIG_USB_KONICAWC=m +CONFIG_USB_OV511=m +CONFIG_USB_SE401=m +CONFIG_USB_SN9C102=m +CONFIG_USB_STV680=m +# CONFIG_USB_PWC is not set + +# +# USB Network Adapters +# +CONFIG_USB_CATC=m +CONFIG_USB_KAWETH=m +CONFIG_USB_PEGASUS=m +CONFIG_USB_RTL8150=m +CONFIG_USB_USBNET=m +CONFIG_USB_NET_AX8817X=m +CONFIG_USB_NET_CDCETHER=m +# CONFIG_USB_NET_GL620A is not set +CONFIG_USB_NET_NET1080=m +# CONFIG_USB_NET_PLUSB is not set +# CONFIG_USB_NET_RNDIS_HOST is not set +# CONFIG_USB_NET_CDC_SUBSET is not set +CONFIG_USB_NET_ZAURUS=m +# CONFIG_USB_ZD1201 is not set +CONFIG_USB_MON=y + +# +# USB port drivers +# + +# +# USB Serial Converter support +# +CONFIG_USB_SERIAL=m +CONFIG_USB_SERIAL_GENERIC=y +# CONFIG_USB_SERIAL_AIRPRIME is not set +CONFIG_USB_SERIAL_BELKIN=m +# CONFIG_USB_SERIAL_WHITEHEAT is not set +CONFIG_USB_SERIAL_DIGI_ACCELEPORT=m +# CONFIG_USB_SERIAL_CP2101 is not set +CONFIG_USB_SERIAL_CYPRESS_M8=m +CONFIG_USB_SERIAL_EMPEG=m +CONFIG_USB_SERIAL_FTDI_SIO=m +CONFIG_USB_SERIAL_VISOR=m +CONFIG_USB_SERIAL_IPAQ=m +CONFIG_USB_SERIAL_IR=m +CONFIG_USB_SERIAL_EDGEPORT=m +CONFIG_USB_SERIAL_EDGEPORT_TI=m +CONFIG_USB_SERIAL_GARMIN=m +CONFIG_USB_SERIAL_IPW=m +CONFIG_USB_SERIAL_KEYSPAN_PDA=m +CONFIG_USB_SERIAL_KEYSPAN=m +# CONFIG_USB_SERIAL_KEYSPAN_MPR is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA28 is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA28X is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA28XA is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA28XB is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA19 is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA18X is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA19W is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA19QW is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA19QI is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA49W is not set +# CONFIG_USB_SERIAL_KEYSPAN_USA49WLC is not set +CONFIG_USB_SERIAL_KLSI=m +CONFIG_USB_SERIAL_KOBIL_SCT=m +CONFIG_USB_SERIAL_MCT_U232=m +CONFIG_USB_SERIAL_PL2303=m +# CONFIG_USB_SERIAL_HP4X is not set +CONFIG_USB_SERIAL_SAFE=m +# CONFIG_USB_SERIAL_SAFE_PADDED is not set +CONFIG_USB_SERIAL_TI=m +CONFIG_USB_SERIAL_CYBERJACK=m +CONFIG_USB_SERIAL_XIRCOM=m +CONFIG_USB_SERIAL_OMNINET=m +CONFIG_USB_EZUSB=y + +# +# USB Miscellaneous drivers +# +CONFIG_USB_EMI62=m +CONFIG_USB_EMI26=m +CONFIG_USB_AUERSWALD=m +CONFIG_USB_RIO500=m +CONFIG_USB_LEGOTOWER=m +CONFIG_USB_LCD=m +CONFIG_USB_LED=m +CONFIG_USB_CYTHERM=m +CONFIG_USB_PHIDGETKIT=m +CONFIG_USB_PHIDGETSERVO=m +CONFIG_USB_IDMOUSE=m +# CONFIG_USB_LD is not set +# CONFIG_USB_TEST is not set + +# +# USB DSL modem support +# + +# +# USB Gadget Support +# +CONFIG_USB_GADGET=y +# CONFIG_USB_GADGET_DEBUG_FILES is not set +CONFIG_USB_GADGET_SELECTED=y +# CONFIG_USB_GADGET_NET2280 is not set +CONFIG_USB_GADGET_PXA2XX=y +CONFIG_USB_PXA2XX=y +# CONFIG_USB_PXA2XX_SMALL is not set +# CONFIG_USB_GADGET_GOKU is not set +# CONFIG_USB_GADGET_LH7A40X is not set +# CONFIG_USB_GADGET_OMAP is not set +# CONFIG_USB_GADGET_DUMMY_HCD is not set +# CONFIG_USB_GADGET_DUALSPEED is not set +CONFIG_USB_ZERO=m +CONFIG_USB_ETH=m +CONFIG_USB_ETH_RNDIS=y +CONFIG_USB_GADGETFS=m +CONFIG_USB_FILE_STORAGE=m +# CONFIG_USB_FILE_STORAGE_TEST is not set +CONFIG_USB_G_SERIAL=m + +# +# MMC/SD Card support +# +CONFIG_MMC=y +# CONFIG_MMC_DEBUG is not set +CONFIG_MMC_BLOCK=y +CONFIG_MMC_PXA=y +# CONFIG_MMC_WBSD is not set + +# +# File systems +# +CONFIG_EXT2_FS=y +# CONFIG_EXT2_FS_XATTR is not set +# CONFIG_EXT2_FS_XIP is not set +# CONFIG_EXT3_FS is not set +# CONFIG_JBD is not set +# CONFIG_REISERFS_FS is not set +# CONFIG_JFS_FS is not set +# CONFIG_FS_POSIX_ACL is not set +# CONFIG_XFS_FS is not set +# CONFIG_MINIX_FS is not set +# CONFIG_ROMFS_FS is not set +CONFIG_INOTIFY=y +# CONFIG_QUOTA is not set +CONFIG_DNOTIFY=y +# CONFIG_AUTOFS_FS is not set +# CONFIG_AUTOFS4_FS is not set +# CONFIG_FUSE_FS is not set + +# +# CD-ROM/DVD Filesystems +# +# CONFIG_ISO9660_FS is not set +# CONFIG_UDF_FS is not set + +# +# DOS/FAT/NT Filesystems +# +CONFIG_FAT_FS=y +CONFIG_MSDOS_FS=y +CONFIG_VFAT_FS=y +CONFIG_FAT_DEFAULT_CODEPAGE=437 +CONFIG_FAT_DEFAULT_IOCHARSET="iso8859-1" +# CONFIG_NTFS_FS is not set + +# +# Pseudo filesystems +# +CONFIG_PROC_FS=y +CONFIG_SYSFS=y +CONFIG_TMPFS=y +# CONFIG_HUGETLB_PAGE is not set +CONFIG_RAMFS=y +# CONFIG_RELAYFS_FS is not set + +# +# Miscellaneous filesystems +# +# CONFIG_ADFS_FS is not set +# CONFIG_AFFS_FS is not set +# CONFIG_HFS_FS is not set +# CONFIG_HFSPLUS_FS is not set +# CONFIG_BEFS_FS is not set +# CONFIG_BFS_FS is not set +# CONFIG_EFS_FS is not set +# CONFIG_JFFS_FS is not set +CONFIG_JFFS2_FS=y +CONFIG_JFFS2_FS_DEBUG=0 +CONFIG_JFFS2_FS_WRITEBUFFER=y +CONFIG_JFFS2_COMPRESSION_OPTIONS=y +CONFIG_JFFS2_ZLIB=y +CONFIG_JFFS2_RTIME=y +CONFIG_JFFS2_RUBIN=y +# CONFIG_JFFS2_CMODE_NONE is not set +CONFIG_JFFS2_CMODE_PRIORITY=y +# CONFIG_JFFS2_CMODE_SIZE is not set +CONFIG_CRAMFS=m +# CONFIG_VXFS_FS is not set +# CONFIG_HPFS_FS is not set +# CONFIG_QNX4FS_FS is not set +# CONFIG_SYSV_FS is not set +# CONFIG_UFS_FS is not set + +# +# Network File Systems +# +CONFIG_NFS_FS=m +CONFIG_NFS_V3=y +# CONFIG_NFS_V3_ACL is not set +CONFIG_NFS_V4=y +# CONFIG_NFS_DIRECTIO is not set +# CONFIG_NFSD is not set +CONFIG_LOCKD=m +CONFIG_LOCKD_V4=y +CONFIG_NFS_COMMON=y +CONFIG_SUNRPC=m +CONFIG_SUNRPC_GSS=m +CONFIG_RPCSEC_GSS_KRB5=m +# CONFIG_RPCSEC_GSS_SPKM3 is not set +CONFIG_SMB_FS=m +CONFIG_SMB_NLS_DEFAULT=y +CONFIG_SMB_NLS_REMOTE="cp437" +# CONFIG_CIFS is not set +# CONFIG_NCP_FS is not set +# CONFIG_CODA_FS is not set +# CONFIG_AFS_FS is not set +# CONFIG_9P_FS is not set + +# +# Partition Types +# +CONFIG_PARTITION_ADVANCED=y +# CONFIG_ACORN_PARTITION is not set +# CONFIG_OSF_PARTITION is not set +# CONFIG_AMIGA_PARTITION is not set +# CONFIG_ATARI_PARTITION is not set +# CONFIG_MAC_PARTITION is not set +CONFIG_MSDOS_PARTITION=y +# CONFIG_BSD_DISKLABEL is not set +# CONFIG_MINIX_SUBPARTITION is not set +# CONFIG_SOLARIS_X86_PARTITION is not set +# CONFIG_UNIXWARE_DISKLABEL is not set +# CONFIG_LDM_PARTITION is not set +# CONFIG_SGI_PARTITION is not set +# CONFIG_ULTRIX_PARTITION is not set +# CONFIG_SUN_PARTITION is not set +# CONFIG_EFI_PARTITION is not set + +# +# Native Language Support +# +CONFIG_NLS=y +CONFIG_NLS_DEFAULT="cp437" +CONFIG_NLS_CODEPAGE_437=y +# CONFIG_NLS_CODEPAGE_737 is not set +# CONFIG_NLS_CODEPAGE_775 is not set +# CONFIG_NLS_CODEPAGE_850 is not set +# CONFIG_NLS_CODEPAGE_852 is not set +# CONFIG_NLS_CODEPAGE_855 is not set +# CONFIG_NLS_CODEPAGE_857 is not set +# CONFIG_NLS_CODEPAGE_860 is not set +# CONFIG_NLS_CODEPAGE_861 is not set +# CONFIG_NLS_CODEPAGE_862 is not set +# CONFIG_NLS_CODEPAGE_863 is not set +# CONFIG_NLS_CODEPAGE_864 is not set +# CONFIG_NLS_CODEPAGE_865 is not set +# CONFIG_NLS_CODEPAGE_866 is not set +# CONFIG_NLS_CODEPAGE_869 is not set +# CONFIG_NLS_CODEPAGE_936 is not set +# CONFIG_NLS_CODEPAGE_950 is not set +# CONFIG_NLS_CODEPAGE_932 is not set +# CONFIG_NLS_CODEPAGE_949 is not set +# CONFIG_NLS_CODEPAGE_874 is not set +# CONFIG_NLS_ISO8859_8 is not set +# CONFIG_NLS_CODEPAGE_1250 is not set +# CONFIG_NLS_CODEPAGE_1251 is not set +# CONFIG_NLS_ASCII is not set +CONFIG_NLS_ISO8859_1=y +# CONFIG_NLS_ISO8859_2 is not set +# CONFIG_NLS_ISO8859_3 is not set +# CONFIG_NLS_ISO8859_4 is not set +# CONFIG_NLS_ISO8859_5 is not set +# CONFIG_NLS_ISO8859_6 is not set +# CONFIG_NLS_ISO8859_7 is not set +# CONFIG_NLS_ISO8859_9 is not set +# CONFIG_NLS_ISO8859_13 is not set +# CONFIG_NLS_ISO8859_14 is not set +# CONFIG_NLS_ISO8859_15 is not set +# CONFIG_NLS_KOI8_R is not set +# CONFIG_NLS_KOI8_U is not set +CONFIG_NLS_UTF8=y + +# +# Profiling support +# +CONFIG_PROFILING=y +CONFIG_OPROFILE=m + +# +# Kernel hacking +# +# CONFIG_PRINTK_TIME is not set +CONFIG_DEBUG_KERNEL=y +CONFIG_MAGIC_SYSRQ=y +CONFIG_LOG_BUF_SHIFT=14 +CONFIG_DETECT_SOFTLOCKUP=y +# CONFIG_SCHEDSTATS is not set +# CONFIG_DEBUG_SLAB is not set +# CONFIG_DEBUG_PREEMPT is not set +# CONFIG_DEBUG_SPINLOCK is not set +# CONFIG_DEBUG_SPINLOCK_SLEEP is not set +# CONFIG_DEBUG_KOBJECT is not set +CONFIG_DEBUG_BUGVERBOSE=y +# CONFIG_DEBUG_INFO is not set +# CONFIG_DEBUG_FS is not set +CONFIG_FRAME_POINTER=y +# CONFIG_DEBUG_USER is not set +# CONFIG_DEBUG_WAITQ is not set +CONFIG_DEBUG_ERRORS=y +CONFIG_DEBUG_LL=y +# CONFIG_DEBUG_ICEDCC is not set + +# +# Security options +# +# CONFIG_KEYS is not set +# CONFIG_SECURITY is not set + +# +# Cryptographic options +# +CONFIG_CRYPTO=y +CONFIG_CRYPTO_HMAC=y +CONFIG_CRYPTO_NULL=m +CONFIG_CRYPTO_MD4=m +CONFIG_CRYPTO_MD5=m +CONFIG_CRYPTO_SHA1=m +CONFIG_CRYPTO_SHA256=m +CONFIG_CRYPTO_SHA512=m +CONFIG_CRYPTO_WP512=m +# CONFIG_CRYPTO_TGR192 is not set +CONFIG_CRYPTO_DES=m +CONFIG_CRYPTO_BLOWFISH=m +CONFIG_CRYPTO_TWOFISH=m +CONFIG_CRYPTO_SERPENT=m +CONFIG_CRYPTO_AES=m +CONFIG_CRYPTO_CAST5=m +CONFIG_CRYPTO_CAST6=m +CONFIG_CRYPTO_TEA=m +CONFIG_CRYPTO_ARC4=m +CONFIG_CRYPTO_KHAZAD=m +CONFIG_CRYPTO_ANUBIS=m +CONFIG_CRYPTO_DEFLATE=m +CONFIG_CRYPTO_MICHAEL_MIC=m +CONFIG_CRYPTO_CRC32C=m +CONFIG_CRYPTO_TEST=m + +# +# Hardware crypto devices +# + +# +# Library routines +# +CONFIG_CRC_CCITT=y +# CONFIG_CRC16 is not set +CONFIG_CRC32=y +CONFIG_LIBCRC32C=m +CONFIG_ZLIB_INFLATE=y +CONFIG_ZLIB_DEFLATE=y -- cgit v1.2.3 From 71e2b2ecc1c44cb4f2f3e68827af8b90246becac Mon Sep 17 00:00:00 2001 From: Vincent Sanders Date: Mon, 10 Oct 2005 18:24:09 +0100 Subject: [ARM] 2968/1: defconfig for the ARM Collie platform Patch from Vincent Sanders Add a defconfig for the ARM Collie platform Signed-off-by: Richard Purdie Signed-off-by: Vincent Sanders Signed-off-by: Russell King --- arch/arm/configs/collie_defconfig | 888 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 888 insertions(+) create mode 100644 arch/arm/configs/collie_defconfig diff --git a/arch/arm/configs/collie_defconfig b/arch/arm/configs/collie_defconfig new file mode 100644 index 00000000000..40dfe07a8bc --- /dev/null +++ b/arch/arm/configs/collie_defconfig @@ -0,0 +1,888 @@ +# +# Automatically generated make config: don't edit +# Linux kernel version: 2.6.14-rc3 +# Sun Oct 9 16:55:14 2005 +# +CONFIG_ARM=y +CONFIG_MMU=y +CONFIG_UID16=y +CONFIG_RWSEM_GENERIC_SPINLOCK=y +CONFIG_GENERIC_CALIBRATE_DELAY=y + +# +# Code maturity level options +# +CONFIG_EXPERIMENTAL=y +# CONFIG_CLEAN_COMPILE is not set +CONFIG_BROKEN=y +CONFIG_BROKEN_ON_SMP=y +CONFIG_LOCK_KERNEL=y +CONFIG_INIT_ENV_ARG_LIMIT=32 + +# +# General setup +# +CONFIG_LOCALVERSION="" +CONFIG_LOCALVERSION_AUTO=y +CONFIG_SWAP=y +CONFIG_SYSVIPC=y +# CONFIG_POSIX_MQUEUE is not set +CONFIG_BSD_PROCESS_ACCT=y +# CONFIG_BSD_PROCESS_ACCT_V3 is not set +CONFIG_SYSCTL=y +# CONFIG_AUDIT is not set +CONFIG_HOTPLUG=y +CONFIG_KOBJECT_UEVENT=y +# CONFIG_IKCONFIG is not set +CONFIG_INITRAMFS_SOURCE="" +CONFIG_EMBEDDED=y +CONFIG_KALLSYMS=y +# CONFIG_KALLSYMS_ALL is not set +# CONFIG_KALLSYMS_EXTRA_PASS is not set +CONFIG_PRINTK=y +CONFIG_BUG=y +CONFIG_BASE_FULL=y +CONFIG_FUTEX=y +CONFIG_EPOLL=y +# CONFIG_CC_OPTIMIZE_FOR_SIZE is not set +CONFIG_SHMEM=y +CONFIG_CC_ALIGN_FUNCTIONS=0 +CONFIG_CC_ALIGN_LABELS=0 +CONFIG_CC_ALIGN_LOOPS=0 +CONFIG_CC_ALIGN_JUMPS=0 +# CONFIG_TINY_SHMEM is not set +CONFIG_BASE_SMALL=0 + +# +# Loadable module support +# +CONFIG_MODULES=y +CONFIG_MODULE_UNLOAD=y +CONFIG_MODULE_FORCE_UNLOAD=y +CONFIG_OBSOLETE_MODPARM=y +CONFIG_MODVERSIONS=y +# CONFIG_MODULE_SRCVERSION_ALL is not set +CONFIG_KMOD=y + +# +# System Type +# +# CONFIG_ARCH_CLPS7500 is not set +# CONFIG_ARCH_CLPS711X is not set +# CONFIG_ARCH_CO285 is not set +# CONFIG_ARCH_EBSA110 is not set +# CONFIG_ARCH_CAMELOT is not set +# CONFIG_ARCH_FOOTBRIDGE is not set +# CONFIG_ARCH_INTEGRATOR is not set +# CONFIG_ARCH_IOP3XX is not set +# CONFIG_ARCH_IXP4XX is not set +# CONFIG_ARCH_IXP2000 is not set +# CONFIG_ARCH_L7200 is not set +# CONFIG_ARCH_PXA is not set +# CONFIG_ARCH_RPC is not set +CONFIG_ARCH_SA1100=y +# CONFIG_ARCH_S3C2410 is not set +# CONFIG_ARCH_SHARK is not set +# CONFIG_ARCH_LH7A40X is not set +# CONFIG_ARCH_OMAP is not set +# CONFIG_ARCH_VERSATILE is not set +# CONFIG_ARCH_IMX is not set +# CONFIG_ARCH_H720X is not set +# CONFIG_ARCH_AAEC2000 is not set + +# +# SA11x0 Implementations +# +# CONFIG_SA1100_ASSABET is not set +# CONFIG_SA1100_CERF is not set +CONFIG_SA1100_COLLIE=y +# CONFIG_SA1100_H3100 is not set +# CONFIG_SA1100_H3600 is not set +# CONFIG_SA1100_H3800 is not set +# CONFIG_SA1100_BADGE4 is not set +# CONFIG_SA1100_JORNADA720 is not set +# CONFIG_SA1100_HACKKIT is not set +# CONFIG_SA1100_LART is not set +# CONFIG_SA1100_PLEB is not set +# CONFIG_SA1100_SHANNON is not set +# CONFIG_SA1100_SIMPAD is not set +# CONFIG_SA1100_SSP is not set + +# +# Processor Type +# +CONFIG_CPU_32=y +CONFIG_CPU_SA1100=y +CONFIG_CPU_32v4=y +CONFIG_CPU_ABRT_EV4=y +CONFIG_CPU_CACHE_V4WB=y +CONFIG_CPU_CACHE_VIVT=y +CONFIG_CPU_TLB_V4WB=y + +# +# Processor Features +# +CONFIG_SHARP_LOCOMO=y +CONFIG_SHARP_PARAM=y +CONFIG_SHARP_SCOOP=y + +# +# Bus support +# +CONFIG_ISA=y +CONFIG_ISA_DMA_API=y + +# +# PCCARD (PCMCIA/CardBus) support +# +# CONFIG_PCCARD is not set + +# +# Kernel Features +# +# CONFIG_SMP is not set +CONFIG_PREEMPT=y +# CONFIG_NO_IDLE_HZ is not set +CONFIG_ARCH_DISCONTIGMEM_ENABLE=y +CONFIG_SELECT_MEMORY_MODEL=y +# CONFIG_FLATMEM_MANUAL is not set +CONFIG_DISCONTIGMEM_MANUAL=y +# CONFIG_SPARSEMEM_MANUAL is not set +CONFIG_DISCONTIGMEM=y +CONFIG_FLAT_NODE_MEM_MAP=y +CONFIG_NEED_MULTIPLE_NODES=y +# CONFIG_SPARSEMEM_STATIC is not set +# CONFIG_LEDS is not set +CONFIG_ALIGNMENT_TRAP=y + +# +# Boot options +# +CONFIG_ZBOOT_ROM_TEXT=0x0 +CONFIG_ZBOOT_ROM_BSS=0x0 +CONFIG_CMDLINE="console=ttyS0,115200n8 console=tty1 noinitrd root=/dev/mtdblock2 rootfstype=jffs2 debug" +# CONFIG_XIP_KERNEL is not set + +# +# CPU Frequency scaling +# +# CONFIG_CPU_FREQ is not set + +# +# Floating point emulation +# + +# +# At least one emulation must be selected +# +CONFIG_FPE_NWFPE=y +# CONFIG_FPE_NWFPE_XP is not set +# CONFIG_FPE_FASTFPE is not set + +# +# Userspace binary formats +# +CONFIG_BINFMT_ELF=y +CONFIG_BINFMT_AOUT=m +CONFIG_BINFMT_MISC=m +# CONFIG_ARTHUR is not set + +# +# Power management options +# +CONFIG_PM=y +CONFIG_APM=y + +# +# Networking +# +CONFIG_NET=y + +# +# Networking options +# +CONFIG_PACKET=y +CONFIG_PACKET_MMAP=y +CONFIG_UNIX=y +# CONFIG_NET_KEY is not set +CONFIG_INET=y +# CONFIG_IP_MULTICAST is not set +# CONFIG_IP_ADVANCED_ROUTER is not set +CONFIG_IP_FIB_HASH=y +# CONFIG_IP_PNP is not set +# CONFIG_NET_IPIP is not set +# CONFIG_NET_IPGRE is not set +# CONFIG_ARPD is not set +CONFIG_SYN_COOKIES=y +# CONFIG_INET_AH is not set +# CONFIG_INET_ESP is not set +# CONFIG_INET_IPCOMP is not set +# CONFIG_INET_TUNNEL is not set +CONFIG_INET_DIAG=y +CONFIG_INET_TCP_DIAG=y +# CONFIG_TCP_CONG_ADVANCED is not set +CONFIG_TCP_CONG_BIC=y +# CONFIG_IPV6 is not set +# CONFIG_NETFILTER is not set + +# +# DCCP Configuration (EXPERIMENTAL) +# +# CONFIG_IP_DCCP is not set + +# +# SCTP Configuration (EXPERIMENTAL) +# +# CONFIG_IP_SCTP is not set +# CONFIG_ATM is not set +# CONFIG_BRIDGE is not set +# CONFIG_VLAN_8021Q is not set +# CONFIG_DECNET is not set +# CONFIG_LLC2 is not set +# CONFIG_IPX is not set +# CONFIG_ATALK is not set +# CONFIG_X25 is not set +# CONFIG_LAPB is not set +# CONFIG_NET_DIVERT is not set +# CONFIG_ECONET is not set +# CONFIG_WAN_ROUTER is not set +# CONFIG_NET_SCHED is not set +# CONFIG_NET_CLS_ROUTE is not set + +# +# Network testing +# +# CONFIG_NET_PKTGEN is not set +# CONFIG_HAMRADIO is not set +# CONFIG_IRDA is not set +# CONFIG_BT is not set +# CONFIG_IEEE80211 is not set + +# +# Device Drivers +# + +# +# Generic Driver Options +# +CONFIG_STANDALONE=y +CONFIG_PREVENT_FIRMWARE_BUILD=y +CONFIG_FW_LOADER=m +# CONFIG_DEBUG_DRIVER is not set + +# +# Memory Technology Devices (MTD) +# +CONFIG_MTD=y +# CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_CONCAT is not set +CONFIG_MTD_PARTITIONS=y +# CONFIG_MTD_REDBOOT_PARTS is not set +# CONFIG_MTD_CMDLINE_PARTS is not set +# CONFIG_MTD_AFS_PARTS is not set + +# +# User Modules And Translation Layers +# +CONFIG_MTD_CHAR=y +CONFIG_MTD_BLOCK=y +# CONFIG_FTL is not set +# CONFIG_NFTL is not set +# CONFIG_INFTL is not set + +# +# RAM/ROM/Flash chip drivers +# +# CONFIG_MTD_CFI is not set +# CONFIG_MTD_JEDECPROBE is not set +CONFIG_MTD_MAP_BANK_WIDTH_1=y +CONFIG_MTD_MAP_BANK_WIDTH_2=y +CONFIG_MTD_MAP_BANK_WIDTH_4=y +# CONFIG_MTD_MAP_BANK_WIDTH_8 is not set +# CONFIG_MTD_MAP_BANK_WIDTH_16 is not set +# CONFIG_MTD_MAP_BANK_WIDTH_32 is not set +CONFIG_MTD_CFI_I1=y +CONFIG_MTD_CFI_I2=y +# CONFIG_MTD_CFI_I4 is not set +# CONFIG_MTD_CFI_I8 is not set +# CONFIG_MTD_RAM is not set +# CONFIG_MTD_ROM is not set +# CONFIG_MTD_ABSENT is not set +CONFIG_MTD_OBSOLETE_CHIPS=y +# CONFIG_MTD_AMDSTD is not set +CONFIG_MTD_SHARP=y +# CONFIG_MTD_JEDEC is not set + +# +# Mapping drivers for chip access +# +# CONFIG_MTD_COMPLEX_MAPPINGS is not set +# CONFIG_MTD_PLATRAM is not set + +# +# Self-contained MTD device drivers +# +# CONFIG_MTD_SLRAM is not set +# CONFIG_MTD_PHRAM is not set +# CONFIG_MTD_MTDRAM is not set +# CONFIG_MTD_BLKMTD is not set +# CONFIG_MTD_BLOCK2MTD is not set + +# +# Disk-On-Chip Device Drivers +# +# CONFIG_MTD_DOC2000 is not set +# CONFIG_MTD_DOC2001 is not set +# CONFIG_MTD_DOC2001PLUS is not set + +# +# NAND Flash Device Drivers +# +# CONFIG_MTD_NAND is not set + +# +# Parallel port support +# +# CONFIG_PARPORT is not set + +# +# Plug and Play support +# +# CONFIG_PNP is not set + +# +# Block devices +# +# CONFIG_BLK_DEV_XD is not set +# CONFIG_BLK_DEV_COW_COMMON is not set +CONFIG_BLK_DEV_LOOP=y +# CONFIG_BLK_DEV_CRYPTOLOOP is not set +# CONFIG_BLK_DEV_NBD is not set +CONFIG_BLK_DEV_RAM=y +CONFIG_BLK_DEV_RAM_COUNT=16 +CONFIG_BLK_DEV_RAM_SIZE=1024 +CONFIG_BLK_DEV_INITRD=y +# CONFIG_CDROM_PKTCDVD is not set + +# +# IO Schedulers +# +CONFIG_IOSCHED_NOOP=y +CONFIG_IOSCHED_AS=y +CONFIG_IOSCHED_DEADLINE=y +CONFIG_IOSCHED_CFQ=y +CONFIG_ATA_OVER_ETH=m + +# +# ATA/ATAPI/MFM/RLL support +# +# CONFIG_IDE is not set + +# +# SCSI device support +# +# CONFIG_RAID_ATTRS is not set +# CONFIG_SCSI is not set + +# +# Multi-device support (RAID and LVM) +# +# CONFIG_MD is not set + +# +# Fusion MPT device support +# +# CONFIG_FUSION is not set + +# +# IEEE 1394 (FireWire) support +# +# CONFIG_IEEE1394 is not set + +# +# I2O device support +# + +# +# Network device support +# +# CONFIG_NETDEVICES is not set +# CONFIG_NETPOLL is not set +# CONFIG_NET_POLL_CONTROLLER is not set + +# +# ISDN subsystem +# +# CONFIG_ISDN is not set + +# +# Input device support +# +CONFIG_INPUT=y + +# +# Userland interfaces +# +# CONFIG_INPUT_MOUSEDEV is not set +# CONFIG_INPUT_JOYDEV is not set +CONFIG_INPUT_TSDEV=y +CONFIG_INPUT_TSDEV_SCREEN_X=240 +CONFIG_INPUT_TSDEV_SCREEN_Y=320 +CONFIG_INPUT_EVDEV=y +CONFIG_INPUT_EVBUG=y + +# +# Input Device Drivers +# +CONFIG_INPUT_KEYBOARD=y +# CONFIG_KEYBOARD_ATKBD is not set +# CONFIG_KEYBOARD_SUNKBD is not set +# CONFIG_KEYBOARD_LKKBD is not set +CONFIG_KEYBOARD_LOCOMO=y +# CONFIG_KEYBOARD_XTKBD is not set +# CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_INPUT_MOUSE is not set +# CONFIG_INPUT_JOYSTICK is not set +# CONFIG_INPUT_TOUCHSCREEN is not set +# CONFIG_INPUT_MISC is not set + +# +# Hardware I/O ports +# +CONFIG_SERIO=y +# CONFIG_SERIO_SERPORT is not set +# CONFIG_SERIO_LIBPS2 is not set +# CONFIG_SERIO_RAW is not set +# CONFIG_GAMEPORT is not set + +# +# Character devices +# +CONFIG_VT=y +CONFIG_VT_CONSOLE=y +CONFIG_HW_CONSOLE=y +# CONFIG_SERIAL_NONSTANDARD is not set + +# +# Serial drivers +# +# CONFIG_SERIAL_8250 is not set + +# +# Non-8250 serial port support +# +CONFIG_SERIAL_SA1100=y +CONFIG_SERIAL_SA1100_CONSOLE=y +CONFIG_SERIAL_CORE=y +CONFIG_SERIAL_CORE_CONSOLE=y +CONFIG_UNIX98_PTYS=y +# CONFIG_LEGACY_PTYS is not set + +# +# IPMI +# +# CONFIG_IPMI_HANDLER is not set + +# +# Watchdog Cards +# +# CONFIG_WATCHDOG is not set +# CONFIG_NVRAM is not set +# CONFIG_RTC is not set +# CONFIG_DTLK is not set +# CONFIG_R3964 is not set + +# +# Ftape, the floppy tape device driver +# +# CONFIG_RAW_DRIVER is not set + +# +# TPM devices +# + +# +# I2C support +# +CONFIG_I2C=m +# CONFIG_I2C_CHARDEV is not set + +# +# I2C Algorithms +# +CONFIG_I2C_ALGOBIT=m +# CONFIG_I2C_ALGOPCF is not set +# CONFIG_I2C_ALGOPCA is not set + +# +# I2C Hardware Bus support +# +# CONFIG_I2C_ELEKTOR is not set +# CONFIG_I2C_PARPORT_LIGHT is not set +# CONFIG_I2C_STUB is not set +# CONFIG_I2C_PCA_ISA is not set + +# +# Miscellaneous I2C Chip support +# +# CONFIG_SENSORS_DS1337 is not set +# CONFIG_SENSORS_DS1374 is not set +# CONFIG_SENSORS_EEPROM is not set +# CONFIG_SENSORS_PCF8574 is not set +# CONFIG_SENSORS_PCA9539 is not set +# CONFIG_SENSORS_PCF8591 is not set +# CONFIG_SENSORS_RTC8564 is not set +# CONFIG_SENSORS_MAX6875 is not set +# CONFIG_I2C_DEBUG_CORE is not set +# CONFIG_I2C_DEBUG_ALGO is not set +# CONFIG_I2C_DEBUG_BUS is not set +# CONFIG_I2C_DEBUG_CHIP is not set + +# +# Hardware Monitoring support +# +CONFIG_HWMON=y +# CONFIG_HWMON_VID is not set +# CONFIG_SENSORS_ADM1021 is not set +# CONFIG_SENSORS_ADM1025 is not set +# CONFIG_SENSORS_ADM1026 is not set +# CONFIG_SENSORS_ADM1031 is not set +# CONFIG_SENSORS_ADM9240 is not set +# CONFIG_SENSORS_ASB100 is not set +# CONFIG_SENSORS_ATXP1 is not set +# CONFIG_SENSORS_DS1621 is not set +# CONFIG_SENSORS_FSCHER is not set +# CONFIG_SENSORS_FSCPOS is not set +# CONFIG_SENSORS_GL518SM is not set +# CONFIG_SENSORS_GL520SM is not set +# CONFIG_SENSORS_IT87 is not set +# CONFIG_SENSORS_LM63 is not set +# CONFIG_SENSORS_LM75 is not set +# CONFIG_SENSORS_LM77 is not set +# CONFIG_SENSORS_LM78 is not set +# CONFIG_SENSORS_LM80 is not set +# CONFIG_SENSORS_LM83 is not set +# CONFIG_SENSORS_LM85 is not set +# CONFIG_SENSORS_LM87 is not set +# CONFIG_SENSORS_LM90 is not set +# CONFIG_SENSORS_LM92 is not set +# CONFIG_SENSORS_MAX1619 is not set +# CONFIG_SENSORS_PC87360 is not set +# CONFIG_SENSORS_SMSC47M1 is not set +# CONFIG_SENSORS_SMSC47B397 is not set +# CONFIG_SENSORS_W83781D is not set +# CONFIG_SENSORS_W83792D is not set +# CONFIG_SENSORS_W83L785TS is not set +# CONFIG_SENSORS_W83627HF is not set +# CONFIG_SENSORS_W83627EHF is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Misc devices +# + +# +# Multimedia Capabilities Port drivers +# +# CONFIG_MCP_SA11X0 is not set + +# +# Multimedia devices +# +CONFIG_VIDEO_DEV=m + +# +# Video For Linux +# + +# +# Video Adapters +# +# CONFIG_VIDEO_PMS is not set +# CONFIG_VIDEO_CPIA is not set +# CONFIG_VIDEO_SAA5246A is not set +# CONFIG_VIDEO_SAA5249 is not set +# CONFIG_TUNER_3036 is not set +# CONFIG_VIDEO_OVCAMCHIP is not set + +# +# Radio Adapters +# +# CONFIG_RADIO_CADET is not set +# CONFIG_RADIO_RTRACK is not set +# CONFIG_RADIO_RTRACK2 is not set +# CONFIG_RADIO_AZTECH is not set +# CONFIG_RADIO_GEMTEK is not set +# CONFIG_RADIO_MAESTRO is not set +# CONFIG_RADIO_SF16FMI is not set +# CONFIG_RADIO_SF16FMR2 is not set +# CONFIG_RADIO_TERRATEC is not set +# CONFIG_RADIO_TRUST is not set +# CONFIG_RADIO_TYPHOON is not set +# CONFIG_RADIO_ZOLTRIX is not set + +# +# Digital Video Broadcasting Devices +# +# CONFIG_DVB is not set + +# +# Graphics support +# +CONFIG_FB=y +CONFIG_FB_CFB_FILLRECT=y +CONFIG_FB_CFB_COPYAREA=y +CONFIG_FB_CFB_IMAGEBLIT=y +CONFIG_FB_SOFT_CURSOR=y +# CONFIG_FB_MACMODES is not set +CONFIG_FB_MODE_HELPERS=y +# CONFIG_FB_TILEBLITTING is not set +CONFIG_FB_SA1100=y +# CONFIG_FB_S1D13XXX is not set +# CONFIG_FB_VIRTUAL is not set + +# +# Console display driver support +# +# CONFIG_VGA_CONSOLE is not set +# CONFIG_MDA_CONSOLE is not set +CONFIG_DUMMY_CONSOLE=y +CONFIG_FRAMEBUFFER_CONSOLE=y +CONFIG_FONTS=y +CONFIG_FONT_8x8=y +# CONFIG_FONT_8x16 is not set +# CONFIG_FONT_6x11 is not set +# CONFIG_FONT_7x14 is not set +# CONFIG_FONT_PEARL_8x8 is not set +# CONFIG_FONT_ACORN_8x8 is not set +# CONFIG_FONT_MINI_4x6 is not set +# CONFIG_FONT_SUN8x16 is not set +# CONFIG_FONT_SUN12x22 is not set +# CONFIG_FONT_10x18 is not set + +# +# Logo configuration +# +# CONFIG_LOGO is not set +# CONFIG_BACKLIGHT_LCD_SUPPORT is not set + +# +# Sound +# +# CONFIG_SOUND is not set + +# +# USB support +# +CONFIG_USB_ARCH_HAS_HCD=y +# CONFIG_USB_ARCH_HAS_OHCI is not set +# CONFIG_USB is not set + +# +# USB Gadget Support +# +CONFIG_USB_GADGET=y +# CONFIG_USB_GADGET_DEBUG_FILES is not set +# CONFIG_USB_GADGET_NET2280 is not set +# CONFIG_USB_GADGET_PXA2XX is not set +# CONFIG_USB_GADGET_GOKU is not set +# CONFIG_USB_GADGET_LH7A40X is not set +# CONFIG_USB_GADGET_OMAP is not set +# CONFIG_USB_GADGET_DUMMY_HCD is not set +# CONFIG_USB_GADGET_DUALSPEED is not set + +# +# MMC/SD Card support +# +# CONFIG_MMC is not set + +# +# File systems +# +CONFIG_EXT2_FS=y +CONFIG_EXT2_FS_XATTR=y +CONFIG_EXT2_FS_POSIX_ACL=y +CONFIG_EXT2_FS_SECURITY=y +# CONFIG_EXT2_FS_XIP is not set +# CONFIG_EXT3_FS is not set +# CONFIG_JBD is not set +CONFIG_FS_MBCACHE=y +# CONFIG_REISERFS_FS is not set +# CONFIG_JFS_FS is not set +CONFIG_FS_POSIX_ACL=y +# CONFIG_XFS_FS is not set +# CONFIG_MINIX_FS is not set +CONFIG_ROMFS_FS=y +CONFIG_INOTIFY=y +# CONFIG_QUOTA is not set +# CONFIG_DNOTIFY is not set +# CONFIG_AUTOFS_FS is not set +# CONFIG_AUTOFS4_FS is not set +# CONFIG_FUSE_FS is not set + +# +# CD-ROM/DVD Filesystems +# +# CONFIG_ISO9660_FS is not set +# CONFIG_UDF_FS is not set + +# +# DOS/FAT/NT Filesystems +# +CONFIG_FAT_FS=y +CONFIG_MSDOS_FS=y +CONFIG_VFAT_FS=y +CONFIG_FAT_DEFAULT_CODEPAGE=437 +CONFIG_FAT_DEFAULT_IOCHARSET="iso8859-1" +# CONFIG_NTFS_FS is not set + +# +# Pseudo filesystems +# +CONFIG_PROC_FS=y +CONFIG_SYSFS=y +CONFIG_TMPFS=y +# CONFIG_HUGETLBFS is not set +# CONFIG_HUGETLB_PAGE is not set +CONFIG_RAMFS=y +# CONFIG_RELAYFS_FS is not set + +# +# Miscellaneous filesystems +# +# CONFIG_ADFS_FS is not set +# CONFIG_AFFS_FS is not set +# CONFIG_HFS_FS is not set +# CONFIG_HFSPLUS_FS is not set +# CONFIG_BEFS_FS is not set +# CONFIG_BFS_FS is not set +# CONFIG_EFS_FS is not set +# CONFIG_JFFS_FS is not set +CONFIG_JFFS2_FS=y +CONFIG_JFFS2_FS_DEBUG=0 +CONFIG_JFFS2_FS_WRITEBUFFER=y +# CONFIG_JFFS2_COMPRESSION_OPTIONS is not set +CONFIG_JFFS2_ZLIB=y +CONFIG_JFFS2_RTIME=y +# CONFIG_JFFS2_RUBIN is not set +CONFIG_CRAMFS=y +# CONFIG_VXFS_FS is not set +# CONFIG_HPFS_FS is not set +# CONFIG_QNX4FS_FS is not set +# CONFIG_SYSV_FS is not set +# CONFIG_UFS_FS is not set + +# +# Network File Systems +# +# CONFIG_NFS_FS is not set +# CONFIG_NFSD is not set +# CONFIG_SMB_FS is not set +# CONFIG_CIFS is not set +# CONFIG_NCP_FS is not set +# CONFIG_CODA_FS is not set +# CONFIG_AFS_FS is not set +# CONFIG_9P_FS is not set + +# +# Partition Types +# +# CONFIG_PARTITION_ADVANCED is not set +CONFIG_MSDOS_PARTITION=y + +# +# Native Language Support +# +CONFIG_NLS=y +CONFIG_NLS_DEFAULT="cp437" +CONFIG_NLS_CODEPAGE_437=m +# CONFIG_NLS_CODEPAGE_737 is not set +# CONFIG_NLS_CODEPAGE_775 is not set +# CONFIG_NLS_CODEPAGE_850 is not set +# CONFIG_NLS_CODEPAGE_852 is not set +# CONFIG_NLS_CODEPAGE_855 is not set +# CONFIG_NLS_CODEPAGE_857 is not set +# CONFIG_NLS_CODEPAGE_860 is not set +# CONFIG_NLS_CODEPAGE_861 is not set +# CONFIG_NLS_CODEPAGE_862 is not set +# CONFIG_NLS_CODEPAGE_863 is not set +# CONFIG_NLS_CODEPAGE_864 is not set +# CONFIG_NLS_CODEPAGE_865 is not set +# CONFIG_NLS_CODEPAGE_866 is not set +# CONFIG_NLS_CODEPAGE_869 is not set +# CONFIG_NLS_CODEPAGE_936 is not set +# CONFIG_NLS_CODEPAGE_950 is not set +# CONFIG_NLS_CODEPAGE_932 is not set +# CONFIG_NLS_CODEPAGE_949 is not set +# CONFIG_NLS_CODEPAGE_874 is not set +# CONFIG_NLS_ISO8859_8 is not set +# CONFIG_NLS_CODEPAGE_1250 is not set +# CONFIG_NLS_CODEPAGE_1251 is not set +# CONFIG_NLS_ASCII is not set +CONFIG_NLS_ISO8859_1=m +# CONFIG_NLS_ISO8859_2 is not set +# CONFIG_NLS_ISO8859_3 is not set +# CONFIG_NLS_ISO8859_4 is not set +# CONFIG_NLS_ISO8859_5 is not set +# CONFIG_NLS_ISO8859_6 is not set +# CONFIG_NLS_ISO8859_7 is not set +# CONFIG_NLS_ISO8859_9 is not set +# CONFIG_NLS_ISO8859_13 is not set +# CONFIG_NLS_ISO8859_14 is not set +# CONFIG_NLS_ISO8859_15 is not set +# CONFIG_NLS_KOI8_R is not set +# CONFIG_NLS_KOI8_U is not set +CONFIG_NLS_UTF8=m + +# +# Profiling support +# +# CONFIG_PROFILING is not set + +# +# Kernel hacking +# +# CONFIG_PRINTK_TIME is not set +CONFIG_DEBUG_KERNEL=y +CONFIG_MAGIC_SYSRQ=y +CONFIG_LOG_BUF_SHIFT=14 +CONFIG_DETECT_SOFTLOCKUP=y +# CONFIG_SCHEDSTATS is not set +# CONFIG_DEBUG_SLAB is not set +CONFIG_DEBUG_PREEMPT=y +# CONFIG_DEBUG_SPINLOCK is not set +# CONFIG_DEBUG_SPINLOCK_SLEEP is not set +# CONFIG_DEBUG_KOBJECT is not set +# CONFIG_DEBUG_BUGVERBOSE is not set +# CONFIG_DEBUG_INFO is not set +# CONFIG_DEBUG_FS is not set +CONFIG_FRAME_POINTER=y +# CONFIG_DEBUG_USER is not set +# CONFIG_DEBUG_WAITQ is not set +CONFIG_DEBUG_ERRORS=y +# CONFIG_DEBUG_LL is not set + +# +# Security options +# +# CONFIG_KEYS is not set +# CONFIG_SECURITY is not set + +# +# Cryptographic options +# +# CONFIG_CRYPTO is not set + +# +# Hardware crypto devices +# + +# +# Library routines +# +# CONFIG_CRC_CCITT is not set +# CONFIG_CRC16 is not set +CONFIG_CRC32=y +# CONFIG_LIBCRC32C is not set +CONFIG_ZLIB_INFLATE=y +CONFIG_ZLIB_DEFLATE=y -- cgit v1.2.3 From 094804c5a132f04c12dd4902ee15c64362e5c1af Mon Sep 17 00:00:00 2001 From: Andi Kleen Date: Tue, 11 Oct 2005 01:03:39 +0200 Subject: [PATCH] x86_64: Fix change_page_attr cache flushing Noticed by Terence Ripperda Undo wrong change in global_flush_tlb. We need to flush the caches in all cases, not just when pages were reverted. This was a bogus optimization added earlier, but it was wrong. Signed-off-by: Andi Kleen Signed-off-by: Linus Torvalds --- arch/x86_64/mm/pageattr.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/arch/x86_64/mm/pageattr.c b/arch/x86_64/mm/pageattr.c index 94862e1ec03..b90e8fe9eeb 100644 --- a/arch/x86_64/mm/pageattr.c +++ b/arch/x86_64/mm/pageattr.c @@ -220,8 +220,6 @@ void global_flush_tlb(void) down_read(&init_mm.mmap_sem); df = xchg(&df_list, NULL); up_read(&init_mm.mmap_sem); - if (!df) - return; flush_map((df && !df->next) ? df->address : 0); for (; df; df = next_df) { next_df = df->next; -- cgit v1.2.3 From 5d8e1b181c4ad63e6ca90d51287b31afd400d2eb Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Mon, 10 Oct 2005 16:12:13 -0700 Subject: [SPARC64]: Fix Ultra5, Ultra60, et al. boot failures. On the boot processor, we need to do the move onto the Linux trap table a little bit differently else we'll take unhandlable faults in the firmware address space. Previously we would do the following: 1) Disable PSTATE_IE in %pstate. 2) Set %tba by hand to sparc64_ttable_tl0 3) Initialize alternate, mmu, and interrupt global trap registers. 4) Call prom_set_traptable() That doesn't work very well actually with the way we boot the kernel VM these days. It worked by luck on many systems because the firmware accesses for the prom_set_traptable() call happened to be loaded into the TLB already, something we cannot assume. So the new scheme is this: 1) Clear PSTATE_IE in %pstate and set %pil to 15 2) Call prom_set_traptable() 3) Initialize alternate, mmu, and interrupt global trap registers. and this works quite well. This sequence has been moved into a callable function in assembler named setup-trap_table(). The idea is that eventually trampoline.S can use this code as well. That isn't possible currently due to some complications, but eventually we should be able to do it. Thanks to Meelis Roos for the Ultra5 boot failure report. Signed-off-by: David S. Miller --- arch/sparc64/kernel/head.S | 127 ++++++++++++++++++++++++++++++++------------- 1 file changed, 91 insertions(+), 36 deletions(-) diff --git a/arch/sparc64/kernel/head.S b/arch/sparc64/kernel/head.S index 24340496cdd..f1dcdf8f743 100644 --- a/arch/sparc64/kernel/head.S +++ b/arch/sparc64/kernel/head.S @@ -382,32 +382,79 @@ tlb_fixup_done: nop /* Not reached... */ -/* IMPORTANT NOTE: Whenever making changes here, check - * trampoline.S as well. -jj */ - .globl setup_tba -setup_tba: /* i0 = is_starfire */ - save %sp, -160, %sp + /* This is meant to allow the sharing of this code between + * boot processor invocation (via setup_tba() below) and + * secondary processor startup (via trampoline.S). The + * former does use this code, the latter does not yet due + * to some complexities. That should be fixed up at some + * point. + */ + .globl setup_trap_table +setup_trap_table: + save %sp, -192, %sp + + /* Force interrupts to be disabled. Transferring over to + * the Linux trap table is a very delicate operation. + * Until we are actually on the Linux trap table, we cannot + * get the PAGE_OFFSET linear mappings translated. We need + * that mapping to be setup in order to initialize the firmware + * page tables. + * + * So there is this window of time, from the return from + * prom_set_trap_table() until inherit_prom_mappings_post() + * (in arch/sparc64/mm/init.c) completes, during which no + * firmware address space accesses can be made. + */ + rdpr %pstate, %o1 + andn %o1, PSTATE_IE, %o1 + wrpr %o1, 0x0, %pstate + wrpr %g0, 15, %pil - rdpr %tba, %g7 - sethi %hi(prom_tba), %o1 - or %o1, %lo(prom_tba), %o1 - stx %g7, [%o1] + /* Ok, now make the final valid firmware call to jump over + * to the Linux trap table. + */ + call prom_set_trap_table + sethi %hi(sparc64_ttable_tl0), %o0 + + /* Start using proper page size encodings in ctx register. */ + sethi %hi(sparc64_kern_pri_context), %g3 + ldx [%g3 + %lo(sparc64_kern_pri_context)], %g2 + mov PRIMARY_CONTEXT, %g1 + stxa %g2, [%g1] ASI_DMMU + membar #Sync + + /* The Linux trap handlers expect various trap global registers + * to be setup with some fixed values. So here we set these + * up very carefully. These globals are: + * + * Alternate Globals (PSTATE_AG): + * + * %g6 --> current_thread_info() + * + * MMU Globals (PSTATE_MG): + * + * %g1 --> TLB_SFSR + * %g2 --> ((_PAGE_VALID | _PAGE_SZ4MB | + * _PAGE_CP | _PAGE_CV | _PAGE_P | _PAGE_W) + * ^ 0xfffff80000000000) + * (this %g2 value is used for computing the PAGE_OFFSET kernel + * TLB entries quickly, the virtual address of the fault XOR'd + * with this %g2 value is the PTE to load into the TLB) + * %g3 --> VPTE_BASE_CHEETAH or VPTE_BASE_SPITFIRE + * + * Interrupt Globals (PSTATE_IG, setup by init_irqwork_curcpu()): + * + * %g6 --> __irq_work[smp_processor_id()] + */ - /* Setup "Linux" globals 8-) */ rdpr %pstate, %o1 mov %g6, %o2 - wrpr %o1, (PSTATE_AG|PSTATE_IE), %pstate - sethi %hi(sparc64_ttable_tl0), %g1 - wrpr %g1, %tba + wrpr %o1, PSTATE_AG, %pstate mov %o2, %g6 - /* Set up MMU globals */ - wrpr %o1, (PSTATE_MG|PSTATE_IE), %pstate - - /* Set fixed globals used by dTLB miss handler. */ #define KERN_HIGHBITS ((_PAGE_VALID|_PAGE_SZ4MB)^0xfffff80000000000) #define KERN_LOWBITS (_PAGE_CP | _PAGE_CV | _PAGE_P | _PAGE_W) - + wrpr %o1, PSTATE_MG, %pstate mov TSB_REG, %g1 stxa %g0, [%g1] ASI_DMMU membar #Sync @@ -419,17 +466,17 @@ setup_tba: /* i0 = is_starfire */ sllx %g2, 32, %g2 or %g2, KERN_LOWBITS, %g2 - BRANCH_IF_ANY_CHEETAH(g3,g7,cheetah_vpte_base) - ba,pt %xcc, spitfire_vpte_base + BRANCH_IF_ANY_CHEETAH(g3,g7,8f) + ba,pt %xcc, 9f nop -cheetah_vpte_base: +8: sethi %uhi(VPTE_BASE_CHEETAH), %g3 or %g3, %ulo(VPTE_BASE_CHEETAH), %g3 ba,pt %xcc, 2f sllx %g3, 32, %g3 -spitfire_vpte_base: +9: sethi %uhi(VPTE_BASE_SPITFIRE), %g3 or %g3, %ulo(VPTE_BASE_SPITFIRE), %g3 sllx %g3, 32, %g3 @@ -455,29 +502,37 @@ spitfire_vpte_base: sllx %o2, 32, %o2 wr %o2, %asr25 - /* Ok, we're done setting up all the state our trap mechanims needs, - * now get back into normal globals and let the PROM know what is up. - */ 2: wrpr %g0, %g0, %wstate - wrpr %o1, PSTATE_IE, %pstate + wrpr %o1, 0x0, %pstate call init_irqwork_curcpu nop - call prom_set_trap_table - sethi %hi(sparc64_ttable_tl0), %o0 - - /* Start using proper page size encodings in ctx register. */ - sethi %hi(sparc64_kern_pri_context), %g3 - ldx [%g3 + %lo(sparc64_kern_pri_context)], %g2 - mov PRIMARY_CONTEXT, %g1 - stxa %g2, [%g1] ASI_DMMU - membar #Sync - + /* Now we can turn interrupts back on. */ rdpr %pstate, %o1 or %o1, PSTATE_IE, %o1 wrpr %o1, 0, %pstate + wrpr %g0, 0x0, %pil + + ret + restore + + .globl setup_tba +setup_tba: /* i0 = is_starfire */ + save %sp, -192, %sp + + /* The boot processor is the only cpu which invokes this + * routine, the other cpus set things up via trampoline.S. + * So save the OBP trap table address here. + */ + rdpr %tba, %g7 + sethi %hi(prom_tba), %o1 + or %o1, %lo(prom_tba), %o1 + stx %g7, [%o1] + + call setup_trap_table + nop ret restore -- cgit v1.2.3 From 46113830a18847cff8da73005e57bc49c2f95a56 Mon Sep 17 00:00:00 2001 From: Harald Welte Date: Mon, 10 Oct 2005 19:44:29 +0200 Subject: [PATCH] Fix signal sending in usbdevio on async URB completion If a process issues an URB from userspace and (starts to) terminate before the URB comes back, we run into the issue described above. This is because the urb saves a pointer to "current" when it is posted to the device, but there's no guarantee that this pointer is still valid afterwards. In fact, there are three separate issues: 1) the pointer to "current" can become invalid, since the task could be completely gone when the URB completion comes back from the device. 2) Even if the saved task pointer is still pointing to a valid task_struct, task_struct->sighand could have gone meanwhile. 3) Even if the process is perfectly fine, permissions may have changed, and we can no longer send it a signal. So what we do instead, is to save the PID and uid's of the process, and introduce a new kill_proc_info_as_uid() function. Signed-off-by: Harald Welte [ Fixed up types and added symbol exports ] Signed-off-by: Linus Torvalds --- drivers/usb/core/devio.c | 12 +++++++++--- include/linux/sched.h | 1 + kernel/signal.c | 34 ++++++++++++++++++++++++++++++++++ 3 files changed, 44 insertions(+), 3 deletions(-) diff --git a/drivers/usb/core/devio.c b/drivers/usb/core/devio.c index b4265aa7d45..6c35dcbea66 100644 --- a/drivers/usb/core/devio.c +++ b/drivers/usb/core/devio.c @@ -30,6 +30,8 @@ * Revision history * 22.12.1999 0.1 Initial release (split from proc_usb.c) * 04.01.2000 0.2 Turned into its own filesystem + * 30.09.2005 0.3 Fix user-triggerable oops in async URB delivery + * (CAN-2005-3055) */ /*****************************************************************************/ @@ -58,7 +60,8 @@ static struct class *usb_device_class; struct async { struct list_head asynclist; struct dev_state *ps; - struct task_struct *task; + pid_t pid; + uid_t uid, euid; unsigned int signr; unsigned int ifnum; void __user *userbuffer; @@ -290,7 +293,8 @@ static void async_completed(struct urb *urb, struct pt_regs *regs) sinfo.si_errno = as->urb->status; sinfo.si_code = SI_ASYNCIO; sinfo.si_addr = as->userurb; - send_sig_info(as->signr, &sinfo, as->task); + kill_proc_info_as_uid(as->signr, &sinfo, as->pid, as->uid, + as->euid); } wake_up(&ps->wait); } @@ -988,7 +992,9 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, as->userbuffer = NULL; as->signr = uurb->signr; as->ifnum = ifnum; - as->task = current; + as->pid = current->pid; + as->uid = current->uid; + as->euid = current->euid; if (!(uurb->endpoint & USB_DIR_IN)) { if (copy_from_user(as->urb->transfer_buffer, uurb->buffer, as->urb->transfer_buffer_length)) { free_async(as); diff --git a/include/linux/sched.h b/include/linux/sched.h index c3ba31f210a..27519df0f98 100644 --- a/include/linux/sched.h +++ b/include/linux/sched.h @@ -1018,6 +1018,7 @@ extern int force_sig_info(int, struct siginfo *, struct task_struct *); extern int __kill_pg_info(int sig, struct siginfo *info, pid_t pgrp); extern int kill_pg_info(int, struct siginfo *, pid_t); extern int kill_proc_info(int, struct siginfo *, pid_t); +extern int kill_proc_info_as_uid(int, struct siginfo *, pid_t, uid_t, uid_t); extern void do_notify_parent(struct task_struct *, int); extern void force_sig(int, struct task_struct *); extern void force_sig_specific(int, struct task_struct *); diff --git a/kernel/signal.c b/kernel/signal.c index cba193ceda0..50c99264377 100644 --- a/kernel/signal.c +++ b/kernel/signal.c @@ -1193,6 +1193,40 @@ kill_proc_info(int sig, struct siginfo *info, pid_t pid) return error; } +/* like kill_proc_info(), but doesn't use uid/euid of "current" */ +int kill_proc_info_as_uid(int sig, struct siginfo *info, pid_t pid, + uid_t uid, uid_t euid) +{ + int ret = -EINVAL; + struct task_struct *p; + + if (!valid_signal(sig)) + return ret; + + read_lock(&tasklist_lock); + p = find_task_by_pid(pid); + if (!p) { + ret = -ESRCH; + goto out_unlock; + } + if ((!info || ((unsigned long)info != 1 && + (unsigned long)info != 2 && SI_FROMUSER(info))) + && (euid != p->suid) && (euid != p->uid) + && (uid != p->suid) && (uid != p->uid)) { + ret = -EPERM; + goto out_unlock; + } + if (sig && p->sighand) { + unsigned long flags; + spin_lock_irqsave(&p->sighand->siglock, flags); + ret = __group_send_sig_info(sig, info, p); + spin_unlock_irqrestore(&p->sighand->siglock, flags); + } +out_unlock: + read_unlock(&tasklist_lock); + return ret; +} +EXPORT_SYMBOL_GPL(kill_proc_info_as_uid); /* * kill_something_info() interprets pid in interesting ways just like kill(2). -- cgit v1.2.3 From d7dd8a72ab8d305fbe1c4bb571e0633eba3a8d23 Mon Sep 17 00:00:00 2001 From: Linus Torvalds Date: Mon, 10 Oct 2005 16:31:30 -0700 Subject: Use the new "kill_proc_info_as_uid()" for USB disconnect too All the same issues - we can't just save the pointer to the thread, we must save the pid/uid/euid combination. Signed-off-by: Linus Torvalds --- drivers/usb/core/devio.c | 4 +++- drivers/usb/core/inode.c | 2 +- drivers/usb/core/usb.h | 3 ++- 3 files changed, 6 insertions(+), 3 deletions(-) diff --git a/drivers/usb/core/devio.c b/drivers/usb/core/devio.c index 6c35dcbea66..487ff672b10 100644 --- a/drivers/usb/core/devio.c +++ b/drivers/usb/core/devio.c @@ -530,7 +530,9 @@ static int usbdev_open(struct inode *inode, struct file *file) INIT_LIST_HEAD(&ps->async_completed); init_waitqueue_head(&ps->wait); ps->discsignr = 0; - ps->disctask = current; + ps->disc_pid = current->pid; + ps->disc_uid = current->uid; + ps->disc_euid = current->euid; ps->disccontext = NULL; ps->ifclaimed = 0; wmb(); diff --git a/drivers/usb/core/inode.c b/drivers/usb/core/inode.c index 640f41e4702..d07bba01995 100644 --- a/drivers/usb/core/inode.c +++ b/drivers/usb/core/inode.c @@ -713,7 +713,7 @@ void usbfs_remove_device(struct usb_device *dev) sinfo.si_errno = EPIPE; sinfo.si_code = SI_ASYNCIO; sinfo.si_addr = ds->disccontext; - send_sig_info(ds->discsignr, &sinfo, ds->disctask); + kill_proc_info_as_uid(ds->discsignr, &sinfo, ds->disc_pid, ds->disc_uid, ds->disc_euid); } } usbfs_update_special(); diff --git a/drivers/usb/core/usb.h b/drivers/usb/core/usb.h index 83d48c8133a..e6504f3370a 100644 --- a/drivers/usb/core/usb.h +++ b/drivers/usb/core/usb.h @@ -52,7 +52,8 @@ struct dev_state { struct list_head async_completed; wait_queue_head_t wait; /* wake up if a request completed */ unsigned int discsignr; - struct task_struct *disctask; + pid_t disc_pid; + uid_t disc_uid, disc_euid; void __user *disccontext; unsigned long ifclaimed; }; -- cgit v1.2.3 From 421c7ce6d001fce28b1fa8fdd2e7ded0ed8a0ad5 Mon Sep 17 00:00:00 2001 From: Andi Kleen Date: Mon, 10 Oct 2005 22:32:45 +0200 Subject: [PATCH] x86_64: Allocate cpu local data for all possible CPUs CPU hotplug fills up the possible map to NR_CPUs, but it did that after setting up per CPU data. This lead to CPU data not getting allocated for all possible CPUs, which lead to various side effects. Signed-off-by: Andi Kleen Signed-off-by: Linus Torvalds --- arch/x86_64/kernel/setup64.c | 4 ++++ arch/x86_64/kernel/smpboot.c | 6 +----- include/asm-x86_64/smp.h | 1 + 3 files changed, 6 insertions(+), 5 deletions(-) diff --git a/arch/x86_64/kernel/setup64.c b/arch/x86_64/kernel/setup64.c index bd33be24a38..79190891fbc 100644 --- a/arch/x86_64/kernel/setup64.c +++ b/arch/x86_64/kernel/setup64.c @@ -87,6 +87,10 @@ void __init setup_per_cpu_areas(void) int i; unsigned long size; +#ifdef CONFIG_HOTPLUG_CPU + prefill_possible_map(); +#endif + /* Copy section for each CPU (we discard the original) */ size = ALIGN(__per_cpu_end - __per_cpu_start, SMP_CACHE_BYTES); #ifdef CONFIG_MODULES diff --git a/arch/x86_64/kernel/smpboot.c b/arch/x86_64/kernel/smpboot.c index e12d7baeb33..658a81b33f3 100644 --- a/arch/x86_64/kernel/smpboot.c +++ b/arch/x86_64/kernel/smpboot.c @@ -892,7 +892,7 @@ static __init void disable_smp(void) * those NR_CPUS, hence cpu_possible_map represents entire NR_CPUS range. * - Ashok Raj */ -static void prefill_possible_map(void) +__init void prefill_possible_map(void) { int i; for (i = 0; i < NR_CPUS; i++) @@ -967,10 +967,6 @@ void __init smp_prepare_cpus(unsigned int max_cpus) current_cpu_data = boot_cpu_data; current_thread_info()->cpu = 0; /* needed? */ -#ifdef CONFIG_HOTPLUG_CPU - prefill_possible_map(); -#endif - if (smp_sanity_check(max_cpus) < 0) { printk(KERN_INFO "SMP disabled\n"); disable_smp(); diff --git a/include/asm-x86_64/smp.h b/include/asm-x86_64/smp.h index 24e32611f0b..c57ce407134 100644 --- a/include/asm-x86_64/smp.h +++ b/include/asm-x86_64/smp.h @@ -81,6 +81,7 @@ static inline int hard_smp_processor_id(void) extern int safe_smp_processor_id(void); extern int __cpu_disable(void); extern void __cpu_die(unsigned int cpu); +extern void prefill_possible_map(void); #endif /* !ASSEMBLY */ -- cgit v1.2.3 From 3c92c2ba33cd7d666c5f83cc32aa590e794e91b0 Mon Sep 17 00:00:00 2001 From: Andi Kleen Date: Tue, 11 Oct 2005 01:28:33 +0200 Subject: [PATCH] i386: Don't discard upper 32bits of HWCR on K8 Need to use long long, not long when RMWing a MSR. I think it's harmless right now, but still should be better fixed if AMD adds any bits in the upper 32bit of HWCR. Bug was introduced with the TLB flush filter fix for i386 Signed-off-by: Andi Kleen Signed-off-by: Linus Torvalds --- arch/i386/kernel/cpu/amd.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/i386/kernel/cpu/amd.c b/arch/i386/kernel/cpu/amd.c index 4c1ddf2b57c..53a1681cd96 100644 --- a/arch/i386/kernel/cpu/amd.c +++ b/arch/i386/kernel/cpu/amd.c @@ -29,7 +29,7 @@ static void __init init_amd(struct cpuinfo_x86 *c) int r; #ifdef CONFIG_SMP - unsigned long value; + unsigned long long value; /* Disable TLB flush filter by setting HWCR.FFDIS on K8 * bit 6 of msr C001_0015 -- cgit v1.2.3 From 907a42617970a159361f17ef9a63f04d276995ab Mon Sep 17 00:00:00 2001 From: Linus Torvalds Date: Mon, 10 Oct 2005 18:19:19 -0700 Subject: Linux v2.6.14-rc4 --- Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile b/Makefile index fdb96bc8508..504ba3ceb29 100644 --- a/Makefile +++ b/Makefile @@ -1,7 +1,7 @@ VERSION = 2 PATCHLEVEL = 6 SUBLEVEL = 14 -EXTRAVERSION =-rc3 +EXTRAVERSION =-rc4 NAME=Affluent Albatross # *DOCUMENTATION* -- cgit v1.2.3 From b8df110fea555d5088bba67f446c2435104405be Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Mon, 10 Oct 2005 20:43:22 -0700 Subject: [SPARC64]: Fix oops on runlevel change with serial console. Incorrect uart_write_wakeup() calls cause reference to a NULL tty pointer in sunsab and sunzilog serial drivers. Signed-off-by: David S. Miller --- drivers/serial/sunsab.c | 1 - drivers/serial/sunzilog.c | 5 ++--- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/drivers/serial/sunsab.c b/drivers/serial/sunsab.c index e971156daa6..ba9381fd3f2 100644 --- a/drivers/serial/sunsab.c +++ b/drivers/serial/sunsab.c @@ -274,7 +274,6 @@ static void transmit_chars(struct uart_sunsab_port *up, if (uart_circ_empty(xmit) || uart_tx_stopped(&up->port)) { up->interrupt_mask1 |= SAB82532_IMR1_XPR; writeb(up->interrupt_mask1, &up->regs->w.imr1); - uart_write_wakeup(&up->port); return; } diff --git a/drivers/serial/sunzilog.c b/drivers/serial/sunzilog.c index d75445738c8..7653d6cf05a 100644 --- a/drivers/serial/sunzilog.c +++ b/drivers/serial/sunzilog.c @@ -517,10 +517,9 @@ static void sunzilog_transmit_chars(struct uart_sunzilog_port *up, if (up->port.info == NULL) goto ack_tx_int; xmit = &up->port.info->xmit; - if (uart_circ_empty(xmit)) { - uart_write_wakeup(&up->port); + if (uart_circ_empty(xmit)) goto ack_tx_int; - } + if (uart_tx_stopped(&up->port)) goto ack_tx_int; -- cgit v1.2.3 From 08eb8f124f990aa476589d1f7810f7ec7f259c08 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Mon, 10 Oct 2005 21:02:26 -0700 Subject: [SPARC32]: Revert IOMAP change eb98129eec7fa605f0407dfd92d40ee8ddf5cd9a Breakage noted by Al Viro. It breaks non-PCI builds, it's probably better to have a more direct implementation on sparc32, and which driver actually needs this is still questionable. We can resolve this in 2.6.15 Signed-off-by: David S. Miller --- arch/sparc/Kconfig | 4 ---- arch/sparc/defconfig | 1 - 2 files changed, 5 deletions(-) diff --git a/arch/sparc/Kconfig b/arch/sparc/Kconfig index f7c51b86904..6537445dac0 100644 --- a/arch/sparc/Kconfig +++ b/arch/sparc/Kconfig @@ -21,10 +21,6 @@ config GENERIC_ISA_DMA bool default y -config GENERIC_IOMAP - bool - default y - source "init/Kconfig" menu "General machine setup" diff --git a/arch/sparc/defconfig b/arch/sparc/defconfig index 8a3aef1e22f..a6985626300 100644 --- a/arch/sparc/defconfig +++ b/arch/sparc/defconfig @@ -5,7 +5,6 @@ CONFIG_MMU=y CONFIG_UID16=y CONFIG_HIGHMEM=y CONFIG_GENERIC_ISA_DMA=y -CONFIG_GENERIC_IOMAP=y # # Code maturity level options -- cgit v1.2.3 From e5945b4f605d1479d5b44252a2c691168c5d38d6 Mon Sep 17 00:00:00 2001 From: Cornelia Huck Date: Tue, 11 Oct 2005 08:28:59 -0700 Subject: [PATCH] s390: ccw device reconnect oops. Search for a disconnect ccw_device on the ccw bus rather than on the css bus (was a typo in patch I did for the klist conversion). A cast to an embedding ccw_device from an embedded device in a struct subchannel will lead us to oopses. Signed-off-by: Cornelia Huck Signed-off-by: Martin Schwidefsky Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/s390/cio/device.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/s390/cio/device.c b/drivers/s390/cio/device.c index 14c76f5e417..9adc11e8b8b 100644 --- a/drivers/s390/cio/device.c +++ b/drivers/s390/cio/device.c @@ -544,7 +544,7 @@ get_disc_ccwdev_by_devno(unsigned int devno, struct ccw_device *sibling) .sibling = sibling, }; - dev = bus_find_device(&css_bus_type, NULL, &data, match_devno); + dev = bus_find_device(&ccw_bus_type, NULL, &data, match_devno); return dev ? to_ccwdev(dev) : NULL; } -- cgit v1.2.3 From e4314bf496bb7bb9acd754aeb319c30869bc8d76 Mon Sep 17 00:00:00 2001 From: Anton Blanchard Date: Tue, 11 Oct 2005 08:29:00 -0700 Subject: [PATCH] ppc64: Fix PCI hotplug pSeries_irq_bus_setup is marked __devinit but references s7a_workaround which is marked __initdata. Depending on who got the memory for s7a_workaround (and if the value was now positive), it was possible for PCI hotplugged devices to have 3 subtracted from their interrupt number. This would happen randomly and caused me much confusion :) Signed-off-by: Anton Blanchard Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/ppc64/kernel/pSeries_pci.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/arch/ppc64/kernel/pSeries_pci.c b/arch/ppc64/kernel/pSeries_pci.c index 1f5f141fb7a..928f8febdb3 100644 --- a/arch/ppc64/kernel/pSeries_pci.c +++ b/arch/ppc64/kernel/pSeries_pci.c @@ -32,7 +32,7 @@ #include "pci.h" -static int __initdata s7a_workaround = -1; +static int __devinitdata s7a_workaround = -1; #if 0 void pcibios_name_device(struct pci_dev *dev) @@ -60,7 +60,7 @@ void pcibios_name_device(struct pci_dev *dev) DECLARE_PCI_FIXUP_HEADER(PCI_ANY_ID, PCI_ANY_ID, pcibios_name_device); #endif -static void __init check_s7a(void) +static void __devinit check_s7a(void) { struct device_node *root; char *model; -- cgit v1.2.3 From ad6ce87e5bd4440a6ce9aa9f8cda795b9e902eff Mon Sep 17 00:00:00 2001 From: Abhay Salunke Date: Tue, 11 Oct 2005 08:29:02 -0700 Subject: [PATCH] dell_rbu: changes in packet update mechanism In the current dell_rbu code ver 2.0 the packet update mechanism makes the user app dump every individual packet in to the driver. This adds in efficiency as every packet update makes the /sys/class/firmware/dell_rbu/loading and data files to disappear and reappear again. Thus the user app needs to wait for the files to reappear to dump another packet. This slows down the packet update tremendously in case of large number of packets. I am submitting a new patch for dell_rbu which will change the way we do packet updates; In the new method the user app will create a new single file which has already packetized the rbu image and all the packets are now staged in this file. This driver also creates a new entry in /sys/devices/platform/dell_rbu/packet_size ; the user needs to echo the packet size here before downloading the packet file. The user should do the following: create one single file which has all the packets stacked together. echo the packet size in to /sys/devices/platform/dell_rbu/packet_size. echo 1 > /sys/class/firmware/dell_rbu/loading cat the packetfile > /sys/class/firmware/dell_rbu/data echo 0 > /sys/class/firmware/dell_rbu/loading The driver takes the file which came through /sys/class/firmware/dell_rbu/data and takes chunks of paket_size data from it and place in contiguous memory. This makes packet update process very efficient and fast. As all the packet update happens in one single operation. The user can still read back the downloaded file from /sys/devices/platform/dell_rbu/data. Signed-off-by: Abhay Salunke Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- Documentation/dell_rbu.txt | 38 +++++++--- drivers/firmware/dell_rbu.c | 174 +++++++++++++++++++++++--------------------- 2 files changed, 121 insertions(+), 91 deletions(-) diff --git a/Documentation/dell_rbu.txt b/Documentation/dell_rbu.txt index 95d7f62e4db..941343a7a26 100644 --- a/Documentation/dell_rbu.txt +++ b/Documentation/dell_rbu.txt @@ -35,6 +35,7 @@ The driver load creates the following directories under the /sys file system. /sys/class/firmware/dell_rbu/data /sys/devices/platform/dell_rbu/image_type /sys/devices/platform/dell_rbu/data +/sys/devices/platform/dell_rbu/packet_size The driver supports two types of update mechanism; monolithic and packetized. These update mechanism depends upon the BIOS currently running on the system. @@ -47,8 +48,26 @@ By default the driver uses monolithic memory for the update type. This can be changed to packets during the driver load time by specifying the load parameter image_type=packet. This can also be changed later as below echo packet > /sys/devices/platform/dell_rbu/image_type -Also echoing either mono ,packet or init in to image_type will free up the -memory allocated by the driver. + +In packet update mode the packet size has to be given before any packets can +be downloaded. It is done as below +echo XXXX > /sys/devices/platform/dell_rbu/packet_size +In the packet update mechanism, the user neesd to create a new file having +packets of data arranged back to back. It can be done as follows +The user creates packets header, gets the chunk of the BIOS image and +placs it next to the packetheader; now, the packetheader + BIOS image chunk +added to geather should match the specified packet_size. This makes one +packet, the user needs to create more such packets out of the entire BIOS +image file and then arrange all these packets back to back in to one single +file. +This file is then copied to /sys/class/firmware/dell_rbu/data. +Once this file gets to the driver, the driver extracts packet_size data from +the file and spreads it accross the physical memory in contiguous packet_sized +space. +This method makes sure that all the packets get to the driver in a single operation. + +In monolithic update the user simply get the BIOS image (.hdr file) and copies +to the data file as is without any change to the BIOS image itself. Do the steps below to download the BIOS image. 1) echo 1 > /sys/class/firmware/dell_rbu/loading @@ -58,7 +77,10 @@ Do the steps below to download the BIOS image. The /sys/class/firmware/dell_rbu/ entries will remain till the following is done. echo -1 > /sys/class/firmware/dell_rbu/loading. -Until this step is completed the drivr cannot be unloaded. +Until this step is completed the driver cannot be unloaded. +Also echoing either mono ,packet or init in to image_type will free up the +memory allocated by the driver. + If an user by accident executes steps 1 and 3 above without executing step 2; it will make the /sys/class/firmware/dell_rbu/ entries to disappear. The entries can be recreated by doing the following @@ -66,15 +88,11 @@ echo init > /sys/devices/platform/dell_rbu/image_type NOTE: echoing init in image_type does not change it original value. Also the driver provides /sys/devices/platform/dell_rbu/data readonly file to -read back the image downloaded. This is useful in case of packet update -mechanism where the above steps 1,2,3 will repeated for every packet. -By reading the /sys/devices/platform/dell_rbu/data file all packet data -downloaded can be verified in a single file. -The packets are arranged in this file one after the other in a FIFO order. +read back the image downloaded. NOTE: -This driver requires a patch for firmware_class.c which has the addition -of request_firmware_nowait_nohotplug function to wortk +This driver requires a patch for firmware_class.c which has the modified +request_firmware_nowait function. Also after updating the BIOS image an user mdoe application neeeds to execute code which message the BIOS update request to the BIOS. So on the next reboot the BIOS knows about the new image downloaded and it updates it self. diff --git a/drivers/firmware/dell_rbu.c b/drivers/firmware/dell_rbu.c index b6678239825..4f4ba9b6d18 100644 --- a/drivers/firmware/dell_rbu.c +++ b/drivers/firmware/dell_rbu.c @@ -50,7 +50,7 @@ MODULE_AUTHOR("Abhay Salunke "); MODULE_DESCRIPTION("Driver for updating BIOS image on DELL systems"); MODULE_LICENSE("GPL"); -MODULE_VERSION("2.0"); +MODULE_VERSION("3.0"); #define BIOS_SCAN_LIMIT 0xffffffff #define MAX_IMAGE_LENGTH 16 @@ -62,15 +62,16 @@ static struct _rbu_data { int dma_alloc; spinlock_t lock; unsigned long packet_read_count; - unsigned long packet_write_count; unsigned long num_packets; unsigned long packetsize; + unsigned long imagesize; int entry_created; } rbu_data; static char image_type[MAX_IMAGE_LENGTH + 1] = "mono"; module_param_string(image_type, image_type, sizeof (image_type), 0); -MODULE_PARM_DESC(image_type, "BIOS image type. choose- mono or packet"); +MODULE_PARM_DESC(image_type, + "BIOS image type. choose- mono or packet or init"); struct packet_data { struct list_head list; @@ -88,55 +89,13 @@ static dma_addr_t dell_rbu_dmaaddr; static void init_packet_head(void) { INIT_LIST_HEAD(&packet_data_head.list); - rbu_data.packet_write_count = 0; rbu_data.packet_read_count = 0; rbu_data.num_packets = 0; rbu_data.packetsize = 0; + rbu_data.imagesize = 0; } -static int fill_last_packet(void *data, size_t length) -{ - struct list_head *ptemp_list; - struct packet_data *packet = NULL; - int packet_count = 0; - - pr_debug("fill_last_packet: entry \n"); - - if (!rbu_data.num_packets) { - pr_debug("fill_last_packet: num_packets=0\n"); - return -ENOMEM; - } - - packet_count = rbu_data.num_packets; - - ptemp_list = (&packet_data_head.list)->prev; - - packet = list_entry(ptemp_list, struct packet_data, list); - - if ((rbu_data.packet_write_count + length) > rbu_data.packetsize) { - pr_debug("dell_rbu:%s: packet size data " - "overrun\n", __FUNCTION__); - return -EINVAL; - } - - pr_debug("fill_last_packet : buffer = %p\n", packet->data); - - memcpy((packet->data + rbu_data.packet_write_count), data, length); - - if ((rbu_data.packet_write_count + length) == rbu_data.packetsize) { - /* - * this was the last data chunk in the packet - * so reinitialize the packet data counter to zero - */ - rbu_data.packet_write_count = 0; - } else - rbu_data.packet_write_count += length; - - pr_debug("fill_last_packet: exit \n"); - return 0; -} - -static int create_packet(size_t length) +static int create_packet(void *data, size_t length) { struct packet_data *newpacket; int ordernum = 0; @@ -186,9 +145,11 @@ static int create_packet(size_t length) INIT_LIST_HEAD(&newpacket->list); list_add_tail(&newpacket->list, &packet_data_head.list); /* - * packets have fixed size + * packets may not have fixed size */ - newpacket->length = rbu_data.packetsize; + newpacket->length = length; + + memcpy(newpacket->data, data, length); pr_debug("create_packet: exit \n"); @@ -198,13 +159,37 @@ static int create_packet(size_t length) static int packetize_data(void *data, size_t length) { int rc = 0; + int done = 0; + int packet_length; + u8 *temp; + u8 *end = (u8 *) data + length; + pr_debug("packetize_data: data length %d\n", length); + if (!rbu_data.packetsize) { + printk(KERN_WARNING + "dell_rbu: packetsize not specified\n"); + return -EIO; + } - if (!rbu_data.packet_write_count) { - if ((rc = create_packet(length))) + temp = (u8 *) data; + + /* packetize the hunk */ + while (!done) { + if ((temp + rbu_data.packetsize) < end) + packet_length = rbu_data.packetsize; + else { + /* this is the last packet */ + packet_length = end - temp; + done = 1; + } + + if ((rc = create_packet(temp, packet_length))) return rc; + + pr_debug("%lu:%lu\n", temp, (end - temp)); + temp += packet_length; } - if ((rc = fill_last_packet(data, length))) - return rc; + + rbu_data.imagesize = length; return rc; } @@ -243,7 +228,7 @@ static int do_packet_read(char *data, struct list_head *ptemp_list, return bytes_copied; } -static int packet_read_list(char *data, size_t *pread_length) +static int packet_read_list(char *data, size_t * pread_length) { struct list_head *ptemp_list; int temp_count = 0; @@ -303,10 +288,9 @@ static void packet_empty_list(void) newpacket->ordernum); kfree(newpacket); } - rbu_data.packet_write_count = 0; rbu_data.packet_read_count = 0; rbu_data.num_packets = 0; - rbu_data.packetsize = 0; + rbu_data.imagesize = 0; } /* @@ -425,7 +409,6 @@ static ssize_t read_packet_data(char *buffer, loff_t pos, size_t count) size_t bytes_left; size_t data_length; char *ptempBuf = buffer; - unsigned long imagesize; /* check to see if we have something to return */ if (rbu_data.num_packets == 0) { @@ -434,22 +417,20 @@ static ssize_t read_packet_data(char *buffer, loff_t pos, size_t count) goto read_rbu_data_exit; } - imagesize = rbu_data.num_packets * rbu_data.packetsize; - - if (pos > imagesize) { + if (pos > rbu_data.imagesize) { retval = 0; printk(KERN_WARNING "dell_rbu:read_packet_data: " "data underrun\n"); goto read_rbu_data_exit; } - bytes_left = imagesize - pos; + bytes_left = rbu_data.imagesize - pos; data_length = min(bytes_left, count); if ((retval = packet_read_list(ptempBuf, &data_length)) < 0) goto read_rbu_data_exit; - if ((pos + count) > imagesize) { + if ((pos + count) > rbu_data.imagesize) { rbu_data.packet_read_count = 0; /* this was the last copy */ retval = bytes_left; @@ -499,7 +480,7 @@ static ssize_t read_rbu_mono_data(char *buffer, loff_t pos, size_t count) } static ssize_t read_rbu_data(struct kobject *kobj, char *buffer, - loff_t pos, size_t count) + loff_t pos, size_t count) { ssize_t ret_count = 0; @@ -531,13 +512,18 @@ static void callbackfn_rbu(const struct firmware *fw, void *context) memcpy(rbu_data.image_update_buffer, fw->data, fw->size); } else if (!strcmp(image_type, "packet")) { - if (!rbu_data.packetsize) - rbu_data.packetsize = fw->size; - else if (rbu_data.packetsize != fw->size) { + /* + * we need to free previous packets if a + * new hunk of packets needs to be downloaded + */ + packet_empty_list(); + if (packetize_data(fw->data, fw->size)) + /* Incase something goes wrong when we are + * in middle of packetizing the data, we + * need to free up whatever packets might + * have been created before we quit. + */ packet_empty_list(); - rbu_data.packetsize = fw->size; - } - packetize_data(fw->data, fw->size); } else pr_debug("invalid image type specified.\n"); spin_unlock(&rbu_data.lock); @@ -553,7 +539,7 @@ static void callbackfn_rbu(const struct firmware *fw, void *context) } static ssize_t read_rbu_image_type(struct kobject *kobj, char *buffer, - loff_t pos, size_t count) + loff_t pos, size_t count) { int size = 0; if (!pos) @@ -562,7 +548,7 @@ static ssize_t read_rbu_image_type(struct kobject *kobj, char *buffer, } static ssize_t write_rbu_image_type(struct kobject *kobj, char *buffer, - loff_t pos, size_t count) + loff_t pos, size_t count) { int rc = count; int req_firm_rc = 0; @@ -621,25 +607,49 @@ static ssize_t write_rbu_image_type(struct kobject *kobj, char *buffer, return rc; } +static ssize_t read_rbu_packet_size(struct kobject *kobj, char *buffer, + loff_t pos, size_t count) +{ + int size = 0; + if (!pos) { + spin_lock(&rbu_data.lock); + size = sprintf(buffer, "%lu\n", rbu_data.packetsize); + spin_unlock(&rbu_data.lock); + } + return size; +} + +static ssize_t write_rbu_packet_size(struct kobject *kobj, char *buffer, + loff_t pos, size_t count) +{ + unsigned long temp; + spin_lock(&rbu_data.lock); + packet_empty_list(); + sscanf(buffer, "%lu", &temp); + if (temp < 0xffffffff) + rbu_data.packetsize = temp; + + spin_unlock(&rbu_data.lock); + return count; +} + static struct bin_attribute rbu_data_attr = { - .attr = { - .name = "data", - .owner = THIS_MODULE, - .mode = 0444, - }, + .attr = {.name = "data",.owner = THIS_MODULE,.mode = 0444}, .read = read_rbu_data, }; static struct bin_attribute rbu_image_type_attr = { - .attr = { - .name = "image_type", - .owner = THIS_MODULE, - .mode = 0644, - }, + .attr = {.name = "image_type",.owner = THIS_MODULE,.mode = 0644}, .read = read_rbu_image_type, .write = write_rbu_image_type, }; +static struct bin_attribute rbu_packet_size_attr = { + .attr = {.name = "packet_size",.owner = THIS_MODULE,.mode = 0644}, + .read = read_rbu_packet_size, + .write = write_rbu_packet_size, +}; + static int __init dcdrbu_init(void) { int rc = 0; @@ -657,6 +667,8 @@ static int __init dcdrbu_init(void) sysfs_create_bin_file(&rbu_device->dev.kobj, &rbu_data_attr); sysfs_create_bin_file(&rbu_device->dev.kobj, &rbu_image_type_attr); + sysfs_create_bin_file(&rbu_device->dev.kobj, + &rbu_packet_size_attr); rc = request_firmware_nowait(THIS_MODULE, FW_ACTION_NOHOTPLUG, "dell_rbu", &rbu_device->dev, &context, callbackfn_rbu); -- cgit v1.2.3 From 19cba8abd6ca09527c194864ae651db65cbacfe1 Mon Sep 17 00:00:00 2001 From: Latchesar Ionkov Date: Tue, 11 Oct 2005 08:29:03 -0700 Subject: [PATCH] v9fs: remove additional buffer allocation from v9fs_file_read and v9fs_file_write v9fs_file_read and v9fs_file_write use kmalloc to allocate buffers as big as the data buffer received as parameter. kmalloc cannot be used to allocate buffers bigger than 128K, so reading/writing data in chunks bigger than 128k fails. This patch reorganizes v9fs_file_read and v9fs_file_write to allocate only buffers as big as the maximum data that can be sent in one 9P message. Signed-off-by: Latchesar Ionkov Cc: Eric Van Hensbergen Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- fs/9p/vfs_file.c | 114 ++++++++++++++++--------------------------------------- 1 file changed, 33 insertions(+), 81 deletions(-) diff --git a/fs/9p/vfs_file.c b/fs/9p/vfs_file.c index a4799e971d1..bbc3cc63854 100644 --- a/fs/9p/vfs_file.c +++ b/fs/9p/vfs_file.c @@ -175,16 +175,16 @@ static int v9fs_file_lock(struct file *filp, int cmd, struct file_lock *fl) } /** - * v9fs_read - read from a file (internal) + * v9fs_file_read - read from a file * @filep: file pointer to read * @data: data buffer to read data into * @count: size of buffer * @offset: offset at which to read data * */ - static ssize_t -v9fs_read(struct file *filp, char *buffer, size_t count, loff_t * offset) +v9fs_file_read(struct file *filp, char __user * data, size_t count, + loff_t * offset) { struct inode *inode = filp->f_dentry->d_inode; struct v9fs_session_info *v9ses = v9fs_inode2v9ses(inode); @@ -194,6 +194,7 @@ v9fs_read(struct file *filp, char *buffer, size_t count, loff_t * offset) int rsize = 0; int result = 0; int total = 0; + int n; dprintk(DEBUG_VFS, "\n"); @@ -216,10 +217,15 @@ v9fs_read(struct file *filp, char *buffer, size_t count, loff_t * offset) } else *offset += result; - /* XXX - extra copy */ - memcpy(buffer, fcall->params.rread.data, result); + n = copy_to_user(data, fcall->params.rread.data, result); + if (n) { + dprintk(DEBUG_ERROR, "Problem copying to user %d\n", n); + kfree(fcall); + return -EFAULT; + } + count -= result; - buffer += result; + data += result; total += result; kfree(fcall); @@ -232,42 +238,7 @@ v9fs_read(struct file *filp, char *buffer, size_t count, loff_t * offset) } /** - * v9fs_file_read - read from a file - * @filep: file pointer to read - * @data: data buffer to read data into - * @count: size of buffer - * @offset: offset at which to read data - * - */ - -static ssize_t -v9fs_file_read(struct file *filp, char __user * data, size_t count, - loff_t * offset) -{ - int retval = -1; - int ret = 0; - char *buffer; - - buffer = kmalloc(count, GFP_KERNEL); - if (!buffer) - return -ENOMEM; - - retval = v9fs_read(filp, buffer, count, offset); - if (retval > 0) { - if ((ret = copy_to_user(data, buffer, retval)) != 0) { - dprintk(DEBUG_ERROR, "Problem copying to user %d\n", - ret); - retval = ret; - } - } - - kfree(buffer); - - return retval; -} - -/** - * v9fs_write - write to a file + * v9fs_file_write - write to a file * @filep: file pointer to write * @data: data buffer to write data from * @count: size of buffer @@ -276,7 +247,8 @@ v9fs_file_read(struct file *filp, char __user * data, size_t count, */ static ssize_t -v9fs_write(struct file *filp, char *buffer, size_t count, loff_t * offset) +v9fs_file_write(struct file *filp, const char __user * data, + size_t count, loff_t * offset) { struct inode *inode = filp->f_dentry->d_inode; struct v9fs_session_info *v9ses = v9fs_inode2v9ses(inode); @@ -286,30 +258,42 @@ v9fs_write(struct file *filp, char *buffer, size_t count, loff_t * offset) int result = -EIO; int rsize = 0; int total = 0; + char *buf; - dprintk(DEBUG_VFS, "data %p count %d offset %x\n", buffer, (int)count, + dprintk(DEBUG_VFS, "data %p count %d offset %x\n", data, (int)count, (int)*offset); rsize = v9ses->maxdata - V9FS_IOHDRSZ; if (v9fid->iounit != 0 && rsize > v9fid->iounit) rsize = v9fid->iounit; - dump_data(buffer, count); + buf = kmalloc(v9ses->maxdata - V9FS_IOHDRSZ, GFP_KERNEL); + if (!buf) + return -ENOMEM; do { if (count < rsize) rsize = count; - result = - v9fs_t_write(v9ses, fid, *offset, rsize, buffer, &fcall); + result = copy_from_user(buf, data, rsize); + if (result) { + dprintk(DEBUG_ERROR, "Problem copying from user\n"); + kfree(buf); + return -EFAULT; + } + + dump_data(buf, rsize); + result = v9fs_t_write(v9ses, fid, *offset, rsize, buf, &fcall); if (result < 0) { eprintk(KERN_ERR, "error while writing: %s(%d)\n", FCALL_ERROR(fcall), result); kfree(fcall); + kfree(buf); return result; } else *offset += result; kfree(fcall); + fcall = NULL; if (result != rsize) { eprintk(KERN_ERR, @@ -319,46 +303,14 @@ v9fs_write(struct file *filp, char *buffer, size_t count, loff_t * offset) } count -= result; - buffer += result; + data += result; total += result; } while (count); + kfree(buf); return total; } -/** - * v9fs_file_write - write to a file - * @filep: file pointer to write - * @data: data buffer to write data from - * @count: size of buffer - * @offset: offset at which to write data - * - */ - -static ssize_t -v9fs_file_write(struct file *filp, const char __user * data, - size_t count, loff_t * offset) -{ - int ret = -1; - char *buffer; - - buffer = kmalloc(count, GFP_KERNEL); - if (buffer == NULL) - return -ENOMEM; - - ret = copy_from_user(buffer, data, count); - if (ret) { - dprintk(DEBUG_ERROR, "Problem copying from user\n"); - ret = -EFAULT; - } else { - ret = v9fs_write(filp, buffer, count, offset); - } - - kfree(buffer); - - return ret; -} - struct file_operations v9fs_file_operations = { .llseek = generic_file_llseek, .read = v9fs_file_read, -- cgit v1.2.3 From 22c1ea44f0d33eda532883858b6cdabc5f265b66 Mon Sep 17 00:00:00 2001 From: Andreas Gruenbacher Date: Tue, 11 Oct 2005 08:29:05 -0700 Subject: [PATCH] nfsacl: Solaris VxFS compatibility fix Here is a compatibility fix between Linux and Solaris when used with VxFS filesystems: Solaris usually accepts acl entries in any order, but with VxFS it replies with NFSERR_INVAL when it sees a four-entry acl that is not in canonical form. It may also fail with other non-canonical acls -- I can't tell, because that case never triggers: We only send non-canonical acls when we fake up an ACL_MASK entry. Instead of adding fake ACL_MASK entries at the end, inserting them in the correct position makes Solaris+VxFS happy. The Linux client and server sides don't care about entry order. The three-entry-acl special case in which we need a fake ACL_MASK entry was handled in xdr_nfsace_encode. The patch moves this into nfsacl_encode. Signed-off-by: Andreas Gruenbacher Acked-by: Trond Myklebust Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- fs/nfs_common/nfsacl.c | 70 +++++++++++++++++++++++++------------------------- 1 file changed, 35 insertions(+), 35 deletions(-) diff --git a/fs/nfs_common/nfsacl.c b/fs/nfs_common/nfsacl.c index 251e5a1bb1c..0c2be8c0307 100644 --- a/fs/nfs_common/nfsacl.c +++ b/fs/nfs_common/nfsacl.c @@ -48,43 +48,26 @@ xdr_nfsace_encode(struct xdr_array2_desc *desc, void *elem) (struct nfsacl_encode_desc *) desc; u32 *p = (u32 *) elem; - if (nfsacl_desc->count < nfsacl_desc->acl->a_count) { - struct posix_acl_entry *entry = - &nfsacl_desc->acl->a_entries[nfsacl_desc->count++]; + struct posix_acl_entry *entry = + &nfsacl_desc->acl->a_entries[nfsacl_desc->count++]; - *p++ = htonl(entry->e_tag | nfsacl_desc->typeflag); - switch(entry->e_tag) { - case ACL_USER_OBJ: - *p++ = htonl(nfsacl_desc->uid); - break; - case ACL_GROUP_OBJ: - *p++ = htonl(nfsacl_desc->gid); - break; - case ACL_USER: - case ACL_GROUP: - *p++ = htonl(entry->e_id); - break; - default: /* Solaris depends on that! */ - *p++ = 0; - break; - } - *p++ = htonl(entry->e_perm & S_IRWXO); - } else { - const struct posix_acl_entry *pa, *pe; - int group_obj_perm = ACL_READ|ACL_WRITE|ACL_EXECUTE; - - FOREACH_ACL_ENTRY(pa, nfsacl_desc->acl, pe) { - if (pa->e_tag == ACL_GROUP_OBJ) { - group_obj_perm = pa->e_perm & S_IRWXO; - break; - } - } - /* fake up ACL_MASK entry */ - *p++ = htonl(ACL_MASK | nfsacl_desc->typeflag); - *p++ = htonl(0); - *p++ = htonl(group_obj_perm); + *p++ = htonl(entry->e_tag | nfsacl_desc->typeflag); + switch(entry->e_tag) { + case ACL_USER_OBJ: + *p++ = htonl(nfsacl_desc->uid); + break; + case ACL_GROUP_OBJ: + *p++ = htonl(nfsacl_desc->gid); + break; + case ACL_USER: + case ACL_GROUP: + *p++ = htonl(entry->e_id); + break; + default: /* Solaris depends on that! */ + *p++ = 0; + break; } - + *p++ = htonl(entry->e_perm & S_IRWXO); return 0; } @@ -105,11 +88,28 @@ nfsacl_encode(struct xdr_buf *buf, unsigned int base, struct inode *inode, .gid = inode->i_gid, }; int err; + struct posix_acl *acl2 = NULL; if (entries > NFS_ACL_MAX_ENTRIES || xdr_encode_word(buf, base, entries)) return -EINVAL; + if (encode_entries && acl && acl->a_count == 3) { + /* Fake up an ACL_MASK entry. */ + acl2 = posix_acl_alloc(4, GFP_KERNEL); + if (!acl2) + return -ENOMEM; + /* Insert entries in canonical order: other orders seem + to confuse Solaris VxFS. */ + acl2->a_entries[0] = acl->a_entries[0]; /* ACL_USER_OBJ */ + acl2->a_entries[1] = acl->a_entries[1]; /* ACL_GROUP_OBJ */ + acl2->a_entries[2] = acl->a_entries[1]; /* ACL_MASK */ + acl2->a_entries[2].e_tag = ACL_MASK; + acl2->a_entries[3] = acl->a_entries[2]; /* ACL_OTHER */ + nfsacl_desc.acl = acl2; + } err = xdr_encode_array2(buf, base + 4, &nfsacl_desc.desc); + if (acl2) + posix_acl_release(acl2); if (!err) err = 8 + nfsacl_desc.desc.elem_size * nfsacl_desc.desc.array_len; -- cgit v1.2.3 From 1bef40032992320dd25a266fc166bfb8fa3f2f59 Mon Sep 17 00:00:00 2001 From: Suzuki Date: Tue, 11 Oct 2005 08:29:06 -0700 Subject: [PATCH] madvise: Avoid returning error code -EBADF for anonymous mappings Revert this recent correctness change: Douglas Crosher reported that it broke an existing application, and that madvise() works without error on anonymous mappings on Solaris. This means that madvise() will remain non-standards-compliant: we should return -EBADF for all requests against non-file-backed vma's, but Linux only does this for MADV_WILLNEED requests. Signed-off-by: Suzuki K P Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- mm/madvise.c | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/mm/madvise.c b/mm/madvise.c index 4454936f87d..20e075d1c64 100644 --- a/mm/madvise.c +++ b/mm/madvise.c @@ -83,6 +83,9 @@ static long madvise_willneed(struct vm_area_struct * vma, { struct file *file = vma->vm_file; + if (!file) + return -EBADF; + if (file->f_mapping->a_ops->get_xip_page) { /* no bad return value, but ignore advice */ return 0; @@ -141,11 +144,7 @@ static long madvise_vma(struct vm_area_struct *vma, struct vm_area_struct **prev, unsigned long start, unsigned long end, int behavior) { - struct file *filp = vma->vm_file; - long error = -EBADF; - - if (!filp) - goto out; + long error; switch (behavior) { case MADV_NORMAL: @@ -166,8 +165,6 @@ madvise_vma(struct vm_area_struct *vma, struct vm_area_struct **prev, error = -EINVAL; break; } - -out: return error; } -- cgit v1.2.3 From a0c111c631e7ab4abd68920debd44259160812ef Mon Sep 17 00:00:00 2001 From: Paolo Galtieri Date: Tue, 11 Oct 2005 08:29:07 -0700 Subject: [PATCH] ppc highmem fix I've noticed that the calculations for seg_size and nr_segs in __dma_sync_page_highmem() (arch/ppc/kernel/dma-mapping.c) are wrong. The incorrect calculations can result in either an oops or a panic when running fsck depending on the size of the partition. The problem with the seg_size calculation is that it can result in a negative number if size is offset > size. The problem with the nr_segs caculation is returns the wrong number of segments, e.g. it returns 1 when size is 200 and offset is 4095, when it should return 2 or more. Acked-by: Benjamin Herrenschmidt Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/ppc/kernel/dma-mapping.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/arch/ppc/kernel/dma-mapping.c b/arch/ppc/kernel/dma-mapping.c index b566d982806..8edee806dae 100644 --- a/arch/ppc/kernel/dma-mapping.c +++ b/arch/ppc/kernel/dma-mapping.c @@ -401,10 +401,10 @@ EXPORT_SYMBOL(__dma_sync); static inline void __dma_sync_page_highmem(struct page *page, unsigned long offset, size_t size, int direction) { - size_t seg_size = min((size_t)PAGE_SIZE, size) - offset; + size_t seg_size = min((size_t)(PAGE_SIZE - offset), size); size_t cur_size = seg_size; unsigned long flags, start, seg_offset = offset; - int nr_segs = PAGE_ALIGN(size + (PAGE_SIZE - offset))/PAGE_SIZE; + int nr_segs = 1 + ((size - seg_size) + PAGE_SIZE - 1)/PAGE_SIZE; int seg_nr = 0; local_irq_save(flags); -- cgit v1.2.3 From 6de505173e24e76bb33a2595312e0c2b44d49e58 Mon Sep 17 00:00:00 2001 From: "akpm@osdl.org" Date: Tue, 11 Oct 2005 08:29:08 -0700 Subject: [PATCH] binfmt_elf bss padding fix Nir Tzachar points out that if an ELF file specifies a zero-length bss at a whacky address, we cannot load that binary because padzero() tries to zero out the end of the page at the whacky address, and that may not be writeable. See also http://bugzilla.kernel.org/show_bug.cgi?id=5411 So teach load_elf_binary() to skip the bss settng altogether if the elf file has a zero-length bss segment. Cc: Roland McGrath Cc: Daniel Jacobowitz Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- fs/binfmt_elf.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/fs/binfmt_elf.c b/fs/binfmt_elf.c index 7976a238f0a..d4b15576e58 100644 --- a/fs/binfmt_elf.c +++ b/fs/binfmt_elf.c @@ -905,7 +905,7 @@ static int load_elf_binary(struct linux_binprm * bprm, struct pt_regs * regs) send_sig(SIGKILL, current, 0); goto out_free_dentry; } - if (padzero(elf_bss)) { + if (likely(elf_bss != elf_brk) && unlikely(padzero(elf_bss))) { send_sig(SIGSEGV, current, 0); retval = -EFAULT; /* Nobody gets to see this, but.. */ goto out_free_dentry; -- cgit v1.2.3 From 9de11aab1c8fd87da7e1fb435ce0ff26bacd7909 Mon Sep 17 00:00:00 2001 From: Hirokazu Takata Date: Tue, 11 Oct 2005 08:29:09 -0700 Subject: [PATCH] m32r: trap handler code for illegal traps This patch prevents illegal traps from causing m32r kernel's infinite loop execution. Signed-off-by: Naoto Sugai Signed-off-by: Hirokazu Takata Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/m32r/kernel/entry.S | 9 +++++++++ arch/m32r/kernel/traps.c | 33 ++++++++++++++++----------------- 2 files changed, 25 insertions(+), 17 deletions(-) diff --git a/arch/m32r/kernel/entry.S b/arch/m32r/kernel/entry.S index dddbf6b5ed2..85920fb8d08 100644 --- a/arch/m32r/kernel/entry.S +++ b/arch/m32r/kernel/entry.S @@ -681,6 +681,15 @@ ENTRY(debug_trap) bl do_debug_trap bra error_code +ENTRY(ill_trap) + /* void ill_trap(void) */ + SWITCH_TO_KERNEL_STACK + SAVE_ALL + ldi r1, #0 ; error_code ; FIXME + mv r0, sp ; pt_regs + bl do_ill_trap + bra error_code + /* Cache flushing handler */ ENTRY(cache_flushing_handler) diff --git a/arch/m32r/kernel/traps.c b/arch/m32r/kernel/traps.c index 01922271d17..5fe8ed6d62d 100644 --- a/arch/m32r/kernel/traps.c +++ b/arch/m32r/kernel/traps.c @@ -5,8 +5,6 @@ * Hitoshi Yamamoto */ -/* $Id$ */ - /* * 'traps.c' handles hardware traps and faults after we have saved some * state in 'entry.S'. @@ -35,6 +33,7 @@ asmlinkage void ei_handler(void); asmlinkage void rie_handler(void); asmlinkage void debug_trap(void); asmlinkage void cache_flushing_handler(void); +asmlinkage void ill_trap(void); #ifdef CONFIG_SMP extern void smp_reschedule_interrupt(void); @@ -77,22 +76,22 @@ void set_eit_vector_entries(void) eit_vector[5] = BRA_INSN(default_eit_handler, 5); eit_vector[8] = BRA_INSN(rie_handler, 8); eit_vector[12] = BRA_INSN(alignment_check, 12); - eit_vector[16] = 0xff000000UL; + eit_vector[16] = BRA_INSN(ill_trap, 16); eit_vector[17] = BRA_INSN(debug_trap, 17); eit_vector[18] = BRA_INSN(system_call, 18); - eit_vector[19] = 0xff000000UL; - eit_vector[20] = 0xff000000UL; - eit_vector[21] = 0xff000000UL; - eit_vector[22] = 0xff000000UL; - eit_vector[23] = 0xff000000UL; - eit_vector[24] = 0xff000000UL; - eit_vector[25] = 0xff000000UL; - eit_vector[26] = 0xff000000UL; - eit_vector[27] = 0xff000000UL; + eit_vector[19] = BRA_INSN(ill_trap, 19); + eit_vector[20] = BRA_INSN(ill_trap, 20); + eit_vector[21] = BRA_INSN(ill_trap, 21); + eit_vector[22] = BRA_INSN(ill_trap, 22); + eit_vector[23] = BRA_INSN(ill_trap, 23); + eit_vector[24] = BRA_INSN(ill_trap, 24); + eit_vector[25] = BRA_INSN(ill_trap, 25); + eit_vector[26] = BRA_INSN(ill_trap, 26); + eit_vector[27] = BRA_INSN(ill_trap, 27); eit_vector[28] = BRA_INSN(cache_flushing_handler, 28); - eit_vector[29] = 0xff000000UL; - eit_vector[30] = 0xff000000UL; - eit_vector[31] = 0xff000000UL; + eit_vector[29] = BRA_INSN(ill_trap, 29); + eit_vector[30] = BRA_INSN(ill_trap, 30); + eit_vector[31] = BRA_INSN(ill_trap, 31); eit_vector[32] = BRA_INSN(ei_handler, 32); eit_vector[64] = BRA_INSN(pie_handler, 64); #ifdef CONFIG_MMU @@ -286,7 +285,8 @@ asmlinkage void do_##name(struct pt_regs * regs, long error_code) \ DO_ERROR( 1, SIGTRAP, "debug trap", debug_trap) DO_ERROR_INFO(0x20, SIGILL, "reserved instruction ", rie_handler, ILL_ILLOPC, regs->bpc) -DO_ERROR_INFO(0x100, SIGILL, "privilege instruction", pie_handler, ILL_PRVOPC, regs->bpc) +DO_ERROR_INFO(0x100, SIGILL, "privileged instruction", pie_handler, ILL_PRVOPC, regs->bpc) +DO_ERROR_INFO(-1, SIGILL, "illegal trap", ill_trap, ILL_ILLTRP, regs->bpc) extern int handle_unaligned_access(unsigned long, struct pt_regs *); @@ -329,4 +329,3 @@ asmlinkage void do_alignment_check(struct pt_regs *regs, long error_code) set_fs(oldfs); } } - -- cgit v1.2.3 From d3089792f6ee38cdc9e254a7cb2f8c8d7f38c20d Mon Sep 17 00:00:00 2001 From: Michael Krufky Date: Tue, 11 Oct 2005 09:28:24 -0700 Subject: [PATCH] V4L: Enable s-video input on DViCO FusionHDTV5 Lite * bttv-cards.c: - Enable S-Video input on DViCO FusionHDTV5 Lite Signed-off-by: Michael Krufky Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/media/video/bttv-cards.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/media/video/bttv-cards.c b/drivers/media/video/bttv-cards.c index 6c332800d6a..0881a17d522 100644 --- a/drivers/media/video/bttv-cards.c +++ b/drivers/media/video/bttv-cards.c @@ -2393,10 +2393,10 @@ struct tvcard bttv_tvcards[] = { .tuner = 0, .tuner_type = TUNER_LG_TDVS_H062F, .tuner_addr = ADDR_UNSET, - .video_inputs = 2, + .video_inputs = 3, .audio_inputs = 1, .svhs = 2, - .muxsel = { 2, 3 }, + .muxsel = { 2, 3, 1 }, .gpiomask = 0x00e00007, .audiomux = { 0x00400005, 0, 0x00000001, 0, 0x00c00007, 0 }, .no_msp34xx = 1, -- cgit v1.2.3 From 9149ccfa3571eaa4a4b444777d67fc4ed3ebcf27 Mon Sep 17 00:00:00 2001 From: Peter Bergner Date: Tue, 11 Oct 2005 09:28:24 -0700 Subject: [PATCH] ppc64: Add R_PPC64_TOC16 module reloc Newer gcc's are generating this relocation, so the module loader needs to handle it. Signed-off-by: Peter Bergner Signed-off-by: Anton Blanchard Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/ppc64/kernel/module.c | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/arch/ppc64/kernel/module.c b/arch/ppc64/kernel/module.c index c683bf88e69..928b8581fcb 100644 --- a/arch/ppc64/kernel/module.c +++ b/arch/ppc64/kernel/module.c @@ -341,6 +341,19 @@ int apply_relocate_add(Elf64_Shdr *sechdrs, *(unsigned long *)location = my_r2(sechdrs, me); break; + case R_PPC64_TOC16: + /* Subtact TOC pointer */ + value -= my_r2(sechdrs, me); + if (value + 0x8000 > 0xffff) { + printk("%s: bad TOC16 relocation (%lu)\n", + me->name, value); + return -ENOEXEC; + } + *((uint16_t *) location) + = (*((uint16_t *) location) & ~0xffff) + | (value & 0xffff); + break; + case R_PPC64_TOC16_DS: /* Subtact TOC pointer */ value -= my_r2(sechdrs, me); -- cgit v1.2.3 From f5154a98a1931641f0448f6512294a15279110d7 Mon Sep 17 00:00:00 2001 From: Hugh Dickins Date: Tue, 11 Oct 2005 19:16:26 +0100 Subject: [PATCH] Don't map the same page too much Refuse to install a page into a mapping if the mapping count is already ridiculously large. You probably cannot trigger this on 32-bit architectures, but on a 64-bit setup we should protect against it. Signed-off-by: Hugh Dickins Signed-off-by: Linus Torvalds --- mm/fremap.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/mm/fremap.c b/mm/fremap.c index 3235fb77c13..ab23a0673c3 100644 --- a/mm/fremap.c +++ b/mm/fremap.c @@ -89,6 +89,9 @@ int install_page(struct mm_struct *mm, struct vm_area_struct *vma, size = (i_size_read(inode) + PAGE_CACHE_SIZE - 1) >> PAGE_CACHE_SHIFT; if (!page->mapping || page->index >= size) goto err_unlock; + err = -ENOMEM; + if (page_mapcount(page) > INT_MAX/2) + goto err_unlock; zap_pte(mm, vma, addr, pte); -- cgit v1.2.3 From b1b510aa284af1908d5d369d52f7dae16aaabd71 Mon Sep 17 00:00:00 2001 From: "David S. Miller" Date: Tue, 11 Oct 2005 15:45:16 -0700 Subject: [SPARC64]: Fix net booting on Ultra5 We were not doing alignment properly when remapping the kernel image. What we want is a 4MB aligned physical address to map at KERNBASE. Mistakedly we were 4MB aligning the virtual address where the kernel initially sits, that's wrong. Instead, we should PAGE align the virtual address, then 4MB align the physical address result the prom gives to us. Signed-off-by: David S. Miller --- arch/sparc64/kernel/head.S | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/arch/sparc64/kernel/head.S b/arch/sparc64/kernel/head.S index f1dcdf8f743..4c942f71184 100644 --- a/arch/sparc64/kernel/head.S +++ b/arch/sparc64/kernel/head.S @@ -191,8 +191,9 @@ prom_boot_mapping_phys_low: stx %l3, [%sp + 2047 + 128 + 0x10] ! num_rets, 5 stx %l2, [%sp + 2047 + 128 + 0x18] ! arg1: "translate" stx %l5, [%sp + 2047 + 128 + 0x20] ! arg2: prom_mmu_ihandle_cache - srlx %l0, 22, %l3 - sllx %l3, 22, %l3 + /* PAGE align */ + srlx %l0, 13, %l3 + sllx %l3, 13, %l3 stx %l3, [%sp + 2047 + 128 + 0x28] ! arg3: vaddr, our PC stx %g0, [%sp + 2047 + 128 + 0x30] ! res1 stx %g0, [%sp + 2047 + 128 + 0x38] ! res2 @@ -211,6 +212,9 @@ prom_boot_mapping_phys_low: ldx [%sp + 2047 + 128 + 0x48], %l2 ! physaddr high stx %l2, [%l4 + 0x0] ldx [%sp + 2047 + 128 + 0x50], %l3 ! physaddr low + /* 4MB align */ + srlx %l3, 22, %l3 + sllx %l3, 22, %l3 stx %l3, [%l4 + 0x8] /* Leave service as-is, "call-method" */ -- cgit v1.2.3